Index: r36/LESS1 ================================================================== --- r36/LESS1 +++ r36/LESS1 @@ -1,296 +1,296 @@ -COMMENT - - - REDUCE INTERACTIVE LESSON NUMBER 1 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 1 of 7 interactive lessons about the REDUCE -system for computer symbolic mathematics. These lessons presume an -acquaintance with elementary calculus, together with a previous -exposure to some computer programming language. - -These lessons have been designed for use on a DEC system 10 or 20. -Apart from changes to the prompt and interrupt characters however -they should work just as well with any REDUCE implementation. - -In REDUCE, any sequence of characters from the word "COMMENT" through -the next semicolon or dollar-sign statement separator is an -explanatory remark ignored by the system. In general, either -separator signals the end of a statement, with the dollar sign -suppressing any output that might otherwise automatically be produced -by the statement. The typing of a carriage return initiates the -immediate sequential execution of all statements which have been -terminated on that line. When REDUCE is ready for more input, it will -prompt you with an asterisk at the left margin. - -To terminate the lesson and return to the operating system, type an -interrupt character (DEC: control-C ) at any time. - -Expressions can be formed using "**", "*", "/", "+", and "-" to -indicate exponentiation, multiplication, division, addition, and -subtraction or negation respectively. Assignments to variables can -be done using the operator ":=". For example:; - -R2D2 := (987654321/15)**3; - -COMMENT The immediately preceding line, without a semicolon, is the -computed output generated by the line with a semicolon which precedes -it. Note that exact indefinite-precision rational arithmetic was -used, in contrast to the limited-precision arithmetic of traditional -programming languages. - -We can use the name R2D2 to represent its value in subsequent -expressions such as; - -R2D2 := -R2D2/25 + 3*(13-5); - -COMMENT Now I will give you an opportunity to try some analogous -computations. To do so, type the letter N followed by a carriage return -in response to our question "CONT?" (You could type Y if you wish to -relinquish this opportunity, but I strongly recommend reinforced -learning through active participation.) After trying an example or two, -type the command "CONT" terminated by a semicolon and carriage return -when you wish to proceed with the rest of the lesson. To avoid -interference with our examples, please don't assign anything to any -variable names beginning with the letters E through I. To avoid lengthy -delays, I recommend keeping all of your examples approximately as -trivial as ours, saving your more ambitious experiments until after the -lesson. If you happen to initiate a calculation requiring an undue -amount of time to evaluate or to print, you can abort that computation -with an interrupt to get back to the operating system. Restart REDUCE, -followed by the statement "IN LESS1", followed by a semicolon and -return, to restart the lesson at the beginning; - -PAUSE; - -COMMENT Now watch this example illustrating some more dramatic -differences from traditional scientific programming systems:; - -E1 := 2*G + 3*G + H**3/H; - -COMMENT Note how we are allowed to use variables to which we have -assigned no values! Note too how similar terms and similar factors -are combined automatically. REDUCE also automatically expands -products and powers of sums, together with placing expressions over -common denominators, as illustrated by the examples:; - -E2 := E1*(F+G); -E2 := E1**2; -E1+1/E1; - -COMMENT Our last example also illustrates that there is no need to -assign an expression if we do not plan to use its value later. Try -some similar examples:; - -PAUSE; - -COMMENT It is not always desirable to expand expressions over a -common denominator, and we can use the OFF statement to turn off -either or both computational switches which control these -transformations. The switch named EXP controls EXPansion, and the -switch named MCD controls the Making of Common Denominators; - -OFF EXP, MCD; -E2 := E1**2 $ -E2 := E2*(F+G) + 1/E1; -COMMENT To turn these switches back on, we type:; - -ON EXP, MCD; - -COMMENT Try a few relevant examples with these switches turned off -individually and jointly; - -PAUSE; - -ON EXP; % Just in case you turned it off. - -COMMENT Now consider the example:; - -E2 := (2*(F*H)**2 - F**2*G*H - (F*G)**2 - F*H**3 + F*H*G**2 - H**4 - + G*H**3)/(F**2*H - F**2*G - F*H**2 + 2*F*G*H - F*G**2 - - G*H**2 + G**2*H); - -COMMENT It is not obvious, but the numerator and denominator of this -expression share a nontrivial common divisor which can be canceled. -To make REDUCE automatically cancel greatest common divisors, we turn -on the computational switch named GCD:; - -ON GCD; -E2; - -COMMENT The switch is not on by default because - - 1. It can consume a lot of time. - 2. Often we know in advance the few places where a nontrivial - GCD can occur in our problem. - 3. Even without GCD cancellation, expansion and common denomin- - ators guarantee that any rational expression which is equiv- - alent to zero simplifies to zero. - 4. When the denominator is the greatest common divisor, such - as for (X**2 - 2*X + 1)/(X-1), REDUCE cancels the - greatest common divisor even when GCD is OFF. - 5. GCD cancellation sometimes makes expressions more - complicated, such as with (F**10 - G**10)/(F**2 + F*G -2*G**2). - -Try the examples mentioned in this comment, together with one -or two other relevant ones; - -PAUSE; - -COMMENT Exact rational arithmetic can consume an alarming amount of -computer time when the constituent integers have quite large -magnitudes, and the results become awkward to interpret -qualitatively. When this is the case and somewhat inexact numerical -coefficients are acceptable, we can have the arithmetic done floating -point by turning on the computational switch ROUNDED. With this switch -on, any non-integer rational numbers are approximated by floating-point -numbers, and the result of any arithmetic operation is floating-point -when any of its operands is floating point. For example:; - -ON ROUNDED; -E1:= (12.3456789E3 *F + 3*G)**2 + 1/2; - -COMMENT With ROUNDED off, any floating-point constants are -automatically approximated by rational numbers:; - -OFF ROUNDED; -E1 := 12.35*G; -PAUSE; - -COMMENT A number of elementary functions, such as SIN, COS and LOG, -are built into REDUCE. Moreover, the letter E represents the base of -the natural logarithms, so the exponentiation operator enables us to -represent the exponential function as well as fractional powers. For -example:; - -E1:= SIN(-F*G) + LOG(E) + (3*G**2*COS(-1))**(1/2); - -COMMENT What automatic simplifications can you identify in this -example? - -Note that most REDUCE implementations do not approximate the values -of these functions for non-trivial numerical arguments, and exact -computations are generally impossible for such cases. - -Experimentally determine some other built-in simplifications for -these functions; - -PAUSE; - -COMMENT Later you will learn how to introduce additional -simplifications and additional functions, including numerical -approximations for examples such as COS(1). - -Differentiation is also built-into REDUCE. For example, to -differentiate E1 with respect to F; - -E2 := DF(E1,F); - -COMMENT To compute the second derivative of E2 with respect to G, we -can type either DF(E2,G,2) or DF(E1,F,1,G,2) or DF(E1,F,G,2) or -DF(E1,G,2,F,1) or; - -DF(E1,G,2,F); - -COMMENT Surely you can't resist trying a few derivatives of your -own! (Careful, High-order derivatives can be alarmingly complicated); - -PAUSE; - -COMMENT REDUCE uses the name I to represent (-1)**(1/2), -incorporating some simplification rules such as replacing I**2 by -1. -Here is an opportunity to experimentally determine other -simplifications such as for I**3, 1/I**23, and (I**2-1)/(I-1); - -PAUSE; - -COMMENT Clearly it is inadvisable to use E or I as a variable. T is -also inadvisable for reasons that will become clear later. - -The value of a variable is said to be "bound" to the variable. Any -variable to which we have assigned a value is called a bound variable, -and any variable to which we have not assigned a value is called an -indeterminate. Occasionally it is desirable to make a bound variable -into an indeterminate, and this can be done using the CLEAR command. -For example:; - -CLEAR R2D2, E1, E2; -E2; - -COMMENT If you suspect that a degenerate assignment, such as E1:=E1, -would suffice to clear a bound variable, try it on one of your own -bound variables:; - -PAUSE; - -COMMENT REDUCE also supports matrix algebra, as illustrated by the -following sequence:; - -MATRIX E1(4,1), F, H; - -COMMENT This declaration establishes E1 as a matrix with 4 rows and 1 -column, while establishing F and H as matrices of unspecified size. -To establish element values (and sizes if not already established in -the MATRIX declaration), we can use the MAT function, as illustrated -by the following example:; - -H := MAT((LOG(G), G+3), (G, 5/7)); - -COMMENT Only after establishing the size and establishing the element -values of a declared matrix by executing a matrix assignment can we -refer to an individual element or to the matrix as a whole. For -example to increase the last element of H by 1 then form twice the -transpose of H, we can type; - -H(2,2) := H(2,2) + 1; -2*TP(H); - -COMMENT To compute the determinant of H:; - -DET(H); - -COMMENT To compute the trace of H:; - -TRACE(H); - -COMMENT To compute the inverse of H, we can type H**(-1) or 1/H. To -compute the solution to the equation H*F = MAT((G),(2)), we can -left-multiply the right-hand side by the inverse of H:; - -F := 1/H*MAT((G),(2)); - -COMMENT Notes: - 1. MAT((G),(2))/H would denote right-multiplication by the - inverse, which is not what we want. - 2. Solutions for a set of right-hand-side vectors are most - efficiently computed simultaneously by collecting the right- - hand sides together as the columns of a single multiple-column - matrix. - 3. Subexpressions of the form 1/H*... or H**(-1)*... are computed - more efficiently than if the inverse is computed separately in - a previous statement, so separate computation of the inverse - is advisable only if several solutions are desired and if - they cannot be computed simultaneously. - 4. MAT must have parentheses around each row of elements even if - there is only one row or only one element per row. - 5. References to individual matrix elements must have exactly two - subscripts, even if the matrix has only one row or one column. - -Congratulations on completing lesson 1! I urge you to try a sequence of -more ambitious examples for the various features that have been -introduced, in order to gain some familiarity with the relationship -between problem size and computing time for various operations. (In most -implementations, the command "ON TIME" causes computing time to be -printed.) I also urge you to bring to the next lesson appropriate -examples from textbooks, articles, or elsewhere, in order to experience -the decisive learning reinforcement afforded by meaningful personal -examples that are not arbitrarily contrived. - -To avoid the possibility of interference from assignments and declar- -ations in lesson 1, it is wise to execute lesson 2 in a fresh REDUCE -job, when you are ready. - -;END; +COMMENT + + + REDUCE INTERACTIVE LESSON NUMBER 1 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 1 of 7 interactive lessons about the REDUCE +system for computer symbolic mathematics. These lessons presume an +acquaintance with elementary calculus, together with a previous +exposure to some computer programming language. + +These lessons have been designed for use on a DEC system 10 or 20. +Apart from changes to the prompt and interrupt characters however +they should work just as well with any REDUCE implementation. + +In REDUCE, any sequence of characters from the word "COMMENT" through +the next semicolon or dollar-sign statement separator is an +explanatory remark ignored by the system. In general, either +separator signals the end of a statement, with the dollar sign +suppressing any output that might otherwise automatically be produced +by the statement. The typing of a carriage return initiates the +immediate sequential execution of all statements which have been +terminated on that line. When REDUCE is ready for more input, it will +prompt you with an asterisk at the left margin. + +To terminate the lesson and return to the operating system, type an +interrupt character (DEC: control-C ) at any time. + +Expressions can be formed using "**", "*", "/", "+", and "-" to +indicate exponentiation, multiplication, division, addition, and +subtraction or negation respectively. Assignments to variables can +be done using the operator ":=". For example:; + +R2D2 := (987654321/15)**3; + +COMMENT The immediately preceding line, without a semicolon, is the +computed output generated by the line with a semicolon which precedes +it. Note that exact indefinite-precision rational arithmetic was +used, in contrast to the limited-precision arithmetic of traditional +programming languages. + +We can use the name R2D2 to represent its value in subsequent +expressions such as; + +R2D2 := -R2D2/25 + 3*(13-5); + +COMMENT Now I will give you an opportunity to try some analogous +computations. To do so, type the letter N followed by a carriage return +in response to our question "CONT?" (You could type Y if you wish to +relinquish this opportunity, but I strongly recommend reinforced +learning through active participation.) After trying an example or two, +type the command "CONT" terminated by a semicolon and carriage return +when you wish to proceed with the rest of the lesson. To avoid +interference with our examples, please don't assign anything to any +variable names beginning with the letters E through I. To avoid lengthy +delays, I recommend keeping all of your examples approximately as +trivial as ours, saving your more ambitious experiments until after the +lesson. If you happen to initiate a calculation requiring an undue +amount of time to evaluate or to print, you can abort that computation +with an interrupt to get back to the operating system. Restart REDUCE, +followed by the statement "IN LESS1", followed by a semicolon and +return, to restart the lesson at the beginning; + +PAUSE; + +COMMENT Now watch this example illustrating some more dramatic +differences from traditional scientific programming systems:; + +E1 := 2*G + 3*G + H**3/H; + +COMMENT Note how we are allowed to use variables to which we have +assigned no values! Note too how similar terms and similar factors +are combined automatically. REDUCE also automatically expands +products and powers of sums, together with placing expressions over +common denominators, as illustrated by the examples:; + +E2 := E1*(F+G); +E2 := E1**2; +E1+1/E1; + +COMMENT Our last example also illustrates that there is no need to +assign an expression if we do not plan to use its value later. Try +some similar examples:; + +PAUSE; + +COMMENT It is not always desirable to expand expressions over a +common denominator, and we can use the OFF statement to turn off +either or both computational switches which control these +transformations. The switch named EXP controls EXPansion, and the +switch named MCD controls the Making of Common Denominators; + +OFF EXP, MCD; +E2 := E1**2 $ +E2 := E2*(F+G) + 1/E1; +COMMENT To turn these switches back on, we type:; + +ON EXP, MCD; + +COMMENT Try a few relevant examples with these switches turned off +individually and jointly; + +PAUSE; + +ON EXP; % Just in case you turned it off. + +COMMENT Now consider the example:; + +E2 := (2*(F*H)**2 - F**2*G*H - (F*G)**2 - F*H**3 + F*H*G**2 - H**4 + + G*H**3)/(F**2*H - F**2*G - F*H**2 + 2*F*G*H - F*G**2 + - G*H**2 + G**2*H); + +COMMENT It is not obvious, but the numerator and denominator of this +expression share a nontrivial common divisor which can be canceled. +To make REDUCE automatically cancel greatest common divisors, we turn +on the computational switch named GCD:; + +ON GCD; +E2; + +COMMENT The switch is not on by default because + + 1. It can consume a lot of time. + 2. Often we know in advance the few places where a nontrivial + GCD can occur in our problem. + 3. Even without GCD cancellation, expansion and common denomin- + ators guarantee that any rational expression which is equiv- + alent to zero simplifies to zero. + 4. When the denominator is the greatest common divisor, such + as for (X**2 - 2*X + 1)/(X-1), REDUCE cancels the + greatest common divisor even when GCD is OFF. + 5. GCD cancellation sometimes makes expressions more + complicated, such as with (F**10 - G**10)/(F**2 + F*G -2*G**2). + +Try the examples mentioned in this comment, together with one +or two other relevant ones; + +PAUSE; + +COMMENT Exact rational arithmetic can consume an alarming amount of +computer time when the constituent integers have quite large +magnitudes, and the results become awkward to interpret +qualitatively. When this is the case and somewhat inexact numerical +coefficients are acceptable, we can have the arithmetic done floating +point by turning on the computational switch ROUNDED. With this switch +on, any non-integer rational numbers are approximated by floating-point +numbers, and the result of any arithmetic operation is floating-point +when any of its operands is floating point. For example:; + +ON ROUNDED; +E1:= (12.3456789E3 *F + 3*G)**2 + 1/2; + +COMMENT With ROUNDED off, any floating-point constants are +automatically approximated by rational numbers:; + +OFF ROUNDED; +E1 := 12.35*G; +PAUSE; + +COMMENT A number of elementary functions, such as SIN, COS and LOG, +are built into REDUCE. Moreover, the letter E represents the base of +the natural logarithms, so the exponentiation operator enables us to +represent the exponential function as well as fractional powers. For +example:; + +E1:= SIN(-F*G) + LOG(E) + (3*G**2*COS(-1))**(1/2); + +COMMENT What automatic simplifications can you identify in this +example? + +Note that most REDUCE implementations do not approximate the values +of these functions for non-trivial numerical arguments, and exact +computations are generally impossible for such cases. + +Experimentally determine some other built-in simplifications for +these functions; + +PAUSE; + +COMMENT Later you will learn how to introduce additional +simplifications and additional functions, including numerical +approximations for examples such as COS(1). + +Differentiation is also built-into REDUCE. For example, to +differentiate E1 with respect to F; + +E2 := DF(E1,F); + +COMMENT To compute the second derivative of E2 with respect to G, we +can type either DF(E2,G,2) or DF(E1,F,1,G,2) or DF(E1,F,G,2) or +DF(E1,G,2,F,1) or; + +DF(E1,G,2,F); + +COMMENT Surely you can't resist trying a few derivatives of your +own! (Careful, High-order derivatives can be alarmingly complicated); + +PAUSE; + +COMMENT REDUCE uses the name I to represent (-1)**(1/2), +incorporating some simplification rules such as replacing I**2 by -1. +Here is an opportunity to experimentally determine other +simplifications such as for I**3, 1/I**23, and (I**2-1)/(I-1); + +PAUSE; + +COMMENT Clearly it is inadvisable to use E or I as a variable. T is +also inadvisable for reasons that will become clear later. + +The value of a variable is said to be "bound" to the variable. Any +variable to which we have assigned a value is called a bound variable, +and any variable to which we have not assigned a value is called an +indeterminate. Occasionally it is desirable to make a bound variable +into an indeterminate, and this can be done using the CLEAR command. +For example:; + +CLEAR R2D2, E1, E2; +E2; + +COMMENT If you suspect that a degenerate assignment, such as E1:=E1, +would suffice to clear a bound variable, try it on one of your own +bound variables:; + +PAUSE; + +COMMENT REDUCE also supports matrix algebra, as illustrated by the +following sequence:; + +MATRIX E1(4,1), F, H; + +COMMENT This declaration establishes E1 as a matrix with 4 rows and 1 +column, while establishing F and H as matrices of unspecified size. +To establish element values (and sizes if not already established in +the MATRIX declaration), we can use the MAT function, as illustrated +by the following example:; + +H := MAT((LOG(G), G+3), (G, 5/7)); + +COMMENT Only after establishing the size and establishing the element +values of a declared matrix by executing a matrix assignment can we +refer to an individual element or to the matrix as a whole. For +example to increase the last element of H by 1 then form twice the +transpose of H, we can type; + +H(2,2) := H(2,2) + 1; +2*TP(H); + +COMMENT To compute the determinant of H:; + +DET(H); + +COMMENT To compute the trace of H:; + +TRACE(H); + +COMMENT To compute the inverse of H, we can type H**(-1) or 1/H. To +compute the solution to the equation H*F = MAT((G),(2)), we can +left-multiply the right-hand side by the inverse of H:; + +F := 1/H*MAT((G),(2)); + +COMMENT Notes: + 1. MAT((G),(2))/H would denote right-multiplication by the + inverse, which is not what we want. + 2. Solutions for a set of right-hand-side vectors are most + efficiently computed simultaneously by collecting the right- + hand sides together as the columns of a single multiple-column + matrix. + 3. Subexpressions of the form 1/H*... or H**(-1)*... are computed + more efficiently than if the inverse is computed separately in + a previous statement, so separate computation of the inverse + is advisable only if several solutions are desired and if + they cannot be computed simultaneously. + 4. MAT must have parentheses around each row of elements even if + there is only one row or only one element per row. + 5. References to individual matrix elements must have exactly two + subscripts, even if the matrix has only one row or one column. + +Congratulations on completing lesson 1! I urge you to try a sequence of +more ambitious examples for the various features that have been +introduced, in order to gain some familiarity with the relationship +between problem size and computing time for various operations. (In most +implementations, the command "ON TIME" causes computing time to be +printed.) I also urge you to bring to the next lesson appropriate +examples from textbooks, articles, or elsewhere, in order to experience +the decisive learning reinforcement afforded by meaningful personal +examples that are not arbitrarily contrived. + +To avoid the possibility of interference from assignments and declar- +ations in lesson 1, it is wise to execute lesson 2 in a fresh REDUCE +job, when you are ready. + +;END; Index: r36/LESS2 ================================================================== --- r36/LESS2 +++ r36/LESS2 @@ -1,253 +1,253 @@ -COMMENT - - REDUCE INTERACTIVE LESSON NUMBER 2 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 2 of 7 REDUCE lessons. Please refrain from -using variables beginning with the letters F through H during the -lesson. - -By now you have probably had the experience of generating an -expression, and then having to repeat the calculation because you -forgot to assign it to a variable or because you did not expect to -want to use it later. REDUCE maintains a history of all inputs and -computation during an interactive session. (Note, this is only for -interactive sessions.) To use an input expression in a new -computation, you can say - - INPUT(n) - -where n is the appropriate command number. The evaluated computations -can be accessed through - - WS(n) or simply WS - -if you wish to refer to the last computation. WS stands for Work Space. -As with all REDUCE expressions, these can also be used to create new -expressions: - - (INPUT(n)/WS(n2))**2 - -Special characters can be used to make unique REDUCE variable names -that reduce the chance of accidental interference with any other -variables. In general, whenever you want to include an otherwise -forbidden character such as * in a name, merely precede it by an -exclamation point, which is called the escape character. However, -pick a character other than "*", which is used for many internal -REDUCE names. Otherwise, if most of us use "*" the purpose will be -defeated; - -G+!%H; -WS; -PAUSE; - -COMMENT You can also name the expression in the workspace by using -the command SAVEAS, for example:; - -SAVEAS GPLUSH; -GPLUSH; -PAUSE; - -COMMENT You may have noticed that REDUCE imposes its own order on the -indeterminates and functional forms that appear in results, and that -this ordering can strongly affect the intelligibility of the results. -For example:; - -G1:= 2*H*G + E + F1 + F + F**2 + F2 + 5 + LOG(F1) + SIN(F1); - -COMMENT The ORDER declaration permits us to order indeterminates and -functional forms as we choose. For example, to order F2 before F1, -and to order F1 before all remaining variables:; - -ORDER F2, F1; -G1; -PAUSE; - -COMMENT Now suppose we partially change our mind and decide to -order LOG(F1) ahead of F1; - -ORDER LOG(F1), F1; -G1; - -COMMENT Note that any other indeterminates or functional forms under -the influence of a previous ORDER declaration, such as F2, rank -before those mentioned in the later declaration. Try to determine -the default ordering algorithm used in your REDUCE implementation, and -try to achieve some delicate rearrangements using the ORDER -declaration.; - -PAUSE; - -COMMENT You may have also noticed that REDUCE factors out any -number, indeterminate, functional form, or the largest integer power -thereof which exactly divides every term of a result or every term of -a parenthesized subexpression of a result. For example:; - -ON EXP, MCD; -G1:= F**2*(G**2 + 2*G) + F*(G**2+H)/(2*F1); - -COMMENT This process usually leads to more compact expressions and -reveals important structural information. However, the process can -yield results which are difficult to interpret if the resulting -parentheses are nested more than about two levels, and it is often -desirable to see a fully expanded result to facilitate direct -comparison of all terms. To suppress this monomial factoring, we can -turn off an output control switch named ALLFAC; - -OFF ALLFAC; -G1; -PAUSE; - -COMMENT The ALLFAC monomial-factorization process is strongly -dependent upon the ordering. We can achieve a more selective monomial -factorization by using the FACTOR declaration, which declares a -variable to have FACTOR status. If any indeterminates or functional -forms occurring in an expression are in FACTOR status when the -expression is printed, terms having the same powers of the -indeterminates or functional forms are collected together, and the -power is factored out. Terms containing two or more indeterminates or -functional forms under FACTOR status are not included in this monomial -factorization process. For example:; - -OFF ALLFAC; FACTOR F; G1; -FACTOR G; G1; PAUSE; - -COMMENT We can use the REMFAC command to remove items from factor -status; - -REMFAC F; -G1; - -COMMENT ALLFAC can still have an effect on the coefficients of the -monomials that have been factored out under the influence of FACTOR:; - -ON ALLFAC; -G1; -PAUSE; - -COMMENT It is often desirable to distribute denominators over all -factored subexpressions generated under the influence of a FACTOR -declaration, such as when we wish to view a result as a polynomial or -as a power series in the factored indeterminates or functional forms, -with coefficients which are rational functions of any other -indeterminates or functional forms. (A mnemonic aid is: think RAT -for RATional-function coefficients.) For example:; - -ON RAT; -G1; -PAUSE; - -COMMENT RAT has no effect on expressions which have no -indeterminates or functional forms under the influence of FACTOR. -The related but different DIV switch permits us to distribute numerical -and monomial factors of the denominator over every term of the -numerator, expressing these distributed portions as rational-number -coefficients and negative power factors respectively. (A mnemonic -aid: DIV DIVides by monomials.) The overall effect can also depend -strongly on whether the RAT switch is on or off. Series and -polynomials are often most attractive with RAT and DIV both on; - -ON DIV, RAT; -G1; -OFF RAT; -G1; -PAUSE; - -REMFAC G; -G1; -PAUSE; - -COMMENT With a very complicated result, detailed study of the result -is often facilitated by having each new term begin on a new line, -which can be accomplished using the LIST switch:; - -ON LIST; -G1; -PAUSE; - -COMMENT In various combinations, ORDER, FACTOR, the computational -switches EXP, MCD, GCD, and ROUNDED, together with the output control -switches ALLFAC, RAT, DIV, and LIST provide a variety of output -alternatives. With experience, it is usually possible to use these -tools to produce a result in the desired form, or at least in a form -which is far more acceptable than the one produced by the default -settings. I encourage you to experiment with various combinations -while this information is fresh in your mind; - -PAUSE; -OFF LIST, RAT, DIV, GCD, ROUNDED; -ON ALLFAC, MCD, EXP; - -COMMENT You may have wondered whether or not an assignment to a -variable, say F1, automatically updates the value of a bound -variable, say G1, which was previously assigned an expression -containing F1. The answer is: - - 1. If F1 was a bound variable in the expression when it was set - to G1, then subsequent changes to the value of F1 have no - effect on G1 because all traces of F1 in G1 disappeared after - F1 contributed its value to the formation of G1. - 2. If F1 was an indeterminate in an expression previously - assigned to G1, then for each subsequent use of G1, F1 - contributes its current value at the time of that use. - -These phenomena are illustrated by the following sequence:; - -PAUSE; -F2 := F; -G1 := F1 + F2; -F2 := G; -G1; -F1 := G; -F1 := H; -G1; -F1 := G; -G1; - -COMMENT Experience indicates that it is well worth studying this -sequence and experimenting with others until these phenomena are -thoroughly understood. You might, for example, mimic the above -example, but with another level of evaluation included by inserting a -statement analogous to "Q9:=G1" after "F2:=G", and inserting an -expression analogous to "Q9" at the end, to compare with G1. ; - -PAUSE; -COMMENT Note also, that if an indeterminate is used directly, or -indirectly through another expression, in evaluating itself, this will -lead to an infinite recursion. For example, the following expression -results in infinite recursion at the first evaluation of H1. On some -machines (Vax/Unix, IBM) this will cause REDUCE to terminate abnormally. - - H1 := H1 + 1 - -You may experiment with this problem, later at your own risk. - -It is often desirable to make an assignment to an indeterminate in a -previously established expression have a permanent effect, as if the -assignment were done before forming the expression. This can be done by -using the substitute function, SUB. - -G1 := F1 + F2; - -H1 := SUB(F1=H, G1); -F1 := G; -H1; - -COMMENT Note the use of "=" rather than ":=" in SUB. This function -is also valuable for achieving the effect of a local assignment -within a subexpression, without binding the involved indeterminate or -functional form in the rest of the expression or wherever else it -occurs. More generally the SUB function can have any number of -equations of the form "indeterminate or functional form = -expression", separated by commas, before the expression which is its -last argument. Try devising a set of examples which reveals whether -such multiple substitutions are done left to right, right to left, in -parallel, or unpredictably. - -This is the end of lesson 2. To execute lesson 3, start a fresh -REDUCE job. - -;END; +COMMENT + + REDUCE INTERACTIVE LESSON NUMBER 2 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 2 of 7 REDUCE lessons. Please refrain from +using variables beginning with the letters F through H during the +lesson. + +By now you have probably had the experience of generating an +expression, and then having to repeat the calculation because you +forgot to assign it to a variable or because you did not expect to +want to use it later. REDUCE maintains a history of all inputs and +computation during an interactive session. (Note, this is only for +interactive sessions.) To use an input expression in a new +computation, you can say + + INPUT(n) + +where n is the appropriate command number. The evaluated computations +can be accessed through + + WS(n) or simply WS + +if you wish to refer to the last computation. WS stands for Work Space. +As with all REDUCE expressions, these can also be used to create new +expressions: + + (INPUT(n)/WS(n2))**2 + +Special characters can be used to make unique REDUCE variable names +that reduce the chance of accidental interference with any other +variables. In general, whenever you want to include an otherwise +forbidden character such as * in a name, merely precede it by an +exclamation point, which is called the escape character. However, +pick a character other than "*", which is used for many internal +REDUCE names. Otherwise, if most of us use "*" the purpose will be +defeated; + +G+!%H; +WS; +PAUSE; + +COMMENT You can also name the expression in the workspace by using +the command SAVEAS, for example:; + +SAVEAS GPLUSH; +GPLUSH; +PAUSE; + +COMMENT You may have noticed that REDUCE imposes its own order on the +indeterminates and functional forms that appear in results, and that +this ordering can strongly affect the intelligibility of the results. +For example:; + +G1:= 2*H*G + E + F1 + F + F**2 + F2 + 5 + LOG(F1) + SIN(F1); + +COMMENT The ORDER declaration permits us to order indeterminates and +functional forms as we choose. For example, to order F2 before F1, +and to order F1 before all remaining variables:; + +ORDER F2, F1; +G1; +PAUSE; + +COMMENT Now suppose we partially change our mind and decide to +order LOG(F1) ahead of F1; + +ORDER LOG(F1), F1; +G1; + +COMMENT Note that any other indeterminates or functional forms under +the influence of a previous ORDER declaration, such as F2, rank +before those mentioned in the later declaration. Try to determine +the default ordering algorithm used in your REDUCE implementation, and +try to achieve some delicate rearrangements using the ORDER +declaration.; + +PAUSE; + +COMMENT You may have also noticed that REDUCE factors out any +number, indeterminate, functional form, or the largest integer power +thereof which exactly divides every term of a result or every term of +a parenthesized subexpression of a result. For example:; + +ON EXP, MCD; +G1:= F**2*(G**2 + 2*G) + F*(G**2+H)/(2*F1); + +COMMENT This process usually leads to more compact expressions and +reveals important structural information. However, the process can +yield results which are difficult to interpret if the resulting +parentheses are nested more than about two levels, and it is often +desirable to see a fully expanded result to facilitate direct +comparison of all terms. To suppress this monomial factoring, we can +turn off an output control switch named ALLFAC; + +OFF ALLFAC; +G1; +PAUSE; + +COMMENT The ALLFAC monomial-factorization process is strongly +dependent upon the ordering. We can achieve a more selective monomial +factorization by using the FACTOR declaration, which declares a +variable to have FACTOR status. If any indeterminates or functional +forms occurring in an expression are in FACTOR status when the +expression is printed, terms having the same powers of the +indeterminates or functional forms are collected together, and the +power is factored out. Terms containing two or more indeterminates or +functional forms under FACTOR status are not included in this monomial +factorization process. For example:; + +OFF ALLFAC; FACTOR F; G1; +FACTOR G; G1; PAUSE; + +COMMENT We can use the REMFAC command to remove items from factor +status; + +REMFAC F; +G1; + +COMMENT ALLFAC can still have an effect on the coefficients of the +monomials that have been factored out under the influence of FACTOR:; + +ON ALLFAC; +G1; +PAUSE; + +COMMENT It is often desirable to distribute denominators over all +factored subexpressions generated under the influence of a FACTOR +declaration, such as when we wish to view a result as a polynomial or +as a power series in the factored indeterminates or functional forms, +with coefficients which are rational functions of any other +indeterminates or functional forms. (A mnemonic aid is: think RAT +for RATional-function coefficients.) For example:; + +ON RAT; +G1; +PAUSE; + +COMMENT RAT has no effect on expressions which have no +indeterminates or functional forms under the influence of FACTOR. +The related but different DIV switch permits us to distribute numerical +and monomial factors of the denominator over every term of the +numerator, expressing these distributed portions as rational-number +coefficients and negative power factors respectively. (A mnemonic +aid: DIV DIVides by monomials.) The overall effect can also depend +strongly on whether the RAT switch is on or off. Series and +polynomials are often most attractive with RAT and DIV both on; + +ON DIV, RAT; +G1; +OFF RAT; +G1; +PAUSE; + +REMFAC G; +G1; +PAUSE; + +COMMENT With a very complicated result, detailed study of the result +is often facilitated by having each new term begin on a new line, +which can be accomplished using the LIST switch:; + +ON LIST; +G1; +PAUSE; + +COMMENT In various combinations, ORDER, FACTOR, the computational +switches EXP, MCD, GCD, and ROUNDED, together with the output control +switches ALLFAC, RAT, DIV, and LIST provide a variety of output +alternatives. With experience, it is usually possible to use these +tools to produce a result in the desired form, or at least in a form +which is far more acceptable than the one produced by the default +settings. I encourage you to experiment with various combinations +while this information is fresh in your mind; + +PAUSE; +OFF LIST, RAT, DIV, GCD, ROUNDED; +ON ALLFAC, MCD, EXP; + +COMMENT You may have wondered whether or not an assignment to a +variable, say F1, automatically updates the value of a bound +variable, say G1, which was previously assigned an expression +containing F1. The answer is: + + 1. If F1 was a bound variable in the expression when it was set + to G1, then subsequent changes to the value of F1 have no + effect on G1 because all traces of F1 in G1 disappeared after + F1 contributed its value to the formation of G1. + 2. If F1 was an indeterminate in an expression previously + assigned to G1, then for each subsequent use of G1, F1 + contributes its current value at the time of that use. + +These phenomena are illustrated by the following sequence:; + +PAUSE; +F2 := F; +G1 := F1 + F2; +F2 := G; +G1; +F1 := G; +F1 := H; +G1; +F1 := G; +G1; + +COMMENT Experience indicates that it is well worth studying this +sequence and experimenting with others until these phenomena are +thoroughly understood. You might, for example, mimic the above +example, but with another level of evaluation included by inserting a +statement analogous to "Q9:=G1" after "F2:=G", and inserting an +expression analogous to "Q9" at the end, to compare with G1. ; + +PAUSE; +COMMENT Note also, that if an indeterminate is used directly, or +indirectly through another expression, in evaluating itself, this will +lead to an infinite recursion. For example, the following expression +results in infinite recursion at the first evaluation of H1. On some +machines (Vax/Unix, IBM) this will cause REDUCE to terminate abnormally. + + H1 := H1 + 1 + +You may experiment with this problem, later at your own risk. + +It is often desirable to make an assignment to an indeterminate in a +previously established expression have a permanent effect, as if the +assignment were done before forming the expression. This can be done by +using the substitute function, SUB. + +G1 := F1 + F2; + +H1 := SUB(F1=H, G1); +F1 := G; +H1; + +COMMENT Note the use of "=" rather than ":=" in SUB. This function +is also valuable for achieving the effect of a local assignment +within a subexpression, without binding the involved indeterminate or +functional form in the rest of the expression or wherever else it +occurs. More generally the SUB function can have any number of +equations of the form "indeterminate or functional form = +expression", separated by commas, before the expression which is its +last argument. Try devising a set of examples which reveals whether +such multiple substitutions are done left to right, right to left, in +parallel, or unpredictably. + +This is the end of lesson 2. To execute lesson 3, start a fresh +REDUCE job. + +;END; Index: r36/LESS3 ================================================================== --- r36/LESS3 +++ r36/LESS3 @@ -1,362 +1,362 @@ -COMMENT - REDUCE INTERACTIVE LESSON NUMBER 3 - - David R. Stoutemyer - University of Hawaii - - Update for REDUCE 3.4 - Herbert Melenk - Konrad-Zuse-Zentrum Berlin - -COMMENT This is lesson 3 of 7 REDUCE lessons. Please refrain from -using variables beginning with the letters F through H during the -lesson. - -Mathematics is replete with many named elementary and not-so- -elementary functions besides the set built into REDUCE such as SIN, -COS, and LOG, and it is often convenient to utilize expressions -containing a functional form such as f(x) to denote an unknown -function or a class of functions. Functions are called operators in -REDUCE, and by merely declaring their names as such, we are free to -use them for functional forms. For example; - -OPERATOR F; -G1 := F(F(COT(F)), F()); - -COMMENT Note that - 1. We can use the same name for both a variable and an operator. - (However, this practice often leads to confusion.) - 2. We can use the same operator for any number of arguments -- - including zero arguments such as for F(). - 3. We can assign values to specific instances of functional - forms; - -PAUSE; -COMMENT COT is one of the functions already defined in REDUCE -together with a few of its properties. However, the user can augment -or even override these definitions depending on the needs of a given -problem. For example, if one wished to write COT(F) in terms of TAN, -one could say; - -COT(F) := 1/TAN(F); -G1 := G1 + COT(H+1); - -PAUSE; - -COMMENT Naturally, our assignment for COT(F) did not affect -COT(H+1) in our example above. However, we can use a LET rule to -make all cotangents automatically be replaced by the reciprocal of -the corresponding tangents:; - -LET COT(~F) => 1/TAN(F); -G1; - -COMMENT Any variable preceded by a tilde is a dummy variable which -is distinct from any other previously or subsequently introduced -indeterminate, variable, or dummy variable having the same name -outside the rule. The leftmost occurrence of a dummy variable in -a rule must be marked with a tilde. - -The arguments to LET are either single rules or lists (explicitly -enlosed in {..} or as a variable with a list value). All elements -of a list have to be rules (i.e., expressions written in terms of -the operator "=>") or names of other rule lists. So alternatively -we could have written the above command as - LET COT(~F) => 1/TAN(F) - or as command sequence - RS:={COT(~F) => 1/TAN(F)} - LET RS - -The CLEARRULES command allows to clear one or more rules. They -have to be entered here in the same form as for LET - otherwise -REDUCE is unable to identify them. - -CLEARRULES COT(~F) => 1/TAN(F); -COT(G+5); - -COMMENT alternative forms would have been - CLEARRULES {COT(~F) => 1/TAN(F)} - or with the above value of RS - CLEARRULES RS -Note, that a call CLEAR RS would not remove the rule(s) from -the system - it only would remove the list value from the variable -RS; - -PAUSE; - -COMMENT The arguments of a functional form on the left-hand side of a -rule can be more complicated than mere indeterminates. For example, -we may wish to inform REDUCE how to differentiate expressions involving -a symbolic function P, whose derivative is expressed in terms of -another function Q; - -OPERATOR P,Q; -LET DF(P(~X),X) => Q(X)**2; - -DF(3*P(F*G), G); - -COMMENT Also, REDUCE obviously knows the chain rule; - -PAUSE; - -COMMENT As another example, suppose that we wish to employ the -angle-sum identities for SIN and COS; - -LET{SIN(~X+~Y) => SIN(X)*COS(Y) + SIN(Y)*COS(X), - COS(~X+~Y) => COS(X)*COS(Y) - SIN(X)*SIN(Y)}; -COS(5+F-G); - -COMMENT Note that: - 1. LET can have any number of replacement rules written - as a list. - 2. There was no need for rules with 3 or more addends, because - the above rules were automatically employed recursively, with - two of the three addends 5, F, and -G grouped together as one - of the dummy variables the first time through. - 3. Despite the subexpression F-G in our example, there was no - need to make rules for the difference of two angles, because - subexpressions of the form X-Y are treated as X+(-Y). - 4. Built-in rules were employed to convert expressions of the - form SIN(-X) or COS(-X) to -SIN(X) or COS(X) respectively. - -As an exercise, try to implement rules which transform the logarithms -of products and quotients respectively to sums and differences of -logarithms, while converting the logarithm of a power of a quantity to -the power times the logarithm of the quantity; PAUSE; - -COMMENT Actually, the left-hand side of a rule also can be -somewhat more general than a functional form. The left-hand side can -be a power of an indeterminate or of a functional form, or the left- -hand side can be a product of such powers and/or indeterminates or -functional forms. For example, we can have the rule -"SIN(~X)**2=>1-COS(~X)**2", or we can have the rule; - -LET COS(~X)**2 => 1 - SIN(~X)**2; -G1 := COS(F)**3 + COS(G); -PAUSE; - -COMMENT Note that a replacement takes place wherever a left-hand side of -a rule divides a term. With a rule replacing SIN(X)**2 and a rule -replacing COS(X)**2 simultaneously in effect, an expression which uses -either one will lead to an infinite recursion that eventually exhausts -the available storage. (Try it if you wish -- after the lesson). We are -also permitted to employ a more symmetric rule using a top level "+" -provided that no free variables appear in the rule. However, a rule -such as "SIN(~X)**2+COS(X)**2=>1" is not permitted. We can -get around the restriction against a top-level "+" on the left side -though, at the minor nuisance of having to employ an operator whenever -we want the rule applied to an expression:; - -CLEARRULES COS(~X)**2 => 1 - SIN(~X)**2; -OPERATOR TRIGSIMP; -TRIGSIMP_RULES:= - {TRIGSIMP(~A*SIN(~X)**2 + A*COS(X)**2 + ~C) => A + TRIGSIMP(C), - TRIGSIMP(~A*SIN(~X)**2 + A*COS(X)**2) => A, - TRIGSIMP(SIN(~X)**2 + COS(X)**2 + ~C) => 1 + TRIGSIMP(C), - TRIGSIMP(SIN(~X)**2 + COS(X)**2) => 1, - TRIGSIMP(~X) => X}$ -G1 := F*COS(G)**2 + F*SIN(G)**2 + G*SIN(G)**2 + G*COS(G)**2 + 5; -G1 := TRIGSIMP(G1) WHERE TRIGSIMP_RULES; -PAUSE; - - -COMMENT Here we use another syntactical paradigm: the rule list -is assigned to a name (here TRIGSIMP_RULES) and it is activated -only locally for one evaluation, using the WHERE clause. - -Why doesn't our rule TRIGSIMP(~X)=>X defeat the other more -specific ones? The reason is that rules inside a list are applied in a -first-in-first-applied order, with the whole process immediately -restarted whenever any rule succeeds. Thus the rule TRIGSIMP(X)=X, -intended to make the operator TRIGSIMP eventually evaporate, is tried -only after all of the genuine simplification rules have done all that -they can. For such reasons we usually write rules for an operator in -an order which proceeds from the most specific to the most general -cases. Experimentation will reveal that TRIGSIMP will not simplify -higher powers of sine and cosine, such as COS(X)**4 + -2*COS(X)**2*SIN(X)**2 + SIN(X)**4, and that TRIGSIMP will not -necessarily work when there are more than 6 terms. This latter -restriction is not fundamental but is a practical one imposed to keep -the combinatorial searching associated with the current algorithm -under reasonable control. As an exercise, see if you can generalize -the rules sufficiently so that 5*COS(H)**2+6*SIN(H)**2 simplifies to -5 + SIN(H)**2 or to 6-COS(H)**2; - -PAUSE; - -COMMENT rules do not need to have free variables. For -example, we could introduce the simplification rule to replace all -subsequent instances of M*C**2 by ENERGY; - -CLEAR M,C,ENERGY; -G1 := (3*M**2*C**2 + M*C**3 + C**2 + M + M*C + M1*C1**2) - WHERE M*C**2 => ENERGY; -PAUSE; - -COMMENT Suppose that instead we wish to replace M by ENERGY/C**2:; - -G1 WHERE M=>ENERGY/C**2; - -COMMENT You may wonder how a rule of the trivial form -"indeterminate => ..." differs from the corresponding assignment -"indeterminate := ...". The difference is - - 1. The rule does not replace any contained bound variables - with their values until the rule is actually used for a - replacement. - 2. The LET rule performs the evaluation of any contained bound - variables every time the rule is used. - -Thus, the rule "X => X + 1" would cause infinite recursion at the -first subsequent occurrence of X, as would the pair of rules -"{X=>Y, Y=>X}". (Try it! -- after the lesson.) To illustrate point 1 -above, compare the following sequence with the analogous earlier one in -lesson 2 using assignments throughout; - -CLEAR E1, F; -E2:= F; -LET F1 => E1 + E2; -F1; -E2 := G; -F1; -PAUSE; - -COMMENT For a subsequent example, we need to replace E**(I*X) by -COS(X)**2 + I*SIN(X)**2 for all X. See if you can successfully -introduce this rule; - -PAUSE; -E**I; - -COMMENT REDUCE does not match I as an instance of the pattern I*X -with X=1, so if you neglected to include a rule for this degenerate -case, do so now; - -PAUSE; -CLEAR X, N, NMINUS1; -ZERO := E**(N*I*X) - E**(NMINUS1*I*X)*E**(I*X); -REALZERO := SUB(I=0, ZERO); -IMAGZERO := SUB(I=0, -I*ZERO); - -COMMENT Regarding the last two assignments as equations, we can solve -them to get recurrence relations defining SIN(N*X) and COS(N*X) in -terms of angles having lower multiplicity. - -Can you figure out why I didn't use N-1 rather than NMINUS1 above? - -Can you devise a similar technique to derive the angle-sum identities -that we previously implemented?; - -PAUSE; - -COMMENT To implement a set of trigonometric multiple-angle expansion -rules, we need to match the patterns SIN(N*X) and COS(N*X) only when N -is an integer exceeding 1. We can implement one of the necessary rules -as follows; - - COS(~N*~X) => COS(X)*COS((N-1)*X) - SIN(X)*SIN((N-1)*X) - WHEN FIXP N AND N>1 - -COMMENT Note: - 1. In a conditional rule, any dummy variables should - appear in the lhs of the replacement with a tilde. - 2. FIXP, standing for fix Predicate, is a built-in function - which yields true if and only if its argument is an integer. - In lesson 6 we will learn how to write such a function - exclusively for integers. Other useful predicates - are NUMBERP (it is true if its argument represents a - numeric value, that is an integer, a rational number - or a rounded (floating point) number) and EVENP - (which is true if the argument is an integer multiple - of 2). - 3. Arbitrarily-complicated true-false conditions can be composed - using the relational operators =, NEQ, <, >, <=, >=, together - with the logical operators "AND", "OR", "NOT". - 4. Operators < , >, <=, and >= work only when both sides are - numbers. - 5. The relational operators have higher precedence than "NOT", - which has higher precedence than "AND", which has higher - precedence than "OR". - 6. In a sequence of items joined by "AND" operators, testing is - done left to right, and testing is discontinued after the - first item which is false. - 7. In a sequence of items joined by "OR" operators, testing is - done left to right, and testing is discontinued after the - first item which is true. - 8. We didn't actually need the "AND N>1" part in the above rule - Can you guess why? - -Your mission is to complete the set of multiple-angle rules and to -test them on the example COS(4*X) + COS(X/3) + COS(F*X); - -PAUSE; - -COMMENT Now suppose that we wish to write a set of rules for doing -symbolic integration, such that expressions of the form -INTEGRATE(X**P,X) are replaced by X**(P+1)/(P+1) for arbitrary X and -P, provided P is independent of X. This will of course be less -complete that the analytic integration package available with REDUCE, -but for specific classes of integrals it is often a reasonable way to -do such integration. Noting that DF(P,X) is 0 if P is independent of -X, we can accomplish this as follows; - -OPERATOR INTEGRATE; -LET INTEGRATE(~X**~P,X) => X**(P+1)/(P+1) WHEN DF(P,X)=0; -INTEGRATE(F**5,F); -INTEGRATE(G**G, G); -INTEGRATE(F**G,F); - -PAUSE; - -G1 := INTEGRATE(G*F**5,F) + INTEGRATE(F**5+F**G,F); - -COMMENT The last example indicates that we must incorporate rules -which distribute integrals over sums and extract factors which are -independent of the second argument of INTEGRATE. Can you think of -rules which accomplish this? It is a good exercise, but this -particular pair of properties of INTEGRATE is so prevalent in -mathematics that operators with these properties are called linear, -and a corresponding declaration is built into REDUCE; - -LINEAR INTEGRATE; -G1; -G1:= INTEGRATE(F+1,F) + INTEGRATE(1/F**5,F); - -PAUSE; - -COMMENT We overcame one difficulty and uncovered 3 others. Clearly -REDUCE does not regard F to match the pattern F**P as F**1, or 1 to -match the pattern as F**0, or 1/F**5 to match the pattern as F**(-1), -so we can add additional rules for such cases; - -LET { - INTEGRATE(1/~X**~P,X) => X**(1-P)/(1-P) WHEN DF(P,X)=0, - INTEGRATE(~X,X) => X**2/2, - INTEGRATE(1,~X) => X}$ -G1; - -COMMENT A remaining problem is that INTEGRATE(X**-1,X) will lead to -X**0/(-1+1), which simplifies to 1/0, which will cause a zero-divide -error message. Consequently, we should also include the correct rule -for this special case; - -LET INTEGRATE(~X**-1,X) => LOG(X); -INTEGRATE(1/X,X); - -PAUSE; - -COMMENT We now collect the integration rules so far to one list -according to the law that within a rule set a more specific rule -should precede the more general one; - -INTEGRATE_RULES := -{ INTEGRATE(1,~X) => X, - INTEGRATE(~X,X) => X**2/2, - INTEGRATE(~X**-1,X) => LOG(X), - INTEGRATE(1/~X**~P,X) => X**(1-P)/(1-P) WHEN DF(P,X)=0, - INTEGRATE(~X**~P,X) => X**(P+1)/(P+1) WHEN DF(P,X)=0}$ - -COMMENT This is the end of lesson 3. We leave it as an intriguing -exercise to extend this integrator. - -;END; +COMMENT + REDUCE INTERACTIVE LESSON NUMBER 3 + + David R. Stoutemyer + University of Hawaii + + Update for REDUCE 3.4 + Herbert Melenk + Konrad-Zuse-Zentrum Berlin + +COMMENT This is lesson 3 of 7 REDUCE lessons. Please refrain from +using variables beginning with the letters F through H during the +lesson. + +Mathematics is replete with many named elementary and not-so- +elementary functions besides the set built into REDUCE such as SIN, +COS, and LOG, and it is often convenient to utilize expressions +containing a functional form such as f(x) to denote an unknown +function or a class of functions. Functions are called operators in +REDUCE, and by merely declaring their names as such, we are free to +use them for functional forms. For example; + +OPERATOR F; +G1 := F(F(COT(F)), F()); + +COMMENT Note that + 1. We can use the same name for both a variable and an operator. + (However, this practice often leads to confusion.) + 2. We can use the same operator for any number of arguments -- + including zero arguments such as for F(). + 3. We can assign values to specific instances of functional + forms; + +PAUSE; +COMMENT COT is one of the functions already defined in REDUCE +together with a few of its properties. However, the user can augment +or even override these definitions depending on the needs of a given +problem. For example, if one wished to write COT(F) in terms of TAN, +one could say; + +COT(F) := 1/TAN(F); +G1 := G1 + COT(H+1); + +PAUSE; + +COMMENT Naturally, our assignment for COT(F) did not affect +COT(H+1) in our example above. However, we can use a LET rule to +make all cotangents automatically be replaced by the reciprocal of +the corresponding tangents:; + +LET COT(~F) => 1/TAN(F); +G1; + +COMMENT Any variable preceded by a tilde is a dummy variable which +is distinct from any other previously or subsequently introduced +indeterminate, variable, or dummy variable having the same name +outside the rule. The leftmost occurrence of a dummy variable in +a rule must be marked with a tilde. + +The arguments to LET are either single rules or lists (explicitly +enlosed in {..} or as a variable with a list value). All elements +of a list have to be rules (i.e., expressions written in terms of +the operator "=>") or names of other rule lists. So alternatively +we could have written the above command as + LET COT(~F) => 1/TAN(F) + or as command sequence + RS:={COT(~F) => 1/TAN(F)} + LET RS + +The CLEARRULES command allows to clear one or more rules. They +have to be entered here in the same form as for LET - otherwise +REDUCE is unable to identify them. + +CLEARRULES COT(~F) => 1/TAN(F); +COT(G+5); + +COMMENT alternative forms would have been + CLEARRULES {COT(~F) => 1/TAN(F)} + or with the above value of RS + CLEARRULES RS +Note, that a call CLEAR RS would not remove the rule(s) from +the system - it only would remove the list value from the variable +RS; + +PAUSE; + +COMMENT The arguments of a functional form on the left-hand side of a +rule can be more complicated than mere indeterminates. For example, +we may wish to inform REDUCE how to differentiate expressions involving +a symbolic function P, whose derivative is expressed in terms of +another function Q; + +OPERATOR P,Q; +LET DF(P(~X),X) => Q(X)**2; + +DF(3*P(F*G), G); + +COMMENT Also, REDUCE obviously knows the chain rule; + +PAUSE; + +COMMENT As another example, suppose that we wish to employ the +angle-sum identities for SIN and COS; + +LET{SIN(~X+~Y) => SIN(X)*COS(Y) + SIN(Y)*COS(X), + COS(~X+~Y) => COS(X)*COS(Y) - SIN(X)*SIN(Y)}; +COS(5+F-G); + +COMMENT Note that: + 1. LET can have any number of replacement rules written + as a list. + 2. There was no need for rules with 3 or more addends, because + the above rules were automatically employed recursively, with + two of the three addends 5, F, and -G grouped together as one + of the dummy variables the first time through. + 3. Despite the subexpression F-G in our example, there was no + need to make rules for the difference of two angles, because + subexpressions of the form X-Y are treated as X+(-Y). + 4. Built-in rules were employed to convert expressions of the + form SIN(-X) or COS(-X) to -SIN(X) or COS(X) respectively. + +As an exercise, try to implement rules which transform the logarithms +of products and quotients respectively to sums and differences of +logarithms, while converting the logarithm of a power of a quantity to +the power times the logarithm of the quantity; PAUSE; + +COMMENT Actually, the left-hand side of a rule also can be +somewhat more general than a functional form. The left-hand side can +be a power of an indeterminate or of a functional form, or the left- +hand side can be a product of such powers and/or indeterminates or +functional forms. For example, we can have the rule +"SIN(~X)**2=>1-COS(~X)**2", or we can have the rule; + +LET COS(~X)**2 => 1 - SIN(~X)**2; +G1 := COS(F)**3 + COS(G); +PAUSE; + +COMMENT Note that a replacement takes place wherever a left-hand side of +a rule divides a term. With a rule replacing SIN(X)**2 and a rule +replacing COS(X)**2 simultaneously in effect, an expression which uses +either one will lead to an infinite recursion that eventually exhausts +the available storage. (Try it if you wish -- after the lesson). We are +also permitted to employ a more symmetric rule using a top level "+" +provided that no free variables appear in the rule. However, a rule +such as "SIN(~X)**2+COS(X)**2=>1" is not permitted. We can +get around the restriction against a top-level "+" on the left side +though, at the minor nuisance of having to employ an operator whenever +we want the rule applied to an expression:; + +CLEARRULES COS(~X)**2 => 1 - SIN(~X)**2; +OPERATOR TRIGSIMP; +TRIGSIMP_RULES:= + {TRIGSIMP(~A*SIN(~X)**2 + A*COS(X)**2 + ~C) => A + TRIGSIMP(C), + TRIGSIMP(~A*SIN(~X)**2 + A*COS(X)**2) => A, + TRIGSIMP(SIN(~X)**2 + COS(X)**2 + ~C) => 1 + TRIGSIMP(C), + TRIGSIMP(SIN(~X)**2 + COS(X)**2) => 1, + TRIGSIMP(~X) => X}$ +G1 := F*COS(G)**2 + F*SIN(G)**2 + G*SIN(G)**2 + G*COS(G)**2 + 5; +G1 := TRIGSIMP(G1) WHERE TRIGSIMP_RULES; +PAUSE; + + +COMMENT Here we use another syntactical paradigm: the rule list +is assigned to a name (here TRIGSIMP_RULES) and it is activated +only locally for one evaluation, using the WHERE clause. + +Why doesn't our rule TRIGSIMP(~X)=>X defeat the other more +specific ones? The reason is that rules inside a list are applied in a +first-in-first-applied order, with the whole process immediately +restarted whenever any rule succeeds. Thus the rule TRIGSIMP(X)=X, +intended to make the operator TRIGSIMP eventually evaporate, is tried +only after all of the genuine simplification rules have done all that +they can. For such reasons we usually write rules for an operator in +an order which proceeds from the most specific to the most general +cases. Experimentation will reveal that TRIGSIMP will not simplify +higher powers of sine and cosine, such as COS(X)**4 + +2*COS(X)**2*SIN(X)**2 + SIN(X)**4, and that TRIGSIMP will not +necessarily work when there are more than 6 terms. This latter +restriction is not fundamental but is a practical one imposed to keep +the combinatorial searching associated with the current algorithm +under reasonable control. As an exercise, see if you can generalize +the rules sufficiently so that 5*COS(H)**2+6*SIN(H)**2 simplifies to +5 + SIN(H)**2 or to 6-COS(H)**2; + +PAUSE; + +COMMENT rules do not need to have free variables. For +example, we could introduce the simplification rule to replace all +subsequent instances of M*C**2 by ENERGY; + +CLEAR M,C,ENERGY; +G1 := (3*M**2*C**2 + M*C**3 + C**2 + M + M*C + M1*C1**2) + WHERE M*C**2 => ENERGY; +PAUSE; + +COMMENT Suppose that instead we wish to replace M by ENERGY/C**2:; + +G1 WHERE M=>ENERGY/C**2; + +COMMENT You may wonder how a rule of the trivial form +"indeterminate => ..." differs from the corresponding assignment +"indeterminate := ...". The difference is + + 1. The rule does not replace any contained bound variables + with their values until the rule is actually used for a + replacement. + 2. The LET rule performs the evaluation of any contained bound + variables every time the rule is used. + +Thus, the rule "X => X + 1" would cause infinite recursion at the +first subsequent occurrence of X, as would the pair of rules +"{X=>Y, Y=>X}". (Try it! -- after the lesson.) To illustrate point 1 +above, compare the following sequence with the analogous earlier one in +lesson 2 using assignments throughout; + +CLEAR E1, F; +E2:= F; +LET F1 => E1 + E2; +F1; +E2 := G; +F1; +PAUSE; + +COMMENT For a subsequent example, we need to replace E**(I*X) by +COS(X)**2 + I*SIN(X)**2 for all X. See if you can successfully +introduce this rule; + +PAUSE; +E**I; + +COMMENT REDUCE does not match I as an instance of the pattern I*X +with X=1, so if you neglected to include a rule for this degenerate +case, do so now; + +PAUSE; +CLEAR X, N, NMINUS1; +ZERO := E**(N*I*X) - E**(NMINUS1*I*X)*E**(I*X); +REALZERO := SUB(I=0, ZERO); +IMAGZERO := SUB(I=0, -I*ZERO); + +COMMENT Regarding the last two assignments as equations, we can solve +them to get recurrence relations defining SIN(N*X) and COS(N*X) in +terms of angles having lower multiplicity. + +Can you figure out why I didn't use N-1 rather than NMINUS1 above? + +Can you devise a similar technique to derive the angle-sum identities +that we previously implemented?; + +PAUSE; + +COMMENT To implement a set of trigonometric multiple-angle expansion +rules, we need to match the patterns SIN(N*X) and COS(N*X) only when N +is an integer exceeding 1. We can implement one of the necessary rules +as follows; + + COS(~N*~X) => COS(X)*COS((N-1)*X) - SIN(X)*SIN((N-1)*X) + WHEN FIXP N AND N>1 + +COMMENT Note: + 1. In a conditional rule, any dummy variables should + appear in the lhs of the replacement with a tilde. + 2. FIXP, standing for fix Predicate, is a built-in function + which yields true if and only if its argument is an integer. + In lesson 6 we will learn how to write such a function + exclusively for integers. Other useful predicates + are NUMBERP (it is true if its argument represents a + numeric value, that is an integer, a rational number + or a rounded (floating point) number) and EVENP + (which is true if the argument is an integer multiple + of 2). + 3. Arbitrarily-complicated true-false conditions can be composed + using the relational operators =, NEQ, <, >, <=, >=, together + with the logical operators "AND", "OR", "NOT". + 4. Operators < , >, <=, and >= work only when both sides are + numbers. + 5. The relational operators have higher precedence than "NOT", + which has higher precedence than "AND", which has higher + precedence than "OR". + 6. In a sequence of items joined by "AND" operators, testing is + done left to right, and testing is discontinued after the + first item which is false. + 7. In a sequence of items joined by "OR" operators, testing is + done left to right, and testing is discontinued after the + first item which is true. + 8. We didn't actually need the "AND N>1" part in the above rule + Can you guess why? + +Your mission is to complete the set of multiple-angle rules and to +test them on the example COS(4*X) + COS(X/3) + COS(F*X); + +PAUSE; + +COMMENT Now suppose that we wish to write a set of rules for doing +symbolic integration, such that expressions of the form +INTEGRATE(X**P,X) are replaced by X**(P+1)/(P+1) for arbitrary X and +P, provided P is independent of X. This will of course be less +complete that the analytic integration package available with REDUCE, +but for specific classes of integrals it is often a reasonable way to +do such integration. Noting that DF(P,X) is 0 if P is independent of +X, we can accomplish this as follows; + +OPERATOR INTEGRATE; +LET INTEGRATE(~X**~P,X) => X**(P+1)/(P+1) WHEN DF(P,X)=0; +INTEGRATE(F**5,F); +INTEGRATE(G**G, G); +INTEGRATE(F**G,F); + +PAUSE; + +G1 := INTEGRATE(G*F**5,F) + INTEGRATE(F**5+F**G,F); + +COMMENT The last example indicates that we must incorporate rules +which distribute integrals over sums and extract factors which are +independent of the second argument of INTEGRATE. Can you think of +rules which accomplish this? It is a good exercise, but this +particular pair of properties of INTEGRATE is so prevalent in +mathematics that operators with these properties are called linear, +and a corresponding declaration is built into REDUCE; + +LINEAR INTEGRATE; +G1; +G1:= INTEGRATE(F+1,F) + INTEGRATE(1/F**5,F); + +PAUSE; + +COMMENT We overcame one difficulty and uncovered 3 others. Clearly +REDUCE does not regard F to match the pattern F**P as F**1, or 1 to +match the pattern as F**0, or 1/F**5 to match the pattern as F**(-1), +so we can add additional rules for such cases; + +LET { + INTEGRATE(1/~X**~P,X) => X**(1-P)/(1-P) WHEN DF(P,X)=0, + INTEGRATE(~X,X) => X**2/2, + INTEGRATE(1,~X) => X}$ +G1; + +COMMENT A remaining problem is that INTEGRATE(X**-1,X) will lead to +X**0/(-1+1), which simplifies to 1/0, which will cause a zero-divide +error message. Consequently, we should also include the correct rule +for this special case; + +LET INTEGRATE(~X**-1,X) => LOG(X); +INTEGRATE(1/X,X); + +PAUSE; + +COMMENT We now collect the integration rules so far to one list +according to the law that within a rule set a more specific rule +should precede the more general one; + +INTEGRATE_RULES := +{ INTEGRATE(1,~X) => X, + INTEGRATE(~X,X) => X**2/2, + INTEGRATE(~X**-1,X) => LOG(X), + INTEGRATE(1/~X**~P,X) => X**(1-P)/(1-P) WHEN DF(P,X)=0, + INTEGRATE(~X**~P,X) => X**(P+1)/(P+1) WHEN DF(P,X)=0}$ + +COMMENT This is the end of lesson 3. We leave it as an intriguing +exercise to extend this integrator. + +;END; Index: r36/LESS4 ================================================================== --- r36/LESS4 +++ r36/LESS4 @@ -1,554 +1,554 @@ -COMMENT - - - - REDUCE INTERACTIVE LESSON NUMBER 4 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 4 of 7 REDUCE lessons. As before, please -refrain from using variables beginning with the letters F through H -during the lesson. - -In theory, assignments and LET statements are sufficient to -accomplish anything that any other practical computing mechanism is -capable of doing. However, it is more convenient for some purposes -to use function procedures which can employ branched selection and -iteration as do most traditional programming languages. As a trivial -example, if we invariably wanted to replace cotangents with the -corresponding tangents, we could type; - -ALGEBRAIC PROCEDURE COT(X); 1/TAN(X); - -COMMENT As an example of the use of this function, we have; - -COT(LOG(F)); - -PAUSE; -COMMENT Note: - 1. The procedure definition automatically declares the procedure - name as an operator. - 2. A procedure can be executed any time after its definition, - until it is cleared. - 3. Any parameters are dummy variables that are distinct from - any other variables with the same name outside the procedure - definition, and the corresponding arguments can be - arbitrary expressions. - 4. The value returned by a procedure is the value of the - expression following the procedure statement. - -We can replace this definition with a different one; - -ALGEBRAIC PROCEDURE COT(Y); COS(Y)/SIN(Y); - -G1:= COT(LOG(F)); - -COMMENT In place of the word ALGEBRAIC, we can optionally use the -word INTEGER when a function always returns an integer value, or we -can optionally use the word REAL when a function always returns a -floating-point value. - -Try writing a procedure definition for the sine in terms of the -cosine, then type G1; - -PAUSE; - -COMMENT Here is a more complicated function which introduces the -notion of a conditional expression; - -ALGEBRAIC PROCEDURE SUMCHECK(AJ, J, M, N, S); - COMMENT J is an indeterminate and the other parameters are - expressions. This function returns the global variable named - PROVED if the function can inductively verify that S equals the - sum of AJ for J going from M through N, returning the global - variable named UNPROVED otherwise. For the best chance of - proving a correct sum, the function should be executed under - the influence of ON EXP, ON MCD, and any other user-supplied - simplification rules relevant to the expression classes of AJ - and S; - IF SUB(J=M,AJ)-SUB(N=M,S) NEQ 0 - OR S+SUB(J=N+1,AJ)-SUB(N=N+1,S) NEQ 0 THEN UNPROVED - ELSE PROVED; - -ON EXP, MCD; - -CLEAR X, J, N; - -SUMCHECK(J, J, 1, N, N*(N+1)/2); - -SUMCHECK(X**J, J, 0, N, (X**(N+1)-1)/(X-1)); - -COMMENT Within procedures of this sort a global variable is any -variable which is not one of the parameters, and a global variable -has the value, if any, which is current for that name at the point -from where the procedure is used. - -;PAUSE; COMMENT -Conditional expressions have the form - - IF condition THEN expression1 ELSE expression2. - -There are generally several equivalent ways of writing a conditional -expression. For example, the body of the above procedure could have -been written - - IF SUB(J=M,A)-SUB(N=M,S)=0 AND S+SUB(J=N+1,A)-SUB(N=N+1,S)=0 - THEN PROVED - ELSE UNPROVED. - -Note how we compare a difference with 0, rather than comparing -two nonzero expressions, for reasons explained in lesson 3. - -As an exercise, write a procedure analogous to SUMCHECK for proving -closed-form product formulas, then test it on the valid formula that -COS(N*X) equals the product of COS(J*X)/COS(J*X-X) for J ranging from -1 through N. You do not need to include prefatory comments -describing parameters and the returned value until you learn how to -use a text editor; - -PAUSE; - -COMMENT Most REDUCE statements are also expressions because they have -a value. The value is usually 0 if nothing else makes sense, but I -will mention the value only if it is useful. - -The value of an assignment statement is the assigned value. Thus a -multiple assignment, performed right to left, can be achieved by a -sequence of the form - - "variable1 := variable2 := ... := variableN := expression", - -moreover, assignments can be inserted within ordinary expressions -such as X*(Y:=5). Such assignments must usually be parenthesized -because of the low precedence of the assignment operator, and -excessive use of this construct tends to make programs confusing. - -;PAUSE;COMMENT - -REDUCE treats as a single expression any sequence of statements -preceded by the pair of adjacent characters << and followed by the -pair >>. The value of such a group expression is the value of the -last statement in the group. - -Group expressions facilitate the implementation of tasks that are -most easily stated as a sequence of operations. However, such -sequences often utilize temporary variables to count, hold -intermediate results, etc., and it is hazardous to use global -variables for that purpose. If a top-level REDUCE statement or -another function directly or indirectly uses that variable name, then -its value or its virgin indeterminate status there might be damaged -by our use as a temporary variable. In large programs or programs -which rely on the work of others, such interference has a -nonnegligible probability, even if all programmers agree to the -convention that all such temporary variables should begin with the -function name as a prefix and all programmers attempt to comply with -the convention. For this reason, REDUCE provides another -expression-valued sequence called a BEGIN-block, which permits the -declaration of local variables that are distinct from any other -variables outside the block having the same name. Another advantage -of using local variables for temporary variables is that the perhaps -large amount of storage occupied by their values can be reclaimed -after leaving their block. - -;PAUSE;COMMENT -A BEGIN-block consists of the word BEGIN, followed by optional -declarations, followed by a sequence of statements, followed by the -word END. Within BEGIN-blocks, it is often convenient to return -control and a value from someplace other than the end of the block. -Control and a value may be returned via a -RETURN-statement of the form - - RETURN expression -or - RETURN, - -0 being returned in the latter case. A BEGIN-block does not return -the value of the last statement. If a value is to be returned RETURN -must be used. These features and others are illustrated by the -following function; - -PAUSE; - -ALGEBRAIC PROCEDURE LIMIT(EX, INDET, PNT); - BEGIN COMMENT This function uses up through 4 iterations of - L'Hospital's rule to attempt determination of the limit of - expression EX as indeterminate INDET approaches expression - PNT. This function is intended for the case where - SUB(INDET=PNT, EX) yields 0/0, provoking a zero-divide - message. This function returns the global variable named - UNDEFINED when the limit is 0 dividing an expression which did - not simplify to 0, and this function returns the global - variable named UNKNOWN when it cannot determine the limit. - Otherwise this function returns an expression which is the - limit. For best results, this function should be executed - under the influence of ON EXP, ON MCD, and any user-supplied - simplification rules appropriate to the expression classes of - EX and PNT; - INTEGER ITERATION; - SCALAR N, D, NLIM, DLIM; - ITERATION := 0; - N := NUM(EX); - D := DEN(EX); - NLIM := SUB(INDET=PNT, N); - DLIM := SUB(INDET=PNT, D); - WHILE NLIM=0 AND DLIM=0 AND ITERATION<5 DO << - N := DF(N, INDET); - D := DF(D, INDET); - NLIM := SUB(INDET=PNT, N); - DLIM := SUB(INDET=PNT, D); - ITERATION := ITERATION + 1 >>; - RETURN (IF NLIM=0 THEN - IF DLIM=0 THEN UNKNOWN - ELSE 0 - ELSE IF DLIM=0 THEN UNDEFINED - ELSE NLIM/DLIM) - END; - -% Examples follow.. -PAUSE; - -G1 := (E**X-1)/X; - -% Evaluation at 1, causes Zero denominator error at top level, continue -% anyway. -SUB(X=0, G1); - -LIMIT(G1, X, 0); - -G1:= ((1-X)/LOG(X))**2; - -% Evaluation at 1, causes Zero denominator error at top level, continue -% anyway. -SUB(X=1, G1); - -LIMIT(G1, X, 1); - -COMMENT Note: - 1. The idea behind L'Hospital's rule is that as long as the - numerator and denominator are both zero at the limit point, we - can replace them by their derivatives without altering the - limit of the quotient. - 2. Assignments within groups and BEGIN-blocks do not - automatically cause output. - 3. Local variables are declared INTEGER, REAL, or SCALAR, the - latter corresponding to the same most general class denoted by - ALGEBRAIC in a procedure statement. All local variables are - initialized to zero, so they cannot serve as indeterminates. - Moreover, if we attempted to overcome this by clearing them, - we would clear all variables with their names. - 4. We do not declare the attributes of parameters. - 5. The NUM and DEN functions respectively extract the numerator - and denominator of their arguments. (With OFF MCD, the - denominator of 1+1/X would be 1.) - 6. The WHILE-loop has the general form - - WHILE condition DO statement. - - REDUCE also has a "GO TO" statement, and using commas rather - than semicolons to prevent termination of this comment, the - above general form of a WHILE-loop is equivalent to - - BEGIN GO TO TEST, - LOOP: statement, - TEST: IF condition THEN GO TO LOOP, - RETURN 0 - END . - - A GOTO statement is permitted only within a block, and the - GOTO statement cannot refer to a label outside the same block - or to a label inside a block that the GOTO statement is not - also within. Actually, 99.99% of REDUCE BEGIN-blocks are less - confusing if written entirely without GOTOs, and I mention - them primarily to explain WHILE-loops in terms of a more - primitive notion. - -;PAUSE;COMMENT - 7. The LIMIT function provides a good illustration of nested - conditional expressions. Proceeding sequentially through such - nests, each ELSE clause is matched with the nearest preceding - unmatched THEN clause in the group or block. In order to help - reveal their structure, I have consistently indented nested - conditional statements, continuations of multi-line statements - and loop-bodies according to one of the many staunchly - defended indentation styles. However, older versions of REDUCE - may ruin my elegant style. If you have such a version, I - encourage you to indent nonetheless, in anticipation of a - replacement for your obsolete version. (If you have an - instructor, I also urge you to humor him by adopting his style - for the duration of the course.) - 8. PL/I programmers take note: "IF ... THEN ... ELSE ..." is - regarded as one expression, and semicolons are used to - separate rather than terminate statements. Moreover, BEGIN - and END are brackets rather than statements, so a semicolon is - never needed immediately after BEGIN, and a semicolon is - necessary immediately preceding END only if the END is - intended as a labeled destination for a GOTO. Within - conditional expressions, an inappropriate semicolon after an - END, a >>, or an ELSE-clause is likely to be one of your most - prevalent mistakes.; -PAUSE; - -COMMENT The next exercise is based on the above LIMIT function: - -For the sum of positive expressions AJ for J ranging from some finite -initial value to infinity, the infinite series converges if the limit -of the ratio SUB(J=J+1,AJ)/AJ is less than 1 as J approaches -infinity. The series diverges if this limit exceeds 1, and the test -is inconclusive if the limit is 1. To convert the problem to the -form required by the above LIMIT program, we can replace J by the -indeterminate 1/!*FOO in the ratio, then take the limit as !*FOO -approaches zero. (Since an indeterminate is necessary here, I picked -the weird name !*FOO to make the chance of conflict negligible) - -After writing such a function to perform the ratio test, test it on -the examples AJ=J/2**J, AJ=1/J**2, AJ=2**J/J**10, and AJ=1/J. (The -first two converge and the second two diverge); - -PAUSE; - -COMMENT Groups or blocks can be used wherever any arbitrary -expression is allowed, including the right-hand side of a LET rule. - -The need for loops with an integer index variable running from a -given initial value through a given final value by a given increment -is so prevalent that REDUCE offers a convenient special way of -accomplishing it via a FOR-loop, which has the general form - - FOR index := initial STEP increment UNTIL final DO statement . - -Except for the use of commas as statement separators, this construct -is equivalent to - - BEGIN INTEGER index, - index := initial, - IF increment>0 THEN WHILE index <= final DO << - statement, - index := index + increment >> - ELSE WHILE index >= final DO << - statement, - index := index + increment >>, - RETURN 0 - END . - -;PAUSE;COMMENT -Note: - 1. The index variable is automatically declared local to the FOR- - loop. - 2. "initial", "increment", and "final" must have integer values. - 3. FORTRAN programmers take note: the body of the loop is not - automatically executed at least once. - 4. An acceptable abbreviation for "STEP 1 UNTIL" is ":". - 5. Since the WHILE-loop and the FOR-loop have implied BEGIN- - blocks, a RETURN statement within their bodies cannot transfer - control further than the point following the loops. - -Another frequent need is to produce output from within a group or -block, because such output is not automatically produced. This can -be done using the WRITE-statement, which has the form - -WRITE expression1, expression2, ..., expressionN. - -Beginning a new line with expression1, the expressions are printed -immediately adjacent to each other, split over line boundaries if -necessary. The value of the WRITE-statement is the value of its last -expression, and any of the expressions can be a character-string -of the form "character1 character2 ... characterM" . - -Inserting the word "WRITE" on a separate line before an assignment -is convenient for debugging, because the word is then easily deleted -afterward. These features and others are illustrated by the following -equation solver; - -PAUSE; -OPERATOR SOLVEFOR, SOLN; - -FOR ALL X, LHS, RHS LET SOLVEFOR(X, LHS, RHS) = SOLVEFOR(X, LHS-RHS); - -COMMENT LHS and RHS are expressions such that P=NUM(LHS-RHS) is a -polynomial of degree at most 2 in the indeterminate or functional -form X. Otherwise an error message is printed. As a convenience, -RHS can be omitted if it is 0. If P is quadratic in X, the two -values of X which satisfy P=0 are stored as the values of the -functional forms SOLN(1) and SOLN(2). If P is a first-degree -polynomial in X, SOLN(1) is set to the one solution. If P simplifies -to 0, SOLN(1) is set to the identifier ARBITRARY. If P is an -expression which does not simplify to zero but does not contain X, -SOLN(1) is set to the identifier NONE. In all other cases, SOLN(1) -is set to the identifier UNKNOWN. The function then returns the -number of SOLN forms which were set. This function prints a well -deserved warning message if the denominator of LHS-RHS contains X. If -LHS-RHS is not polynomial in X, it is wise to execute this function -under the influence of ON GCD; - -PAUSE; -FOR ALL X, LHSMRHS LET SOLVEFOR(X, LHSMRHS) = - BEGIN INTEGER HIPOW; SCALAR TEMP, CFLIST, CF0, CF1, CF2; - IF LHSMRHS = 0 THEN << - SOLN(1) := ARBITRARY; - RETURN 1 >>; - CFLIST := COEFF(LHSMRHS, X); - HIPOW := HIPOW!*; - IF HIPOW = 0 THEN << - SOLN(1) := NONE; - RETURN 1 >>; - IF HIPOW > 2 THEN << - SOLN(1) := UNKNOWN; - RETURN 1 >>; - IF HIPOW = 1 THEN << - SOLN(1) := FIRST(CFLIST)/SECOND(CFLIST); - IF DF(SUB(X=!*FOO, SOLN(1)), !*FOO) NEQ 0 THEN - SOLN(1) := UNKNOWN; - RETURN 1 >>; - CF0 := FIRST(CFLIST)/THIRD(CFLIST); - CF1 := -SECOND(CFLIST)/THIRD(CFLIST)/2; - IF DF(SUB(X=!*FOO, CF0), !*FOO) NEQ 0 - OR DF(SUB(X=!*FOO, CF1), !*FOO) NEQ 0 THEN << - SOLN(1) := UNKNOWN; - RETURN 1 >>; - TEMP := (CF1**2 - CF0)**(1/2); - SOLN(1) := CF1 + TEMP; - SOLN(2) := CF1 - TEMP; - RETURN 2 - END; - -COMMENT And some examples; -PAUSE; - -FOR K:=1:SOLVEFOR(X, A*X**2, -B*X-C) DO WRITE SOLN(K) := SOLN(K); - -FOR K:=1:SOLVEFOR(LOG(X), 5*LOG(X)-7) DO WRITE SOLN(K) := SOLN(K); - -FOR K:=1:SOLVEFOR(X, X, X) DO WRITE SOLN(K) := SOLN(K); - -FOR K:= 1:SOLVEFOR(X, 5) DO WRITE SOLN(K) := SOLN(K); - -FOR K:=1:SOLVEFOR(X, X**3+X+1) DO WRITE SOLN(K) := SOLN(K); - -FOR K:=1:SOLVEFOR(X, X*E**X, 1) DO WRITE SOLN(K) := SOLN(K); - -G1 := X/(E**X-1); - -%Results in 'invalid as POLYNOMIAL' error, continue anyway; -FOR K:=1:SOLVEFOR(X, G1) DO WRITE SOLN(K) := SOLN(K); - -SUB(X=SOLN(1), G1); - -LIMIT(G1, X, SOLN(1)); - -PAUSE; - -COMMENT Here we have used LET rules to permit the user the -convenience of omitting default arguments. (Function definitions have -to have a fixed number of parameters.) - -Array elements are designated by the same syntax as matrix elements -and as functional forms having integer arguments. Here are some -desiderata that may help you decide which of these alternatives is -most appropriate for a particular application: - 1. The lower bound of each array subscript is 0, vs. 1 for - matrices vs unrestricted for functional forms. - 2. The upper bound of each array subscript must have a specific - integer value at the time the array is declared, as must the - upper bounds of matrix subscripts when a matrix is first - referred to, on the left side of a matrix assignment. In - contrast, functional forms never require a commitment to a - specific upper bound. - 3. An array can have any fixed number of subscripts, a matrix - must have exactly 2, and a functional form can have a varying - arbitrary number. - 4. Matrix operations, such as transpose and inverse, are built-in - only for matrices. - 5. For most implementations, access to array elements requires - time approximately proportional to the number of subscripts, - whereas access to matrix elements takes time approximately - proportional to the sum of the two subscript values, whereas - access to functional forms takes average time approximately - proportional to the number of bound functional forms having - that name. - 6. Only functional forms permit the effect of a subscripted - indeterminate such as having an answer be "A(M,N) + B(3,4)". - 7. Only functional forms can be used alone in the LHS of LET - substitutions. -;PAUSE; COMMENT - 8. All arrays, matrices, and operators are global regardless - of where they are declared, so declaring them within a BEGIN - block does not afford the protection and automatic storage - recovery of local variables. Moreover, clearing them within a - BEGIN-block will clear them globally, and functions - cannot return an array or a matrix value. Furthermore, REDUCE - parameters are referenced by value, which means that an - assignment to a parameter has no effect on the corresponding - argument. Thus, matrix or array results cannot be transmitted - back to an argument either. - 9. It is often advantageous to use two or more of these - alternatives to represent a set of quantities at different - times in the same program. For example, to get the general - form of the inverse of a 3-by-3 matrix, we could write - - MATRIX AA, - OPERATOR A, - AA := MAT((0,0,0),(0,0,0),(0,0,0)), - FOR J:=1:3 DO - FOR K:=1:3 DO AA(J,K) := A(J,K), - AA**-1 . - - As another example, we might use an array to receive some - polynomial coefficients, then transfer the values to a matrix - for inversion. - -;PAUSE;COMMENT -The COEFF function is the remaining new feature in our SOLVEFOR -example. The first argument is a polynomial expression in the -indeterminate or functional form which is the second argument. The -polynomial coefficients of the integer powers of the indeterminate are -returned as a LIST, with the independent coefficient first. The -highest and lowest non-zero powers are placed in the variables HIPOW!* -and LOWPOW!* respectively. - -A LIST is a kind of data structure, just as matrices and arrays are. -It is represented as comma separated list of elements enclosed in -braces. The elements can be accessed with the functions FIRST, -SECOND, THIRD, PART(i) which returns the i-th element, and REST, which -returns a list of all but the first element. For example; - -CLEAR X; - -COEFF(X**5+2, X); - -LOWPOW!*; - -HIPOW!*; - -PAUSE; - -COMMENT COEFF does not check to make sure that the coefficients do not -contain its second argument within a functional form, so that is the -reason we differentiated. The reason we first substituted the -indeterminate !*FOO for the second argument is that differentiation -does not work with respect to a functional form. - -The last exercise is to rewrite the last rule so that we can solve -equations which simplify to the form - - a*x**(m+2*l) + b*x**(m+l) + c*x**m = 0, where m>=0 and l>=1. - -The solutions are - - 0, with multiplicity m, - x1*E**(2*j*I*pi/l), - x2*E**(2*j*I*pi/l), with j = 0, 1, ..., l-1, - -where x1 and x2 are the solutions to the quadratic equation - - a*x**2 + b*x + c = 0 . - -As a convenience to the user, you might also wish to have a global -switch named SOLVEPRINT, such that when it is nonzero, the solutions -are automatically printed. - -This is the end of lesson 4. When you are ready to run lesson 5, -start a new REDUCE job. - -;END; +COMMENT + + + + REDUCE INTERACTIVE LESSON NUMBER 4 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 4 of 7 REDUCE lessons. As before, please +refrain from using variables beginning with the letters F through H +during the lesson. + +In theory, assignments and LET statements are sufficient to +accomplish anything that any other practical computing mechanism is +capable of doing. However, it is more convenient for some purposes +to use function procedures which can employ branched selection and +iteration as do most traditional programming languages. As a trivial +example, if we invariably wanted to replace cotangents with the +corresponding tangents, we could type; + +ALGEBRAIC PROCEDURE COT(X); 1/TAN(X); + +COMMENT As an example of the use of this function, we have; + +COT(LOG(F)); + +PAUSE; +COMMENT Note: + 1. The procedure definition automatically declares the procedure + name as an operator. + 2. A procedure can be executed any time after its definition, + until it is cleared. + 3. Any parameters are dummy variables that are distinct from + any other variables with the same name outside the procedure + definition, and the corresponding arguments can be + arbitrary expressions. + 4. The value returned by a procedure is the value of the + expression following the procedure statement. + +We can replace this definition with a different one; + +ALGEBRAIC PROCEDURE COT(Y); COS(Y)/SIN(Y); + +G1:= COT(LOG(F)); + +COMMENT In place of the word ALGEBRAIC, we can optionally use the +word INTEGER when a function always returns an integer value, or we +can optionally use the word REAL when a function always returns a +floating-point value. + +Try writing a procedure definition for the sine in terms of the +cosine, then type G1; + +PAUSE; + +COMMENT Here is a more complicated function which introduces the +notion of a conditional expression; + +ALGEBRAIC PROCEDURE SUMCHECK(AJ, J, M, N, S); + COMMENT J is an indeterminate and the other parameters are + expressions. This function returns the global variable named + PROVED if the function can inductively verify that S equals the + sum of AJ for J going from M through N, returning the global + variable named UNPROVED otherwise. For the best chance of + proving a correct sum, the function should be executed under + the influence of ON EXP, ON MCD, and any other user-supplied + simplification rules relevant to the expression classes of AJ + and S; + IF SUB(J=M,AJ)-SUB(N=M,S) NEQ 0 + OR S+SUB(J=N+1,AJ)-SUB(N=N+1,S) NEQ 0 THEN UNPROVED + ELSE PROVED; + +ON EXP, MCD; + +CLEAR X, J, N; + +SUMCHECK(J, J, 1, N, N*(N+1)/2); + +SUMCHECK(X**J, J, 0, N, (X**(N+1)-1)/(X-1)); + +COMMENT Within procedures of this sort a global variable is any +variable which is not one of the parameters, and a global variable +has the value, if any, which is current for that name at the point +from where the procedure is used. + +;PAUSE; COMMENT +Conditional expressions have the form + + IF condition THEN expression1 ELSE expression2. + +There are generally several equivalent ways of writing a conditional +expression. For example, the body of the above procedure could have +been written + + IF SUB(J=M,A)-SUB(N=M,S)=0 AND S+SUB(J=N+1,A)-SUB(N=N+1,S)=0 + THEN PROVED + ELSE UNPROVED. + +Note how we compare a difference with 0, rather than comparing +two nonzero expressions, for reasons explained in lesson 3. + +As an exercise, write a procedure analogous to SUMCHECK for proving +closed-form product formulas, then test it on the valid formula that +COS(N*X) equals the product of COS(J*X)/COS(J*X-X) for J ranging from +1 through N. You do not need to include prefatory comments +describing parameters and the returned value until you learn how to +use a text editor; + +PAUSE; + +COMMENT Most REDUCE statements are also expressions because they have +a value. The value is usually 0 if nothing else makes sense, but I +will mention the value only if it is useful. + +The value of an assignment statement is the assigned value. Thus a +multiple assignment, performed right to left, can be achieved by a +sequence of the form + + "variable1 := variable2 := ... := variableN := expression", + +moreover, assignments can be inserted within ordinary expressions +such as X*(Y:=5). Such assignments must usually be parenthesized +because of the low precedence of the assignment operator, and +excessive use of this construct tends to make programs confusing. + +;PAUSE;COMMENT + +REDUCE treats as a single expression any sequence of statements +preceded by the pair of adjacent characters << and followed by the +pair >>. The value of such a group expression is the value of the +last statement in the group. + +Group expressions facilitate the implementation of tasks that are +most easily stated as a sequence of operations. However, such +sequences often utilize temporary variables to count, hold +intermediate results, etc., and it is hazardous to use global +variables for that purpose. If a top-level REDUCE statement or +another function directly or indirectly uses that variable name, then +its value or its virgin indeterminate status there might be damaged +by our use as a temporary variable. In large programs or programs +which rely on the work of others, such interference has a +nonnegligible probability, even if all programmers agree to the +convention that all such temporary variables should begin with the +function name as a prefix and all programmers attempt to comply with +the convention. For this reason, REDUCE provides another +expression-valued sequence called a BEGIN-block, which permits the +declaration of local variables that are distinct from any other +variables outside the block having the same name. Another advantage +of using local variables for temporary variables is that the perhaps +large amount of storage occupied by their values can be reclaimed +after leaving their block. + +;PAUSE;COMMENT +A BEGIN-block consists of the word BEGIN, followed by optional +declarations, followed by a sequence of statements, followed by the +word END. Within BEGIN-blocks, it is often convenient to return +control and a value from someplace other than the end of the block. +Control and a value may be returned via a +RETURN-statement of the form + + RETURN expression +or + RETURN, + +0 being returned in the latter case. A BEGIN-block does not return +the value of the last statement. If a value is to be returned RETURN +must be used. These features and others are illustrated by the +following function; + +PAUSE; + +ALGEBRAIC PROCEDURE LIMIT(EX, INDET, PNT); + BEGIN COMMENT This function uses up through 4 iterations of + L'Hospital's rule to attempt determination of the limit of + expression EX as indeterminate INDET approaches expression + PNT. This function is intended for the case where + SUB(INDET=PNT, EX) yields 0/0, provoking a zero-divide + message. This function returns the global variable named + UNDEFINED when the limit is 0 dividing an expression which did + not simplify to 0, and this function returns the global + variable named UNKNOWN when it cannot determine the limit. + Otherwise this function returns an expression which is the + limit. For best results, this function should be executed + under the influence of ON EXP, ON MCD, and any user-supplied + simplification rules appropriate to the expression classes of + EX and PNT; + INTEGER ITERATION; + SCALAR N, D, NLIM, DLIM; + ITERATION := 0; + N := NUM(EX); + D := DEN(EX); + NLIM := SUB(INDET=PNT, N); + DLIM := SUB(INDET=PNT, D); + WHILE NLIM=0 AND DLIM=0 AND ITERATION<5 DO << + N := DF(N, INDET); + D := DF(D, INDET); + NLIM := SUB(INDET=PNT, N); + DLIM := SUB(INDET=PNT, D); + ITERATION := ITERATION + 1 >>; + RETURN (IF NLIM=0 THEN + IF DLIM=0 THEN UNKNOWN + ELSE 0 + ELSE IF DLIM=0 THEN UNDEFINED + ELSE NLIM/DLIM) + END; + +% Examples follow.. +PAUSE; + +G1 := (E**X-1)/X; + +% Evaluation at 1, causes Zero denominator error at top level, continue +% anyway. +SUB(X=0, G1); + +LIMIT(G1, X, 0); + +G1:= ((1-X)/LOG(X))**2; + +% Evaluation at 1, causes Zero denominator error at top level, continue +% anyway. +SUB(X=1, G1); + +LIMIT(G1, X, 1); + +COMMENT Note: + 1. The idea behind L'Hospital's rule is that as long as the + numerator and denominator are both zero at the limit point, we + can replace them by their derivatives without altering the + limit of the quotient. + 2. Assignments within groups and BEGIN-blocks do not + automatically cause output. + 3. Local variables are declared INTEGER, REAL, or SCALAR, the + latter corresponding to the same most general class denoted by + ALGEBRAIC in a procedure statement. All local variables are + initialized to zero, so they cannot serve as indeterminates. + Moreover, if we attempted to overcome this by clearing them, + we would clear all variables with their names. + 4. We do not declare the attributes of parameters. + 5. The NUM and DEN functions respectively extract the numerator + and denominator of their arguments. (With OFF MCD, the + denominator of 1+1/X would be 1.) + 6. The WHILE-loop has the general form + + WHILE condition DO statement. + + REDUCE also has a "GO TO" statement, and using commas rather + than semicolons to prevent termination of this comment, the + above general form of a WHILE-loop is equivalent to + + BEGIN GO TO TEST, + LOOP: statement, + TEST: IF condition THEN GO TO LOOP, + RETURN 0 + END . + + A GOTO statement is permitted only within a block, and the + GOTO statement cannot refer to a label outside the same block + or to a label inside a block that the GOTO statement is not + also within. Actually, 99.99% of REDUCE BEGIN-blocks are less + confusing if written entirely without GOTOs, and I mention + them primarily to explain WHILE-loops in terms of a more + primitive notion. + +;PAUSE;COMMENT + 7. The LIMIT function provides a good illustration of nested + conditional expressions. Proceeding sequentially through such + nests, each ELSE clause is matched with the nearest preceding + unmatched THEN clause in the group or block. In order to help + reveal their structure, I have consistently indented nested + conditional statements, continuations of multi-line statements + and loop-bodies according to one of the many staunchly + defended indentation styles. However, older versions of REDUCE + may ruin my elegant style. If you have such a version, I + encourage you to indent nonetheless, in anticipation of a + replacement for your obsolete version. (If you have an + instructor, I also urge you to humor him by adopting his style + for the duration of the course.) + 8. PL/I programmers take note: "IF ... THEN ... ELSE ..." is + regarded as one expression, and semicolons are used to + separate rather than terminate statements. Moreover, BEGIN + and END are brackets rather than statements, so a semicolon is + never needed immediately after BEGIN, and a semicolon is + necessary immediately preceding END only if the END is + intended as a labeled destination for a GOTO. Within + conditional expressions, an inappropriate semicolon after an + END, a >>, or an ELSE-clause is likely to be one of your most + prevalent mistakes.; +PAUSE; + +COMMENT The next exercise is based on the above LIMIT function: + +For the sum of positive expressions AJ for J ranging from some finite +initial value to infinity, the infinite series converges if the limit +of the ratio SUB(J=J+1,AJ)/AJ is less than 1 as J approaches +infinity. The series diverges if this limit exceeds 1, and the test +is inconclusive if the limit is 1. To convert the problem to the +form required by the above LIMIT program, we can replace J by the +indeterminate 1/!*FOO in the ratio, then take the limit as !*FOO +approaches zero. (Since an indeterminate is necessary here, I picked +the weird name !*FOO to make the chance of conflict negligible) + +After writing such a function to perform the ratio test, test it on +the examples AJ=J/2**J, AJ=1/J**2, AJ=2**J/J**10, and AJ=1/J. (The +first two converge and the second two diverge); + +PAUSE; + +COMMENT Groups or blocks can be used wherever any arbitrary +expression is allowed, including the right-hand side of a LET rule. + +The need for loops with an integer index variable running from a +given initial value through a given final value by a given increment +is so prevalent that REDUCE offers a convenient special way of +accomplishing it via a FOR-loop, which has the general form + + FOR index := initial STEP increment UNTIL final DO statement . + +Except for the use of commas as statement separators, this construct +is equivalent to + + BEGIN INTEGER index, + index := initial, + IF increment>0 THEN WHILE index <= final DO << + statement, + index := index + increment >> + ELSE WHILE index >= final DO << + statement, + index := index + increment >>, + RETURN 0 + END . + +;PAUSE;COMMENT +Note: + 1. The index variable is automatically declared local to the FOR- + loop. + 2. "initial", "increment", and "final" must have integer values. + 3. FORTRAN programmers take note: the body of the loop is not + automatically executed at least once. + 4. An acceptable abbreviation for "STEP 1 UNTIL" is ":". + 5. Since the WHILE-loop and the FOR-loop have implied BEGIN- + blocks, a RETURN statement within their bodies cannot transfer + control further than the point following the loops. + +Another frequent need is to produce output from within a group or +block, because such output is not automatically produced. This can +be done using the WRITE-statement, which has the form + +WRITE expression1, expression2, ..., expressionN. + +Beginning a new line with expression1, the expressions are printed +immediately adjacent to each other, split over line boundaries if +necessary. The value of the WRITE-statement is the value of its last +expression, and any of the expressions can be a character-string +of the form "character1 character2 ... characterM" . + +Inserting the word "WRITE" on a separate line before an assignment +is convenient for debugging, because the word is then easily deleted +afterward. These features and others are illustrated by the following +equation solver; + +PAUSE; +OPERATOR SOLVEFOR, SOLN; + +FOR ALL X, LHS, RHS LET SOLVEFOR(X, LHS, RHS) = SOLVEFOR(X, LHS-RHS); + +COMMENT LHS and RHS are expressions such that P=NUM(LHS-RHS) is a +polynomial of degree at most 2 in the indeterminate or functional +form X. Otherwise an error message is printed. As a convenience, +RHS can be omitted if it is 0. If P is quadratic in X, the two +values of X which satisfy P=0 are stored as the values of the +functional forms SOLN(1) and SOLN(2). If P is a first-degree +polynomial in X, SOLN(1) is set to the one solution. If P simplifies +to 0, SOLN(1) is set to the identifier ARBITRARY. If P is an +expression which does not simplify to zero but does not contain X, +SOLN(1) is set to the identifier NONE. In all other cases, SOLN(1) +is set to the identifier UNKNOWN. The function then returns the +number of SOLN forms which were set. This function prints a well +deserved warning message if the denominator of LHS-RHS contains X. If +LHS-RHS is not polynomial in X, it is wise to execute this function +under the influence of ON GCD; + +PAUSE; +FOR ALL X, LHSMRHS LET SOLVEFOR(X, LHSMRHS) = + BEGIN INTEGER HIPOW; SCALAR TEMP, CFLIST, CF0, CF1, CF2; + IF LHSMRHS = 0 THEN << + SOLN(1) := ARBITRARY; + RETURN 1 >>; + CFLIST := COEFF(LHSMRHS, X); + HIPOW := HIPOW!*; + IF HIPOW = 0 THEN << + SOLN(1) := NONE; + RETURN 1 >>; + IF HIPOW > 2 THEN << + SOLN(1) := UNKNOWN; + RETURN 1 >>; + IF HIPOW = 1 THEN << + SOLN(1) := FIRST(CFLIST)/SECOND(CFLIST); + IF DF(SUB(X=!*FOO, SOLN(1)), !*FOO) NEQ 0 THEN + SOLN(1) := UNKNOWN; + RETURN 1 >>; + CF0 := FIRST(CFLIST)/THIRD(CFLIST); + CF1 := -SECOND(CFLIST)/THIRD(CFLIST)/2; + IF DF(SUB(X=!*FOO, CF0), !*FOO) NEQ 0 + OR DF(SUB(X=!*FOO, CF1), !*FOO) NEQ 0 THEN << + SOLN(1) := UNKNOWN; + RETURN 1 >>; + TEMP := (CF1**2 - CF0)**(1/2); + SOLN(1) := CF1 + TEMP; + SOLN(2) := CF1 - TEMP; + RETURN 2 + END; + +COMMENT And some examples; +PAUSE; + +FOR K:=1:SOLVEFOR(X, A*X**2, -B*X-C) DO WRITE SOLN(K) := SOLN(K); + +FOR K:=1:SOLVEFOR(LOG(X), 5*LOG(X)-7) DO WRITE SOLN(K) := SOLN(K); + +FOR K:=1:SOLVEFOR(X, X, X) DO WRITE SOLN(K) := SOLN(K); + +FOR K:= 1:SOLVEFOR(X, 5) DO WRITE SOLN(K) := SOLN(K); + +FOR K:=1:SOLVEFOR(X, X**3+X+1) DO WRITE SOLN(K) := SOLN(K); + +FOR K:=1:SOLVEFOR(X, X*E**X, 1) DO WRITE SOLN(K) := SOLN(K); + +G1 := X/(E**X-1); + +%Results in 'invalid as POLYNOMIAL' error, continue anyway; +FOR K:=1:SOLVEFOR(X, G1) DO WRITE SOLN(K) := SOLN(K); + +SUB(X=SOLN(1), G1); + +LIMIT(G1, X, SOLN(1)); + +PAUSE; + +COMMENT Here we have used LET rules to permit the user the +convenience of omitting default arguments. (Function definitions have +to have a fixed number of parameters.) + +Array elements are designated by the same syntax as matrix elements +and as functional forms having integer arguments. Here are some +desiderata that may help you decide which of these alternatives is +most appropriate for a particular application: + 1. The lower bound of each array subscript is 0, vs. 1 for + matrices vs unrestricted for functional forms. + 2. The upper bound of each array subscript must have a specific + integer value at the time the array is declared, as must the + upper bounds of matrix subscripts when a matrix is first + referred to, on the left side of a matrix assignment. In + contrast, functional forms never require a commitment to a + specific upper bound. + 3. An array can have any fixed number of subscripts, a matrix + must have exactly 2, and a functional form can have a varying + arbitrary number. + 4. Matrix operations, such as transpose and inverse, are built-in + only for matrices. + 5. For most implementations, access to array elements requires + time approximately proportional to the number of subscripts, + whereas access to matrix elements takes time approximately + proportional to the sum of the two subscript values, whereas + access to functional forms takes average time approximately + proportional to the number of bound functional forms having + that name. + 6. Only functional forms permit the effect of a subscripted + indeterminate such as having an answer be "A(M,N) + B(3,4)". + 7. Only functional forms can be used alone in the LHS of LET + substitutions. +;PAUSE; COMMENT + 8. All arrays, matrices, and operators are global regardless + of where they are declared, so declaring them within a BEGIN + block does not afford the protection and automatic storage + recovery of local variables. Moreover, clearing them within a + BEGIN-block will clear them globally, and functions + cannot return an array or a matrix value. Furthermore, REDUCE + parameters are referenced by value, which means that an + assignment to a parameter has no effect on the corresponding + argument. Thus, matrix or array results cannot be transmitted + back to an argument either. + 9. It is often advantageous to use two or more of these + alternatives to represent a set of quantities at different + times in the same program. For example, to get the general + form of the inverse of a 3-by-3 matrix, we could write + + MATRIX AA, + OPERATOR A, + AA := MAT((0,0,0),(0,0,0),(0,0,0)), + FOR J:=1:3 DO + FOR K:=1:3 DO AA(J,K) := A(J,K), + AA**-1 . + + As another example, we might use an array to receive some + polynomial coefficients, then transfer the values to a matrix + for inversion. + +;PAUSE;COMMENT +The COEFF function is the remaining new feature in our SOLVEFOR +example. The first argument is a polynomial expression in the +indeterminate or functional form which is the second argument. The +polynomial coefficients of the integer powers of the indeterminate are +returned as a LIST, with the independent coefficient first. The +highest and lowest non-zero powers are placed in the variables HIPOW!* +and LOWPOW!* respectively. + +A LIST is a kind of data structure, just as matrices and arrays are. +It is represented as comma separated list of elements enclosed in +braces. The elements can be accessed with the functions FIRST, +SECOND, THIRD, PART(i) which returns the i-th element, and REST, which +returns a list of all but the first element. For example; + +CLEAR X; + +COEFF(X**5+2, X); + +LOWPOW!*; + +HIPOW!*; + +PAUSE; + +COMMENT COEFF does not check to make sure that the coefficients do not +contain its second argument within a functional form, so that is the +reason we differentiated. The reason we first substituted the +indeterminate !*FOO for the second argument is that differentiation +does not work with respect to a functional form. + +The last exercise is to rewrite the last rule so that we can solve +equations which simplify to the form + + a*x**(m+2*l) + b*x**(m+l) + c*x**m = 0, where m>=0 and l>=1. + +The solutions are + + 0, with multiplicity m, + x1*E**(2*j*I*pi/l), + x2*E**(2*j*I*pi/l), with j = 0, 1, ..., l-1, + +where x1 and x2 are the solutions to the quadratic equation + + a*x**2 + b*x + c = 0 . + +As a convenience to the user, you might also wish to have a global +switch named SOLVEPRINT, such that when it is nonzero, the solutions +are automatically printed. + +This is the end of lesson 4. When you are ready to run lesson 5, +start a new REDUCE job. + +;END; Index: r36/LESS5 ================================================================== --- r36/LESS5 +++ r36/LESS5 @@ -1,460 +1,460 @@ -COMMENT - - REDUCE INTERACTIVE LESSON NUMBER 5 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 5 of 7 REDUCE lessons. - -There are at least two good reasons for wanting to save REDUCE -expression assignments on secondary storage: - 1. So that one can logout, then resume computation at a later - time. - 2. So that needed storage space can be cleared without - irrecoverably losing the values of variables which are not - needed in the next expression but will be needed later. - -Using trivial small expressions, the following sequence illustrates -how this could be done: - - OFF NAT, - OUT TEMP, - F1 := (F + G)**2, - G1 := G*F1, - OUT T, - CLEAR F1, - H1 := H*G1, - OUT TEMP, - CLEAR G1, - H2 := F*H1, - CLEAR H1, - SHUT TEMP, - IN TEMP, - F1, - ON NAT, - F1 . - -ON NAT yields the natural output style with raised exponents, which -is unsuitable for subsequent input. - -The OUT-statement causes subsequent output to be directed to the file -named in the statement, until overridden by a different OUT-statement -or until the file is closed by a SHUT-statement. File T is the -terminal, and any other name designates a file on secondary storage. -Such names must comply with the local file-naming conventions as well -as with the REDUCE syntax. If the output is not of lasting -importance, I find that including something like "TEMPORARY" or -"SCRATCH" in the name helps remind me to delete it later. - -Successive OUT-statements to the same file will append rather than -overwrite output if and only if there is no intervening SHUT- -statement for that file. The SHUT-statement also has the effect of -an implied OUT T. - -Note: - 1. The generated output is the simplified expression rather than - the raw form entered at the terminal. - 2. Each output assignment automatically has a dollar-sign - appended so that it is legal input and so that (perhaps - lengthy) output will not unavoidably be generated at the - terminal when the file is read in later. - 3. Output cannot be sent simultaneously to 2 or more files. - 4. Statements entered at the terminal which do not generate - output -- such as declarations, LET rules, and procedure - definitions -- do not appear in the secondary storage file. - 5. One could get declarations, procedure definitions, rules, etc. - written on secondary storage from the terminal by typing - statements such as - - WRITE " - ALGEBRAIC PROCEDURE ... - ... " . - - This could serve as a means of generating permanent copies - of LET rules, procedures, etc., but it is quite awkward - compared with the usual way, which is to generate a file - containing the REDUCE program by using a text editor, then - load the program by using the IN-statement. If you have - refrained from learning a local text editor and the operating- - system file-management commands, hesitate no longer. A half - dozen of the most basic commands will enable you to produce - (and modify!) programs more conveniently than any other method. - To keep from confusing the editor from REDUCE, I suggest that - your first text-editing exercise be to create an IN file for - (re)defining the function FACTORIAL(n). - - 5. The reason I didn't actually execute the above sequence of - statements is that when the input to REDUCE comes from a batch - file, both the input and output are sent to the output file, - (which is convenient for producing a file containing both the - input and output of a demonstration.) Consequently, you would - have seen none of the statements between the "OUT TEMP" and - "OUT T" as well as between the second "OUT TEMP" and the - "SHUT TEMP", until the IN statement was executed. The example - is confusing enough without having things scrambled from the - order you would type them. To clarify all of this, I encourage - you to actually execute the above sequence, with an - appropriately chosen file name and using semicolons rather - than commas. Afterwards, to return to the lesson, type CONT; - -PAUSE; - -COMMENT Suppose you and your colleagues developed or obtained a set -of REDUCE files containing supplementary packages such as trigono- -metric simplification, Laplace transforms, etc. It would be a waste -of time (and perhaps paper) to have these files printed at the -terminal every time they were loaded, so this printing can be -suppressed by inserting the statement "OFF ECHO" at the beginning of -the file, together with the statement "ON ECHO" at the end of the -file. - -The lessons have amply demonstrated the PAUSE-statement, which is -useful for insertion in batch files at the top-level or within -functions when input from the user is necessary or desired. - -It often happens that after generating an expression, one decides -that it would be convenient to use it as the body of a function -definition, with one or more of the indeterminates therein as -parameters. This can be done as follows (say yes to the define -operator prompt); - -(1-(V/C)**2)**(1/2); -FOR ALL V SAVEAS F(V); -F(5); - -COMMENT Here the indeterminate V became a parameter of F. -Alternatively, we can save the previous expression as an indeterminate; - -SAVEAS FOF5; -FOF5; - -COMMENT I find this technique more convenient than referring to the -special variable WS; - -PAUSE; - -COMMENT The FOR-loop provides a convenient way to form finite sums or -products with specific integer index limits. However, this need is -so ubiquitous that REDUCE provides even more convenient syntax of -the forms - - FOR index := initial STEP increment UNTIL final SUM expression, - - FOR index := initial STEP increment UNTIL final PRODUCT expression. - -As before, ":" is an acceptable abbreviation for "STEP 1 UNTIL". As -an example of their use, here is a very concise definition of a -function which computes Taylor-series expansions of symbolic -expressions:; - -ALGEBRAIC PROCEDURE TAYLOR(EX, X, PT, N); - COMMENT This function returns the degree N Taylor-series - expansion of expression EX with respect to indeterminate X, - expanded about expression PT. For a series-like appearance, - display the answer under the influence of FACTOR X, ON RAT, - and perhaps also ON DIV; - SUB(X=PT, EX) + FOR K:=1:N SUM(SUB(X=PT, DF(EX,X,K))*(X-PT)**K - / FOR J:=1:K PRODUCT J); -CLEAR A, X; FACTOR X; ON RAT, DIV; -G1 := TAYLOR(E**X, X, 0, 4); -G2 := TAYLOR(E**COS(X)*COS(SIN(X)), X, 0, 3); -%This illustrates the Zero denominator limitation, continue anyway; -TAYLOR(LOG(X), X, 0, 4); - -COMMENT It would, of course, be more efficient to compute each -derivative and factorial from the preceding one. (Similarly for -(X-PT)**K if and only if PT NEQ 0). - -The Fourier series expansion of our example E**COS(X)*COS(SIN(X)) -is 1 + cos(x) + cos(2*x)/2 + cos(3*x)/(3*2) + ... . -Use the above SUM and PRODUCT features to generate the partial sum of -this series through terms of order COS(6*X); - -PAUSE; - -COMMENT Closed-form solutions are often unobtainable for nontrivial -problems, even using computer algebra. When this is the case, -truncated symbolic series solutions are often worth trying before -resorting to approximate numerical solutions. - -When we combine truncated series it is pointless (and worse yet, -misleading) to retain terms of higher order than is justified by the -constituents. For example, if we wish to multiply together the -truncated series G1 and G2 generated above, there is no point in -retaining terms higher than third degree in X. We can avoid even -generating such terms as follows; - -LET X**4 = 0; -G3 := G1*G2; - -COMMENT Replacing X**4 with 0 has the effect of also replacing all -higher powers of X with 0. We could, of course, use our TAYLOR -function to compute G3 directly, but differentiation is time -consuming compared to truncated polynomial algebra. Moreover, our -TAYLOR function requires a closed-form expression to begin with, -whereas iterative techniques often permit us to construct symbolic -series solutions even when we have no such closed form. - -Now consider the truncated series; - -CLEAR Y; FACTOR Y; -H1 := TAYLOR(COS Y, Y, 0, 6); - -COMMENT Suppose we regard terms of order X**N in G1 as being -comparable to terms of order Y**(2*N) in H1, and we want to form -(G1*H1)**2. This can be done as follows; - -LET Y**7 = 0; -F1 := (G1*H1)**2; - -COMMENT Note however that any terms of the form C*X**M*Y**N with -2*M+N > 6 are inconsistent with the accuracy of the constituent -series, and we have generated several such misleading terms by -independently truncating powers of X and Y. To avoid generating -such junk, we can specify that a term be replaced by 0 whenever a -weighted sum of exponents of specified indeterminates and functional -forms exceeds a specified weight level. In our example this is done -as follows; - -WEIGHT X=2, Y=1; -WTLEVEL 6; -F1 := F1; - -COMMENT variables not mentioned in a WEIGHT declaration have a -weight of 0, and the default weight-level is 2; - -PAUSE; - -COMMENT In lesson 2 I promised to show you ways to overcome the lack -in most REDUCE implementations of automatic numerical techniques -for approximating fractional powers and transcendental functions of -numerical values. One way is to provide a supplementary LET rule -for numerical arguments. For example, since our TAYLOR function -would reveal that the Taylor series for cos x is -1 - x**2/2! + x**4/4! - ...; - -FOR ALL X SUCH THAT NUMBERP X LET ABS(X)=X,ABS(-X)=X; -EPSRECIP := 1024 $ -ON ROUNDED; -WHILE 1.0 + 1.0/EPSRECIP NEQ 1.0 DO - EPSRECIP := EPSRECIP + EPSRECIP; -FOR ALL X SUCH THAT NUMBERP NUM X AND NUMBERP DEN X LET COS X = - BEGIN COMMENT X is integer, real, or a rational number. This rule - returns the Taylor-series approximation to COS X, truncated when - the last included term is less than (1/EPSRECIP) of the returned - answer. EPSRECIP is a global variable initialized to a value - that is appropriate to the local floating-point precision. - Arbitrarily larger values are justifiable when X is exact and - ROUNDED is off. No angle reduction is performed, so this - function is not recommended for ABS(X) >= about PI/2; - INTEGER K; SCALAR MXSQ, TERM, ANS; - K := 1; - MXSQ := -X*X; - TERM := MXSQ/2; - ANS := TERM + 1; - WHILE ABS(NUM TERM)*EPSRECIP*DEN(ANS)-ABS(NUM ANS)*DEN(TERM)>0 DO - << TERM:= TERM*MXSQ/K/(K+1); - ANS:= TERM + ANS; - K := K+2 >>; - RETURN ANS - END; -COS(F) + COS(1/2); -OFF ROUNDED; -COS(1/2); - -COMMENT As an exercise, write a similar rule for the SIN or LOG, or -replace the COS rule with an improved one which uses angle reduction -so that angles outside a modest range are represented as equivalent -angles within the range, before computing the Taylor series; - -PAUSE; - -COMMENT There is a REDUCE compiler, and you may wish to learn the -local incantations for using it. However, even if rules such as -the above ones are compiled, they will be slow compared to the -implementation-dependent hand-coded ones used by most FORTRAN-like -systems, so REDUCE provides a way to generate FORTRAN programs which -can then be compiled and executed in a subsequent job step. This is -useful when there is a lot of floating-point computation or when we -wish to exploit an existing FORTRAN program. Suppose, for example, -that we wish to utilize an existing FORTRAN subroutine which uses the -Newton-Rapheson iteration - - Xnew := Xold - SUB(X=Xold, F(X)/DF(F(X),X)) - -to attempt an approximate solution to the equation F(X)=0. Most such -subroutines require the user to provide a FORTRAN function or -subroutine which, given Xold, returns F(X)/DF(F(X),X) evaluated at -X=Xold. If F(X) is complicated, manual symbolic derivation of -DF(F(X),X) is a tedious and error-prone process. We can get -REDUCE to relieve us of this responsibility as is illustrated below -for the trivial example F(X) = X*E**X - 1: - - ON FORT, ROUNDED, - OUT FONDFFILE, - WRITE " REAL FUNCTION FONDF(XOLD)", - WRITE " REAL XOLD, F", - F := XOLD*E**XOLD - 1.0, - FONDF := F/DF(F,XOLD), - WRITE " RETURN", - WRITE " END", - SHUT FONDFFILE . - -COMMENT Under the influence of ON FORT, the output generated by -assignments is printed as valid FORTRAN assignment statements, using -as many continuation lines as necessary up to the amount specified -by the global variable !*CARDNO, which is initially set to 20. The -output generated by an expression which is not an assignment is a -corresponding assignment to a variable named ANS. In either case, -expressions which would otherwise exceed !*CARDNO continuation -lines are evaluated piecewise, using ANS as an intermediate variable. - -Try executing the above sequence, using an appropriate filename and -using semicolons rather than commas at the end of the lines, then -print the file after the lesson to see how it worked; - -PAUSE; -OFF FORT, ROUNDED; - -COMMENT To make this technique usable by non-REDUCE programmers, we -could write a more general REDUCE program which given merely the -expression F by the user, outputs not only the function FONDF, but -also any necessary Job-control commands and an appropriate main -program for calling the Newton-Rapheson subroutine and printing the -results. - -Sometimes it is desirable to modify or supplement the syntax -of REDUCE. For example: - 1. Electrical engineers may prefer to input J as the representation - of (-1)**(1/2). - 2. Many users may prefer to input LN to denote natural logarithms. - 3. A user with previous exposure to the PL/I-FORMAC computer- - algebra system might prefer to use DERIV instead of DF to - request differentiation. - -Such lexical macros can be established by the DEFINE declaration:; - -CLEAR X,J; -DEFINE J=I, LN=LOG, DERIV=DF; - -COMMENT Now watch!; - -N := 3; -G1 := SUB(X=LN(J**3*X), DERIV(X**2,X)); - -COMMENT Each "equation" in a DEFINE declaration must be of the form -"name = item", where each item is an expression, an operator, or a -REDUCE-reserved word such as "FOR". Such replacements take place -during the lexical scanning, before any evaluation, LET rules, or -built-in simplification. Think of a good application for this -facility, then try it; - -PAUSE; - -COMMENT When REDUCE is being run in batch mode, it is preferable to -have REDUCE make reasonable decisions and proceed when it encounters -apparently undeclared operators, divisions by zero, etc. In -interactive mode, it is preferable to pause and query the user. ON -INT specifies the latter style, and OFF INT specifies the -former. Under the influence of OFF INT, we can also have most -error messages suppressed by specifying OFF MSG. This is sometimes -useful when we expect abnormal conditions and do not want our listing -marred by the associated messages. INT is automatically turned off -during input from a batch file in response to an IN-command from a -terminal. - -Some implementations permit the user to dynamically request more -storage by executing a command of the form - - CORE number, - -where the number is an integer specifying the total desired core in -some units such as bytes, words, kilobytes, or kilowords; - -PAUSE; - -COMMENT Some implementations have a trace command for debugging, -which employs the syntax - - TR functionname1, functionname2, ..., functionnameN . - -An analogous command named UNTR removes function names from trace -status; - -PAUSE; - -COMMENT Some implementations have an assignment-tracing command for -debugging, which employs the syntax - - TRST functionname1, functionname2, ..., functionnameN. - -An analogous command named UNTRST removes functionnames from -this status. All assignments in the designated functions are -reported, except for assignments to array elements. Such functions -must be uncompiled and must have a top-level BEGIN-block. To apply -both TRST and TR to a function simultaneously, it is crucial to -request them in that order, and it is necessary to relinquish the two -kinds of tracing in the opposite order; - -PAUSE; - -COMMENT The REDUCE algebraic algorithms are written in a subset of -REDUCE called RLISP. In turn, the more sophisticated features of -RLISP are written in a small subset of RLISP which is written in a -subset of LISP that is relatively common to most LISP systems. - -RLISP is ideal for implementing algebraic algorithms, but the RLISP -environment is not most suitable for the routine use of these -algorithms in the natural mathematical style of the preceding -lessons. Accordingly, REDUCE jobs are initially in a mode called -ALGEBRAIC, which provides the user with the environment illustrated -in the preceding lessons, while insulating him from accidental -interaction with the numerous functions, global variables, etc. -necessary for implementing the built-in algebra. In contrast, the -underlying RLISP system together with all of the algebraic -simplification algorithms written therein is called SYMBOLIC mode. - -As we have seen, algebraic-mode rules and procedures can be used to -extend the built-in algebraic capabilities. However, some extensions -can be accomplished most easily or efficiently by descending to -SYMBOLIC mode. - -To make REDUCE operate in symbolic mode, we merely execute the top -level mode-declaration statement consisting of the word SYMBOLIC. We -can subsequently switch back by executing the statement consisting of -the word ALGEBRAIC. - -RLISP has the semantics of LISP with the syntax of our by-now-familiar -algebraic-mode REDUCE, so RLISP provides a natural tool for many -applications besides computer algebra, such as games, theorem-proving, -natural-language translation, computer-aided instruction, and -artificial intelligence in general. For this reason, it is possible -to run RLISP without any of the symbolic-mode algebraic algorithms -that are written in RLISP, and it is advisable to thus save space -when the application does not involve computer algebra. - -We have now discussed virtually every feature that is available in -algebraic mode, so lesson 6 will deal solely with RLISP, and -lesson 7 will deal with communication between ALGEBRAIC and -SYMBOLIC mode for mathematical purposes. However, I suggest that -you proceed to those lessons only if and when: - 1. You have consolidated and fully absorbed the information in - lessons 1 through 5 by considerable practice beyond the - exercises therein. (The exercises were intended to also - suggest good related project ideas.) - 2. You feel the need for a facility which you believe is impossible - or quite awkward to implement solely in ALGEBRAIC mode. - 3. You have read the pamphlet "Introduction to LISP", by D. Lurie, - or an equivalent. - 4. You are familiar with definition of Standard LISP, as described - in the "Standard LISP Report" which was published in the October - 1979 SIGPLAN Notices. - -Remember, when you decide to take lesson 6, it is better to do so from -a RLISP job than from a REDUCE job. Also, don't forget to print your -newly generated FORTRAN file and to delete any temporary files created -by this lesson. - -;END; +COMMENT + + REDUCE INTERACTIVE LESSON NUMBER 5 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 5 of 7 REDUCE lessons. + +There are at least two good reasons for wanting to save REDUCE +expression assignments on secondary storage: + 1. So that one can logout, then resume computation at a later + time. + 2. So that needed storage space can be cleared without + irrecoverably losing the values of variables which are not + needed in the next expression but will be needed later. + +Using trivial small expressions, the following sequence illustrates +how this could be done: + + OFF NAT, + OUT TEMP, + F1 := (F + G)**2, + G1 := G*F1, + OUT T, + CLEAR F1, + H1 := H*G1, + OUT TEMP, + CLEAR G1, + H2 := F*H1, + CLEAR H1, + SHUT TEMP, + IN TEMP, + F1, + ON NAT, + F1 . + +ON NAT yields the natural output style with raised exponents, which +is unsuitable for subsequent input. + +The OUT-statement causes subsequent output to be directed to the file +named in the statement, until overridden by a different OUT-statement +or until the file is closed by a SHUT-statement. File T is the +terminal, and any other name designates a file on secondary storage. +Such names must comply with the local file-naming conventions as well +as with the REDUCE syntax. If the output is not of lasting +importance, I find that including something like "TEMPORARY" or +"SCRATCH" in the name helps remind me to delete it later. + +Successive OUT-statements to the same file will append rather than +overwrite output if and only if there is no intervening SHUT- +statement for that file. The SHUT-statement also has the effect of +an implied OUT T. + +Note: + 1. The generated output is the simplified expression rather than + the raw form entered at the terminal. + 2. Each output assignment automatically has a dollar-sign + appended so that it is legal input and so that (perhaps + lengthy) output will not unavoidably be generated at the + terminal when the file is read in later. + 3. Output cannot be sent simultaneously to 2 or more files. + 4. Statements entered at the terminal which do not generate + output -- such as declarations, LET rules, and procedure + definitions -- do not appear in the secondary storage file. + 5. One could get declarations, procedure definitions, rules, etc. + written on secondary storage from the terminal by typing + statements such as + + WRITE " + ALGEBRAIC PROCEDURE ... + ... " . + + This could serve as a means of generating permanent copies + of LET rules, procedures, etc., but it is quite awkward + compared with the usual way, which is to generate a file + containing the REDUCE program by using a text editor, then + load the program by using the IN-statement. If you have + refrained from learning a local text editor and the operating- + system file-management commands, hesitate no longer. A half + dozen of the most basic commands will enable you to produce + (and modify!) programs more conveniently than any other method. + To keep from confusing the editor from REDUCE, I suggest that + your first text-editing exercise be to create an IN file for + (re)defining the function FACTORIAL(n). + + 5. The reason I didn't actually execute the above sequence of + statements is that when the input to REDUCE comes from a batch + file, both the input and output are sent to the output file, + (which is convenient for producing a file containing both the + input and output of a demonstration.) Consequently, you would + have seen none of the statements between the "OUT TEMP" and + "OUT T" as well as between the second "OUT TEMP" and the + "SHUT TEMP", until the IN statement was executed. The example + is confusing enough without having things scrambled from the + order you would type them. To clarify all of this, I encourage + you to actually execute the above sequence, with an + appropriately chosen file name and using semicolons rather + than commas. Afterwards, to return to the lesson, type CONT; + +PAUSE; + +COMMENT Suppose you and your colleagues developed or obtained a set +of REDUCE files containing supplementary packages such as trigono- +metric simplification, Laplace transforms, etc. It would be a waste +of time (and perhaps paper) to have these files printed at the +terminal every time they were loaded, so this printing can be +suppressed by inserting the statement "OFF ECHO" at the beginning of +the file, together with the statement "ON ECHO" at the end of the +file. + +The lessons have amply demonstrated the PAUSE-statement, which is +useful for insertion in batch files at the top-level or within +functions when input from the user is necessary or desired. + +It often happens that after generating an expression, one decides +that it would be convenient to use it as the body of a function +definition, with one or more of the indeterminates therein as +parameters. This can be done as follows (say yes to the define +operator prompt); + +(1-(V/C)**2)**(1/2); +FOR ALL V SAVEAS F(V); +F(5); + +COMMENT Here the indeterminate V became a parameter of F. +Alternatively, we can save the previous expression as an indeterminate; + +SAVEAS FOF5; +FOF5; + +COMMENT I find this technique more convenient than referring to the +special variable WS; + +PAUSE; + +COMMENT The FOR-loop provides a convenient way to form finite sums or +products with specific integer index limits. However, this need is +so ubiquitous that REDUCE provides even more convenient syntax of +the forms + + FOR index := initial STEP increment UNTIL final SUM expression, + + FOR index := initial STEP increment UNTIL final PRODUCT expression. + +As before, ":" is an acceptable abbreviation for "STEP 1 UNTIL". As +an example of their use, here is a very concise definition of a +function which computes Taylor-series expansions of symbolic +expressions:; + +ALGEBRAIC PROCEDURE TAYLOR(EX, X, PT, N); + COMMENT This function returns the degree N Taylor-series + expansion of expression EX with respect to indeterminate X, + expanded about expression PT. For a series-like appearance, + display the answer under the influence of FACTOR X, ON RAT, + and perhaps also ON DIV; + SUB(X=PT, EX) + FOR K:=1:N SUM(SUB(X=PT, DF(EX,X,K))*(X-PT)**K + / FOR J:=1:K PRODUCT J); +CLEAR A, X; FACTOR X; ON RAT, DIV; +G1 := TAYLOR(E**X, X, 0, 4); +G2 := TAYLOR(E**COS(X)*COS(SIN(X)), X, 0, 3); +%This illustrates the Zero denominator limitation, continue anyway; +TAYLOR(LOG(X), X, 0, 4); + +COMMENT It would, of course, be more efficient to compute each +derivative and factorial from the preceding one. (Similarly for +(X-PT)**K if and only if PT NEQ 0). + +The Fourier series expansion of our example E**COS(X)*COS(SIN(X)) +is 1 + cos(x) + cos(2*x)/2 + cos(3*x)/(3*2) + ... . +Use the above SUM and PRODUCT features to generate the partial sum of +this series through terms of order COS(6*X); + +PAUSE; + +COMMENT Closed-form solutions are often unobtainable for nontrivial +problems, even using computer algebra. When this is the case, +truncated symbolic series solutions are often worth trying before +resorting to approximate numerical solutions. + +When we combine truncated series it is pointless (and worse yet, +misleading) to retain terms of higher order than is justified by the +constituents. For example, if we wish to multiply together the +truncated series G1 and G2 generated above, there is no point in +retaining terms higher than third degree in X. We can avoid even +generating such terms as follows; + +LET X**4 = 0; +G3 := G1*G2; + +COMMENT Replacing X**4 with 0 has the effect of also replacing all +higher powers of X with 0. We could, of course, use our TAYLOR +function to compute G3 directly, but differentiation is time +consuming compared to truncated polynomial algebra. Moreover, our +TAYLOR function requires a closed-form expression to begin with, +whereas iterative techniques often permit us to construct symbolic +series solutions even when we have no such closed form. + +Now consider the truncated series; + +CLEAR Y; FACTOR Y; +H1 := TAYLOR(COS Y, Y, 0, 6); + +COMMENT Suppose we regard terms of order X**N in G1 as being +comparable to terms of order Y**(2*N) in H1, and we want to form +(G1*H1)**2. This can be done as follows; + +LET Y**7 = 0; +F1 := (G1*H1)**2; + +COMMENT Note however that any terms of the form C*X**M*Y**N with +2*M+N > 6 are inconsistent with the accuracy of the constituent +series, and we have generated several such misleading terms by +independently truncating powers of X and Y. To avoid generating +such junk, we can specify that a term be replaced by 0 whenever a +weighted sum of exponents of specified indeterminates and functional +forms exceeds a specified weight level. In our example this is done +as follows; + +WEIGHT X=2, Y=1; +WTLEVEL 6; +F1 := F1; + +COMMENT variables not mentioned in a WEIGHT declaration have a +weight of 0, and the default weight-level is 2; + +PAUSE; + +COMMENT In lesson 2 I promised to show you ways to overcome the lack +in most REDUCE implementations of automatic numerical techniques +for approximating fractional powers and transcendental functions of +numerical values. One way is to provide a supplementary LET rule +for numerical arguments. For example, since our TAYLOR function +would reveal that the Taylor series for cos x is +1 - x**2/2! + x**4/4! - ...; + +FOR ALL X SUCH THAT NUMBERP X LET ABS(X)=X,ABS(-X)=X; +EPSRECIP := 1024 $ +ON ROUNDED; +WHILE 1.0 + 1.0/EPSRECIP NEQ 1.0 DO + EPSRECIP := EPSRECIP + EPSRECIP; +FOR ALL X SUCH THAT NUMBERP NUM X AND NUMBERP DEN X LET COS X = + BEGIN COMMENT X is integer, real, or a rational number. This rule + returns the Taylor-series approximation to COS X, truncated when + the last included term is less than (1/EPSRECIP) of the returned + answer. EPSRECIP is a global variable initialized to a value + that is appropriate to the local floating-point precision. + Arbitrarily larger values are justifiable when X is exact and + ROUNDED is off. No angle reduction is performed, so this + function is not recommended for ABS(X) >= about PI/2; + INTEGER K; SCALAR MXSQ, TERM, ANS; + K := 1; + MXSQ := -X*X; + TERM := MXSQ/2; + ANS := TERM + 1; + WHILE ABS(NUM TERM)*EPSRECIP*DEN(ANS)-ABS(NUM ANS)*DEN(TERM)>0 DO + << TERM:= TERM*MXSQ/K/(K+1); + ANS:= TERM + ANS; + K := K+2 >>; + RETURN ANS + END; +COS(F) + COS(1/2); +OFF ROUNDED; +COS(1/2); + +COMMENT As an exercise, write a similar rule for the SIN or LOG, or +replace the COS rule with an improved one which uses angle reduction +so that angles outside a modest range are represented as equivalent +angles within the range, before computing the Taylor series; + +PAUSE; + +COMMENT There is a REDUCE compiler, and you may wish to learn the +local incantations for using it. However, even if rules such as +the above ones are compiled, they will be slow compared to the +implementation-dependent hand-coded ones used by most FORTRAN-like +systems, so REDUCE provides a way to generate FORTRAN programs which +can then be compiled and executed in a subsequent job step. This is +useful when there is a lot of floating-point computation or when we +wish to exploit an existing FORTRAN program. Suppose, for example, +that we wish to utilize an existing FORTRAN subroutine which uses the +Newton-Rapheson iteration + + Xnew := Xold - SUB(X=Xold, F(X)/DF(F(X),X)) + +to attempt an approximate solution to the equation F(X)=0. Most such +subroutines require the user to provide a FORTRAN function or +subroutine which, given Xold, returns F(X)/DF(F(X),X) evaluated at +X=Xold. If F(X) is complicated, manual symbolic derivation of +DF(F(X),X) is a tedious and error-prone process. We can get +REDUCE to relieve us of this responsibility as is illustrated below +for the trivial example F(X) = X*E**X - 1: + + ON FORT, ROUNDED, + OUT FONDFFILE, + WRITE " REAL FUNCTION FONDF(XOLD)", + WRITE " REAL XOLD, F", + F := XOLD*E**XOLD - 1.0, + FONDF := F/DF(F,XOLD), + WRITE " RETURN", + WRITE " END", + SHUT FONDFFILE . + +COMMENT Under the influence of ON FORT, the output generated by +assignments is printed as valid FORTRAN assignment statements, using +as many continuation lines as necessary up to the amount specified +by the global variable !*CARDNO, which is initially set to 20. The +output generated by an expression which is not an assignment is a +corresponding assignment to a variable named ANS. In either case, +expressions which would otherwise exceed !*CARDNO continuation +lines are evaluated piecewise, using ANS as an intermediate variable. + +Try executing the above sequence, using an appropriate filename and +using semicolons rather than commas at the end of the lines, then +print the file after the lesson to see how it worked; + +PAUSE; +OFF FORT, ROUNDED; + +COMMENT To make this technique usable by non-REDUCE programmers, we +could write a more general REDUCE program which given merely the +expression F by the user, outputs not only the function FONDF, but +also any necessary Job-control commands and an appropriate main +program for calling the Newton-Rapheson subroutine and printing the +results. + +Sometimes it is desirable to modify or supplement the syntax +of REDUCE. For example: + 1. Electrical engineers may prefer to input J as the representation + of (-1)**(1/2). + 2. Many users may prefer to input LN to denote natural logarithms. + 3. A user with previous exposure to the PL/I-FORMAC computer- + algebra system might prefer to use DERIV instead of DF to + request differentiation. + +Such lexical macros can be established by the DEFINE declaration:; + +CLEAR X,J; +DEFINE J=I, LN=LOG, DERIV=DF; + +COMMENT Now watch!; + +N := 3; +G1 := SUB(X=LN(J**3*X), DERIV(X**2,X)); + +COMMENT Each "equation" in a DEFINE declaration must be of the form +"name = item", where each item is an expression, an operator, or a +REDUCE-reserved word such as "FOR". Such replacements take place +during the lexical scanning, before any evaluation, LET rules, or +built-in simplification. Think of a good application for this +facility, then try it; + +PAUSE; + +COMMENT When REDUCE is being run in batch mode, it is preferable to +have REDUCE make reasonable decisions and proceed when it encounters +apparently undeclared operators, divisions by zero, etc. In +interactive mode, it is preferable to pause and query the user. ON +INT specifies the latter style, and OFF INT specifies the +former. Under the influence of OFF INT, we can also have most +error messages suppressed by specifying OFF MSG. This is sometimes +useful when we expect abnormal conditions and do not want our listing +marred by the associated messages. INT is automatically turned off +during input from a batch file in response to an IN-command from a +terminal. + +Some implementations permit the user to dynamically request more +storage by executing a command of the form + + CORE number, + +where the number is an integer specifying the total desired core in +some units such as bytes, words, kilobytes, or kilowords; + +PAUSE; + +COMMENT Some implementations have a trace command for debugging, +which employs the syntax + + TR functionname1, functionname2, ..., functionnameN . + +An analogous command named UNTR removes function names from trace +status; + +PAUSE; + +COMMENT Some implementations have an assignment-tracing command for +debugging, which employs the syntax + + TRST functionname1, functionname2, ..., functionnameN. + +An analogous command named UNTRST removes functionnames from +this status. All assignments in the designated functions are +reported, except for assignments to array elements. Such functions +must be uncompiled and must have a top-level BEGIN-block. To apply +both TRST and TR to a function simultaneously, it is crucial to +request them in that order, and it is necessary to relinquish the two +kinds of tracing in the opposite order; + +PAUSE; + +COMMENT The REDUCE algebraic algorithms are written in a subset of +REDUCE called RLISP. In turn, the more sophisticated features of +RLISP are written in a small subset of RLISP which is written in a +subset of LISP that is relatively common to most LISP systems. + +RLISP is ideal for implementing algebraic algorithms, but the RLISP +environment is not most suitable for the routine use of these +algorithms in the natural mathematical style of the preceding +lessons. Accordingly, REDUCE jobs are initially in a mode called +ALGEBRAIC, which provides the user with the environment illustrated +in the preceding lessons, while insulating him from accidental +interaction with the numerous functions, global variables, etc. +necessary for implementing the built-in algebra. In contrast, the +underlying RLISP system together with all of the algebraic +simplification algorithms written therein is called SYMBOLIC mode. + +As we have seen, algebraic-mode rules and procedures can be used to +extend the built-in algebraic capabilities. However, some extensions +can be accomplished most easily or efficiently by descending to +SYMBOLIC mode. + +To make REDUCE operate in symbolic mode, we merely execute the top +level mode-declaration statement consisting of the word SYMBOLIC. We +can subsequently switch back by executing the statement consisting of +the word ALGEBRAIC. + +RLISP has the semantics of LISP with the syntax of our by-now-familiar +algebraic-mode REDUCE, so RLISP provides a natural tool for many +applications besides computer algebra, such as games, theorem-proving, +natural-language translation, computer-aided instruction, and +artificial intelligence in general. For this reason, it is possible +to run RLISP without any of the symbolic-mode algebraic algorithms +that are written in RLISP, and it is advisable to thus save space +when the application does not involve computer algebra. + +We have now discussed virtually every feature that is available in +algebraic mode, so lesson 6 will deal solely with RLISP, and +lesson 7 will deal with communication between ALGEBRAIC and +SYMBOLIC mode for mathematical purposes. However, I suggest that +you proceed to those lessons only if and when: + 1. You have consolidated and fully absorbed the information in + lessons 1 through 5 by considerable practice beyond the + exercises therein. (The exercises were intended to also + suggest good related project ideas.) + 2. You feel the need for a facility which you believe is impossible + or quite awkward to implement solely in ALGEBRAIC mode. + 3. You have read the pamphlet "Introduction to LISP", by D. Lurie, + or an equivalent. + 4. You are familiar with definition of Standard LISP, as described + in the "Standard LISP Report" which was published in the October + 1979 SIGPLAN Notices. + +Remember, when you decide to take lesson 6, it is better to do so from +a RLISP job than from a REDUCE job. Also, don't forget to print your +newly generated FORTRAN file and to delete any temporary files created +by this lesson. + +;END; Index: r36/LESS6 ================================================================== --- r36/LESS6 +++ r36/LESS6 @@ -1,419 +1,419 @@ -COMMENT - - REDUCE INTERACTIVE LESSON NUMBER 6 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 6 of 7 REDUCE lessons. A prerequisite is to -read the pamphlet "An Introduction to LISP", by D. Lurie'. - -To avoid confusion between RLISP and the SYMBOLIC-mode algebraic -algorithms, this lesson will treat only RLISP. Lesson 7 deals with how -the REDUCE algebraic mode is implemented in RLISP and how the user can -interact directly with that implementation. That is why I suggested -that you run this lesson in RLISP rather than full REDUCE. If you -forgot or do not have a locally available separate RLISP, then please -switch now to symbolic mode by typing the statement SYMBOLIC; - -SYMBOLIC; -PAUSE; - -COMMENT Your most frequent mistakes are likely to be forgetting to quote -data examples, using commas as separators within lists, and not puttng -enough levels of parentheses in your data examples. - -Now that you have learned from your reading about the built-in RLISP -functions CAR, CDR, CONS, ATOM, EQ, NULL, LIST, APPEND, REVERSE, DELETE, -MAPLIST, MAPCON, LAMBDA, FLAG, FLAGP, PUT, GET, DEFLIST, NUMBERP, ZEROP, -ONEP, AND, EVAL, PLUS, TIMES, CAAR, CADR, etc., here is an opportunity -to reinforce the learning by practice.: Write expressions using CAR, -CDR, CDDR, etc., (which are defined only through 4 letters between C and -R), to individually extract each atom from F, where; - -F := '((JOHN . DOE) (1147 HOTEL STREET) HONOLULU); -PAUSE; - -COMMENT My solutions are CAAR F, CDAR F, CAADR F, CADADR F, -CADDR CADR F, and CADDR F. - -Although commonly the "." is only mentioned in conjunction with data, we -can also use it as an infix alias for CONS. Do this to build from F and -from the data 'MISTER the s-expression consisting of F with MISTER -inserted before JOHN.DOE; - -PAUSE; - -COMMENT My solution is ('MISTER . CAR F) . CDR F . - -Enough of these inane exercises -- let's get on to something useful! -Let's develop a collection of functions for operating on finite sets. -We will let the elements be arbitrary s-expressions, and we will -represent a set as a list of its elements in arbitrary order, without -duplicates. - -Here is a function which determines whether its first argument is a -member of the set which is its second element; - -SYMBOLIC PROCEDURE MEMBERP(ELEM, SET1); - COMMENT Returns T if s-expression ELEM is a top-level element - of list SET1, returning NIL otherwise; - IF NULL SET1 THEN NIL - ELSE IF ELEM = CAR SET1 THEN T - ELSE MEMBERP(ELEM, CDR SET1); -MEMBERP('BLUE, '(RED BLUE GREEN)); - -COMMENT This function illustrates several convenient techniques for -writing functions which process lists: - - 1. To avoid the errors of taking the CAR or the CDR of an atom, and - to build self confidence while it is not immediately apparent how to - completely solve the problem, treat the trivial cases first. For an - s-expression or list argument, the most trivial cases are generally - when one or more of the arguments are NIL, and a slightly less - trivial case is when one or more is an atom. (Note that we will get - an error message if we use MEMBERP with a second argument which is - not a list. We could check for this, but in the interest of brevity, - I will not strive to make our set-package give set-oriented error - messages.) - - 2. Use CAR to extract the first element and use CDR to refer to the - remainder of the list. - - 3. Use recursion to treat more complicated cases by extracting the - first element and using the same functions on smaller arguments.; - -PAUSE; -COMMENT To make MEMBERP into an infix operator we make the declaration; - -INFIX MEMBERP; -'(JOHN.DOE) MEMBERP '((FIG.NEWTON) FONZO (SANTA CLAUS)); - -COMMENT Infix operators associate left, meaning expressions of the form - - (operator1 operator operand2 operator ... operandN) - -are interpreted as - - ((...(operand1 operator operand2) operator ... operandN). - -Operators may also be flagged RIGHT by - - FLAG ('(op1 op2 ...), 'RIGHT) . - -to give the interpretation - - (operand1 operator (operand2 operator (... operandN))...). - -Of the built-in operators, only ".", "*=", "+", and "*" associate right. - -If we had made the infix declaration before the function definition, the -latter could have begun with the more natural statement - - SYMBOLIC PROCEDURE ELEM MEMBERP SET . - -Infix functions can also be referred to by functional notation if one -desires. Actually, an analogous infix operator named MEMBER is already -built-into RLISP, so we will use MEMBER rather than MEMBERP from here -on; - -MEMBER(1147, CADR F); - -COMMENT Inspired by the simple yet elegant definition of MEMBERP, write -a function named SETP which uses MEMBER to check for a duplicate element -in its list argument, thus determining whether or not the argument of -SETP is a set; - -PAUSE; - -COMMENT My solution is; - -SYMBOLIC PROCEDURE SETP CANDIDATE; - COMMENT Returns T if list CANDIDATE is a set, returning NIL - otherwise; - IF NULL CANDIDATE THEN T - ELSE IF CAR CANDIDATE MEMBER CDR CANDIDATE THEN NIL - ELSE SETP CDR CANDIDATE; -SETP '(KERMIT, (COOKIE MONSTER)); -SETP '(DOG CAT DOG); - -COMMENT If you used a BEGIN-block, local variables, loops, etc., then -your solution is surely more awkward than mine. For the duration of the -lesson, try to do everything without groups, BEGIN-blocks, local -variables, assignments, and loops. Everything can be done using -function composition, conditional expressions, and recursion. It will -be a mind-expanding experience -- more so than transcendental -meditation, psilopsybin, and EST. Afterward, you can revert to your old -ways if you disagree. - -Thus endeth the sermon. - -Incidentally, to make the above definition of SETP work for non-list -arguments all we have to do is insert "ELSE IF ATOM CANDIDATE THEN NIL" -below "IF NULL CANDIDATE THEN T". - -Now try to write an infix procedure named SUBSETOF, such that SET1 -SUBSETOF SET2 returns NIL if SET1 contains an element that SET2 does -not, returning T otherwise. You are always encouraged, by the way, to -use any functions that are already builtin, or that we have previously -defined, or that you define later as auxiliary functions; - -PAUSE; -COMMENT My solution is; - -INFIX SUBSETOF; -SYMBOLIC PROCEDURE SET1 SUBSETOF SET2; - IF NULL SET1 THEN T - ELSE IF CAR SET1 MEMBER SET2 THEN CDR SET1 SUBSETOF SET2 - ELSE NIL; -'(ROOF DOOR) SUBSETOF '(WINDOW DOOR FLOOR ROOF); -'(APPLE BANANA) SUBSETOF '((APPLE COBBLER) (BANANA CREME PIE)); - -COMMENT Two sets are equal when they have identical elements, not -necessarily in the same order. Write an infix procedure named -EQSETP which returns T if its two operands are equal sets, returning -NIL otherwise; - -PAUSE; - -COMMENT The following solution introduces the PRECEDENCE declaration; - -INFIX EQSETP; -PRECEDENCE EQSETP, =; -PRECEDENCE SUBSETOF, EQSETP; -SYMBOLIC PROCEDURE SET1 EQSETP SET2; - SET1 SUBSETOF SET2 AND SET2 SUBSETOF SET1; -'(BALLET TAP) EQSETP '(TAP BALLET); -'(PINE FIR ASPEN) EQSETP '(PINE FIR PALM); - -COMMENT The precedence declarations make SUBSETOF have a higher -precedence than EQSETP and make the latter have higher precedence than -"=", which is higher than "AND",. Consequently, these declarations -enabled me to omit parentheses around "SET1 SUBSUBSETOF SET2" and around -"SET2 SUBSETOF SET1". All prefix operators are higher than any infix -operator, and to inspect the ordering among the latter, we merely -inspect the value of the global variable named; - -PRECLIS!*; - -COMMENT Now see if you can write a REDUCE infix function named -PROPERSUBSETOF, which determines if its left operand is a proper subset -of its right operand, meaning it is a subset which is not equal to the -right operand; - -PAUSE; - -COMMENT All of the above exercises have been predicates. In contrast, -the next exercise is to write a function called MAKESET, which returns -a list which is a copy of its argument, omitting duplicates; - -PAUSE; - -COMMENT How about; - -SYMBOLIC PROCEDURE MAKESET LIS; - IF NULL LIS THEN NIL - ELSE IF CAR LIS MEMBER CDR LIS THEN MAKESET CDR LIS - ELSE CAR LIS . MAKESET CDR LIS; - -COMMENT As you may have guessed, the next exercise is to implement an -operator named INTERSECT, which returns the intersection of its set -operands; - -PAUSE; - -COMMENT Here is my solution; - -INFIX INTERSECT; -PRECEDENCE INTERSECT, SUBSETOF; -SYMBOLIC PROCEDURE SET1 INTERSECT SET2; - IF NULL SET1 THEN NIL - ELSE IF CAR SET1 MEMBER SET2 - THEN CAR SET1 . CDR SET1 INTERSECT SET2 - ELSE CDR SET1 INTERSECT SET2; - -COMMENT Symbolic-mode REDUCE has a built-in function named SETDIFF, -which returns the set of elements which are in its first argument but -not the second. See if you can write an infix definition of a similar -function named DIFFSET; - -PAUSE; - -COMMENT Presenting --; - -INFIX DIFFSET; -PRECEDENCE DIFFSET, INTERSECT; -SYMBOLIC PROCEDURE LEFT DIFFSET RIGHT; - IF NULL LEFT THEN NIL - ELSE IF CAR LEFT MEMBER RIGHT THEN CDR LEFT DIFFSET RIGHT - ELSE CAR LEFT . (CDR LEFT DIFFSET RIGHT); -'(SEAGULL WREN CONDOR) DIFFSET '(WREN LARK); - -COMMENT The symmetric difference of two sets is the set of all elements -which are in only one of the two sets. Implement a corresponding infix -function named SYMDIFF. Look for the easy way! There is almost always -one for examinations and instructional exercises; PAUSE; - -COMMENT Presenting --; -INFIX SYMDIFF; -PRECEDENCE SYMDIFF, INTERSECT; -SYMBOLIC PROCEDURE SET1 SYMDIFF SET2; - APPEND(SET1 DIFFSET SET2, SET2 DIFFSET SET1); -'(SEAGULL WREN CONDOR) SYMDIFF '(WREN LARK); - -COMMENT We can use APPEND because the two set differences are disjoint. - -The above set of exercises (exercises of set?) have all returned set -results. The cardinality, size, or length of a set is the number of -elements in the set. More generally, it is useful to have a function -which returns the length of its list argument, and such a function is -built-into RLISP. See if you can write a similar function named SIZEE; - -PAUSE; -COMMENT Presenting --; -SYMBOLIC PROCEDURE SIZEE LIS; - IF NULL LIS THEN 0 - ELSE 1 + SIZEE CDR LIS; -SIZEE '(HOW MARVELOUSLY CONCISE); -SIZEE '(); - -COMMENT Literal atoms, meaning atoms which are not numbers, are stored -uniquely in LISP and in RLISP, so comparison for equality of literal -atoms can be implemented by comparing their addresses, which is -significantly more efficient than a character-by-character comparison of -their names. The comparison operator "EQ" compares addresses, so it is -the most efficient choice when comparing only literal atoms. The -assignments - - N2 := N1 := 987654321, - S2 := S1 := '(FROG (SALAMANDER.NEWT)), - -make N2 have the same address as N1 and make S2 have the same address as -S1, but if N1 and N2 were constructed independently, they would not -generally have the same address, and similarly for S1 vs. S2. The -comparison operator "=", which is an alias for "EQUAL", does a general -test for identical s-expressions, which need not be merely two pointers -to the same address. Since "=" is built-in, compiled, and crucial, I -will define my own differently-named version denoted ".=" as follows:; - -PAUSE; -NEWTOK '((!. !=) MYEQUAL); -INFIX EQATOM, MYEQUAL; -PRECEDENCE MYEQUAL, EQUAL; -PRECEDENCE EQATOM,EQ; -SYMBOLIC PROCEDURE S1 MYEQUAL S2; - IF ATOM S1 THEN - IF ATOM S2 THEN S1 EQATOM S2 - ELSE NIL - ELSE IF ATOM S2 THEN NIL - ELSE CAR S1 MYEQUAL CAR S2 AND CDR S1 MYEQUAL CDR S2; -SYMBOLIC PROCEDURE A1 EQATOM A2; - IF NUMBERP A1 THEN - IF NUMBERP A2 THEN ZEROP(A1-A2) - ELSE NIL - ELSE IF NUMBERP A2 THEN NIL - ELSE A1 EQ A2; - -COMMENT Here I introduced a help function named EQATOM, because I was -beginning to become confused by detail when I got to the line which uses -EQATOM. Consequently, I procrastinated on attending to some fine detail -by relegating it to a help function which I was confident could be -successfully written later. After completing MYEQUAL, I was confident -that it would work provided EQATOM worked, so I could then turn my -attention entirely to EQATOM, freed of further distraction by concern -about the more ambitious overall goal. It turns out that EQATOM is a -rather handy utility function anyway, and practice helps develop good -judgement about where best to so subdivide tasks. This psychological -divide-and-conquer programming technique is important in most other -programming languages too. - -".=" is different from our previous examples in that ".=" recurses down -the CAR as well as down the CDR of an s-expression; - -PAUSE; -COMMENT -If a list has n elements, our function named MEMBERP or the equivalent -built-in function named MEMBER requires on the order of n "=" tests. -Consequently, the above definitions of SETP and MAKESET, which require -on the order of n membership tests, will require on the order of n**2 -"=" tests. Similarly, if the two operands have m and n elements, the -above definitions of SUBSETOF, EQSETP, INTERSECT, DIFFSET, and -SYMDIFF require on the order of m*n "=" tests. We could decrease the -growth rates to order of n and order of m+n respectively by sorting the -elements before giving lists to these functions. The best algorithms -sort a list of n elements in the order of n*log(n) element comparisons, -and this need be done only once per input set. To do so we need a -function which returns T if the first argument is "=" to the second -argument or should be placed to the left of the second argument. Such a -function, named ORDP, is already built-into symbolic-mode REDUCE, based -on the following rules: - - 1. Any number orders left of NIL. - 2. Larger numbers order left of smaller numbers. - 4. Literal atoms order left of numbers. - 3. Literal atoms order among themselves by address, as determined - by the built-in RLISP function named ORDERP. - 5. Non-atoms order left of atoms. - 6. Non-atoms order among themselves according to ORDP of their - CARs, with ties broken according to ORDP of their CDRs. - -Try writing an analogous function named MYORD, and, if you are in -REDUCE rather than RLISP, test its behavior in comparison to ORDP; - -PAUSE; - -COMMENT Whether or not we use sorted sets, we can reduce the -proportionality constant associated with the growth rate by replacing -"=" by "EQ" if the set elements are restricted to literal atoms. -However, with such elements we can use property-lists to achieve the -growth rates of the sorted algorithms without any need to sort the -sets. On any LISP system that is efficient enough to support REDUCE -with acceptable performance, the time required to access a property of -an atom is modest and very insensitive to the number of distinct -atoms in the program and data. Consequently, the basic technique -for any of our set operations is: - 1. Scan the list argument or one of the two list arguments, - flagging each element as "SEEN". - 2. During the first scan, or during a second scan of the same - list, or during a scan of the second list, check each element - to see whether or not it has already been flagged, and act - accordingly. - 3. Make a final pass through all elements which were flagged to - remove the flag "SEEN". (Otherwise, we may invalidate later set - operations which utilize any of the same atoms.) - -We could use indicators rather than flags, but the latter are slightly -more efficient when an indicator would have only one value (such as -having "SEEN" as the value of an indicator named "SEENORNOT"). - -As an example, here is INTERSECT defined using this technique; - -SYMBOLIC PROCEDURE INTERSECT(S1, S2); - BEGIN SCALAR ANS, SET2; - FLAG(S1, 'SEEN); - SET2 := S2; - WHILE SET2 DO << - IF FLAGP(CAR SET2, 'SEEN) THEN ANS := CAR SET2 . ANS; - SET2 := CDR SET2 >>; - REMFLAG(S1, 'SEEN); - RETURN ANS - END; - -COMMENT Perhaps you noticed that, having used a BEGIN-block, group, -loop, and assignments, I have not practiced what I preached about -using only function composition, conditional expressions, and -recursion during this lesson. Well, now that you have had some -exposure to both extremes, I think you should always fairly -consider both together with appropriate compromises, in each case -choosing whatever is most clear, concise, and natural. For set -operations based on the property-list approach, I find the style -exemplified immediately above most natural. - -As your last exercise for this lesson, develop a file containing a -package for set operations based upon either property-lists or sorting. - -This is the end of lesson 6. When you are ready to run the final lesson -7, load a fresh copy of REDUCE. - -;END; +COMMENT + + REDUCE INTERACTIVE LESSON NUMBER 6 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 6 of 7 REDUCE lessons. A prerequisite is to +read the pamphlet "An Introduction to LISP", by D. Lurie'. + +To avoid confusion between RLISP and the SYMBOLIC-mode algebraic +algorithms, this lesson will treat only RLISP. Lesson 7 deals with how +the REDUCE algebraic mode is implemented in RLISP and how the user can +interact directly with that implementation. That is why I suggested +that you run this lesson in RLISP rather than full REDUCE. If you +forgot or do not have a locally available separate RLISP, then please +switch now to symbolic mode by typing the statement SYMBOLIC; + +SYMBOLIC; +PAUSE; + +COMMENT Your most frequent mistakes are likely to be forgetting to quote +data examples, using commas as separators within lists, and not puttng +enough levels of parentheses in your data examples. + +Now that you have learned from your reading about the built-in RLISP +functions CAR, CDR, CONS, ATOM, EQ, NULL, LIST, APPEND, REVERSE, DELETE, +MAPLIST, MAPCON, LAMBDA, FLAG, FLAGP, PUT, GET, DEFLIST, NUMBERP, ZEROP, +ONEP, AND, EVAL, PLUS, TIMES, CAAR, CADR, etc., here is an opportunity +to reinforce the learning by practice.: Write expressions using CAR, +CDR, CDDR, etc., (which are defined only through 4 letters between C and +R), to individually extract each atom from F, where; + +F := '((JOHN . DOE) (1147 HOTEL STREET) HONOLULU); +PAUSE; + +COMMENT My solutions are CAAR F, CDAR F, CAADR F, CADADR F, +CADDR CADR F, and CADDR F. + +Although commonly the "." is only mentioned in conjunction with data, we +can also use it as an infix alias for CONS. Do this to build from F and +from the data 'MISTER the s-expression consisting of F with MISTER +inserted before JOHN.DOE; + +PAUSE; + +COMMENT My solution is ('MISTER . CAR F) . CDR F . + +Enough of these inane exercises -- let's get on to something useful! +Let's develop a collection of functions for operating on finite sets. +We will let the elements be arbitrary s-expressions, and we will +represent a set as a list of its elements in arbitrary order, without +duplicates. + +Here is a function which determines whether its first argument is a +member of the set which is its second element; + +SYMBOLIC PROCEDURE MEMBERP(ELEM, SET1); + COMMENT Returns T if s-expression ELEM is a top-level element + of list SET1, returning NIL otherwise; + IF NULL SET1 THEN NIL + ELSE IF ELEM = CAR SET1 THEN T + ELSE MEMBERP(ELEM, CDR SET1); +MEMBERP('BLUE, '(RED BLUE GREEN)); + +COMMENT This function illustrates several convenient techniques for +writing functions which process lists: + + 1. To avoid the errors of taking the CAR or the CDR of an atom, and + to build self confidence while it is not immediately apparent how to + completely solve the problem, treat the trivial cases first. For an + s-expression or list argument, the most trivial cases are generally + when one or more of the arguments are NIL, and a slightly less + trivial case is when one or more is an atom. (Note that we will get + an error message if we use MEMBERP with a second argument which is + not a list. We could check for this, but in the interest of brevity, + I will not strive to make our set-package give set-oriented error + messages.) + + 2. Use CAR to extract the first element and use CDR to refer to the + remainder of the list. + + 3. Use recursion to treat more complicated cases by extracting the + first element and using the same functions on smaller arguments.; + +PAUSE; +COMMENT To make MEMBERP into an infix operator we make the declaration; + +INFIX MEMBERP; +'(JOHN.DOE) MEMBERP '((FIG.NEWTON) FONZO (SANTA CLAUS)); + +COMMENT Infix operators associate left, meaning expressions of the form + + (operator1 operator operand2 operator ... operandN) + +are interpreted as + + ((...(operand1 operator operand2) operator ... operandN). + +Operators may also be flagged RIGHT by + + FLAG ('(op1 op2 ...), 'RIGHT) . + +to give the interpretation + + (operand1 operator (operand2 operator (... operandN))...). + +Of the built-in operators, only ".", "*=", "+", and "*" associate right. + +If we had made the infix declaration before the function definition, the +latter could have begun with the more natural statement + + SYMBOLIC PROCEDURE ELEM MEMBERP SET . + +Infix functions can also be referred to by functional notation if one +desires. Actually, an analogous infix operator named MEMBER is already +built-into RLISP, so we will use MEMBER rather than MEMBERP from here +on; + +MEMBER(1147, CADR F); + +COMMENT Inspired by the simple yet elegant definition of MEMBERP, write +a function named SETP which uses MEMBER to check for a duplicate element +in its list argument, thus determining whether or not the argument of +SETP is a set; + +PAUSE; + +COMMENT My solution is; + +SYMBOLIC PROCEDURE SETP CANDIDATE; + COMMENT Returns T if list CANDIDATE is a set, returning NIL + otherwise; + IF NULL CANDIDATE THEN T + ELSE IF CAR CANDIDATE MEMBER CDR CANDIDATE THEN NIL + ELSE SETP CDR CANDIDATE; +SETP '(KERMIT, (COOKIE MONSTER)); +SETP '(DOG CAT DOG); + +COMMENT If you used a BEGIN-block, local variables, loops, etc., then +your solution is surely more awkward than mine. For the duration of the +lesson, try to do everything without groups, BEGIN-blocks, local +variables, assignments, and loops. Everything can be done using +function composition, conditional expressions, and recursion. It will +be a mind-expanding experience -- more so than transcendental +meditation, psilopsybin, and EST. Afterward, you can revert to your old +ways if you disagree. + +Thus endeth the sermon. + +Incidentally, to make the above definition of SETP work for non-list +arguments all we have to do is insert "ELSE IF ATOM CANDIDATE THEN NIL" +below "IF NULL CANDIDATE THEN T". + +Now try to write an infix procedure named SUBSETOF, such that SET1 +SUBSETOF SET2 returns NIL if SET1 contains an element that SET2 does +not, returning T otherwise. You are always encouraged, by the way, to +use any functions that are already builtin, or that we have previously +defined, or that you define later as auxiliary functions; + +PAUSE; +COMMENT My solution is; + +INFIX SUBSETOF; +SYMBOLIC PROCEDURE SET1 SUBSETOF SET2; + IF NULL SET1 THEN T + ELSE IF CAR SET1 MEMBER SET2 THEN CDR SET1 SUBSETOF SET2 + ELSE NIL; +'(ROOF DOOR) SUBSETOF '(WINDOW DOOR FLOOR ROOF); +'(APPLE BANANA) SUBSETOF '((APPLE COBBLER) (BANANA CREME PIE)); + +COMMENT Two sets are equal when they have identical elements, not +necessarily in the same order. Write an infix procedure named +EQSETP which returns T if its two operands are equal sets, returning +NIL otherwise; + +PAUSE; + +COMMENT The following solution introduces the PRECEDENCE declaration; + +INFIX EQSETP; +PRECEDENCE EQSETP, =; +PRECEDENCE SUBSETOF, EQSETP; +SYMBOLIC PROCEDURE SET1 EQSETP SET2; + SET1 SUBSETOF SET2 AND SET2 SUBSETOF SET1; +'(BALLET TAP) EQSETP '(TAP BALLET); +'(PINE FIR ASPEN) EQSETP '(PINE FIR PALM); + +COMMENT The precedence declarations make SUBSETOF have a higher +precedence than EQSETP and make the latter have higher precedence than +"=", which is higher than "AND",. Consequently, these declarations +enabled me to omit parentheses around "SET1 SUBSUBSETOF SET2" and around +"SET2 SUBSETOF SET1". All prefix operators are higher than any infix +operator, and to inspect the ordering among the latter, we merely +inspect the value of the global variable named; + +PRECLIS!*; + +COMMENT Now see if you can write a REDUCE infix function named +PROPERSUBSETOF, which determines if its left operand is a proper subset +of its right operand, meaning it is a subset which is not equal to the +right operand; + +PAUSE; + +COMMENT All of the above exercises have been predicates. In contrast, +the next exercise is to write a function called MAKESET, which returns +a list which is a copy of its argument, omitting duplicates; + +PAUSE; + +COMMENT How about; + +SYMBOLIC PROCEDURE MAKESET LIS; + IF NULL LIS THEN NIL + ELSE IF CAR LIS MEMBER CDR LIS THEN MAKESET CDR LIS + ELSE CAR LIS . MAKESET CDR LIS; + +COMMENT As you may have guessed, the next exercise is to implement an +operator named INTERSECT, which returns the intersection of its set +operands; + +PAUSE; + +COMMENT Here is my solution; + +INFIX INTERSECT; +PRECEDENCE INTERSECT, SUBSETOF; +SYMBOLIC PROCEDURE SET1 INTERSECT SET2; + IF NULL SET1 THEN NIL + ELSE IF CAR SET1 MEMBER SET2 + THEN CAR SET1 . CDR SET1 INTERSECT SET2 + ELSE CDR SET1 INTERSECT SET2; + +COMMENT Symbolic-mode REDUCE has a built-in function named SETDIFF, +which returns the set of elements which are in its first argument but +not the second. See if you can write an infix definition of a similar +function named DIFFSET; + +PAUSE; + +COMMENT Presenting --; + +INFIX DIFFSET; +PRECEDENCE DIFFSET, INTERSECT; +SYMBOLIC PROCEDURE LEFT DIFFSET RIGHT; + IF NULL LEFT THEN NIL + ELSE IF CAR LEFT MEMBER RIGHT THEN CDR LEFT DIFFSET RIGHT + ELSE CAR LEFT . (CDR LEFT DIFFSET RIGHT); +'(SEAGULL WREN CONDOR) DIFFSET '(WREN LARK); + +COMMENT The symmetric difference of two sets is the set of all elements +which are in only one of the two sets. Implement a corresponding infix +function named SYMDIFF. Look for the easy way! There is almost always +one for examinations and instructional exercises; PAUSE; + +COMMENT Presenting --; +INFIX SYMDIFF; +PRECEDENCE SYMDIFF, INTERSECT; +SYMBOLIC PROCEDURE SET1 SYMDIFF SET2; + APPEND(SET1 DIFFSET SET2, SET2 DIFFSET SET1); +'(SEAGULL WREN CONDOR) SYMDIFF '(WREN LARK); + +COMMENT We can use APPEND because the two set differences are disjoint. + +The above set of exercises (exercises of set?) have all returned set +results. The cardinality, size, or length of a set is the number of +elements in the set. More generally, it is useful to have a function +which returns the length of its list argument, and such a function is +built-into RLISP. See if you can write a similar function named SIZEE; + +PAUSE; +COMMENT Presenting --; +SYMBOLIC PROCEDURE SIZEE LIS; + IF NULL LIS THEN 0 + ELSE 1 + SIZEE CDR LIS; +SIZEE '(HOW MARVELOUSLY CONCISE); +SIZEE '(); + +COMMENT Literal atoms, meaning atoms which are not numbers, are stored +uniquely in LISP and in RLISP, so comparison for equality of literal +atoms can be implemented by comparing their addresses, which is +significantly more efficient than a character-by-character comparison of +their names. The comparison operator "EQ" compares addresses, so it is +the most efficient choice when comparing only literal atoms. The +assignments + + N2 := N1 := 987654321, + S2 := S1 := '(FROG (SALAMANDER.NEWT)), + +make N2 have the same address as N1 and make S2 have the same address as +S1, but if N1 and N2 were constructed independently, they would not +generally have the same address, and similarly for S1 vs. S2. The +comparison operator "=", which is an alias for "EQUAL", does a general +test for identical s-expressions, which need not be merely two pointers +to the same address. Since "=" is built-in, compiled, and crucial, I +will define my own differently-named version denoted ".=" as follows:; + +PAUSE; +NEWTOK '((!. !=) MYEQUAL); +INFIX EQATOM, MYEQUAL; +PRECEDENCE MYEQUAL, EQUAL; +PRECEDENCE EQATOM,EQ; +SYMBOLIC PROCEDURE S1 MYEQUAL S2; + IF ATOM S1 THEN + IF ATOM S2 THEN S1 EQATOM S2 + ELSE NIL + ELSE IF ATOM S2 THEN NIL + ELSE CAR S1 MYEQUAL CAR S2 AND CDR S1 MYEQUAL CDR S2; +SYMBOLIC PROCEDURE A1 EQATOM A2; + IF NUMBERP A1 THEN + IF NUMBERP A2 THEN ZEROP(A1-A2) + ELSE NIL + ELSE IF NUMBERP A2 THEN NIL + ELSE A1 EQ A2; + +COMMENT Here I introduced a help function named EQATOM, because I was +beginning to become confused by detail when I got to the line which uses +EQATOM. Consequently, I procrastinated on attending to some fine detail +by relegating it to a help function which I was confident could be +successfully written later. After completing MYEQUAL, I was confident +that it would work provided EQATOM worked, so I could then turn my +attention entirely to EQATOM, freed of further distraction by concern +about the more ambitious overall goal. It turns out that EQATOM is a +rather handy utility function anyway, and practice helps develop good +judgement about where best to so subdivide tasks. This psychological +divide-and-conquer programming technique is important in most other +programming languages too. + +".=" is different from our previous examples in that ".=" recurses down +the CAR as well as down the CDR of an s-expression; + +PAUSE; +COMMENT +If a list has n elements, our function named MEMBERP or the equivalent +built-in function named MEMBER requires on the order of n "=" tests. +Consequently, the above definitions of SETP and MAKESET, which require +on the order of n membership tests, will require on the order of n**2 +"=" tests. Similarly, if the two operands have m and n elements, the +above definitions of SUBSETOF, EQSETP, INTERSECT, DIFFSET, and +SYMDIFF require on the order of m*n "=" tests. We could decrease the +growth rates to order of n and order of m+n respectively by sorting the +elements before giving lists to these functions. The best algorithms +sort a list of n elements in the order of n*log(n) element comparisons, +and this need be done only once per input set. To do so we need a +function which returns T if the first argument is "=" to the second +argument or should be placed to the left of the second argument. Such a +function, named ORDP, is already built-into symbolic-mode REDUCE, based +on the following rules: + + 1. Any number orders left of NIL. + 2. Larger numbers order left of smaller numbers. + 4. Literal atoms order left of numbers. + 3. Literal atoms order among themselves by address, as determined + by the built-in RLISP function named ORDERP. + 5. Non-atoms order left of atoms. + 6. Non-atoms order among themselves according to ORDP of their + CARs, with ties broken according to ORDP of their CDRs. + +Try writing an analogous function named MYORD, and, if you are in +REDUCE rather than RLISP, test its behavior in comparison to ORDP; + +PAUSE; + +COMMENT Whether or not we use sorted sets, we can reduce the +proportionality constant associated with the growth rate by replacing +"=" by "EQ" if the set elements are restricted to literal atoms. +However, with such elements we can use property-lists to achieve the +growth rates of the sorted algorithms without any need to sort the +sets. On any LISP system that is efficient enough to support REDUCE +with acceptable performance, the time required to access a property of +an atom is modest and very insensitive to the number of distinct +atoms in the program and data. Consequently, the basic technique +for any of our set operations is: + 1. Scan the list argument or one of the two list arguments, + flagging each element as "SEEN". + 2. During the first scan, or during a second scan of the same + list, or during a scan of the second list, check each element + to see whether or not it has already been flagged, and act + accordingly. + 3. Make a final pass through all elements which were flagged to + remove the flag "SEEN". (Otherwise, we may invalidate later set + operations which utilize any of the same atoms.) + +We could use indicators rather than flags, but the latter are slightly +more efficient when an indicator would have only one value (such as +having "SEEN" as the value of an indicator named "SEENORNOT"). + +As an example, here is INTERSECT defined using this technique; + +SYMBOLIC PROCEDURE INTERSECT(S1, S2); + BEGIN SCALAR ANS, SET2; + FLAG(S1, 'SEEN); + SET2 := S2; + WHILE SET2 DO << + IF FLAGP(CAR SET2, 'SEEN) THEN ANS := CAR SET2 . ANS; + SET2 := CDR SET2 >>; + REMFLAG(S1, 'SEEN); + RETURN ANS + END; + +COMMENT Perhaps you noticed that, having used a BEGIN-block, group, +loop, and assignments, I have not practiced what I preached about +using only function composition, conditional expressions, and +recursion during this lesson. Well, now that you have had some +exposure to both extremes, I think you should always fairly +consider both together with appropriate compromises, in each case +choosing whatever is most clear, concise, and natural. For set +operations based on the property-list approach, I find the style +exemplified immediately above most natural. + +As your last exercise for this lesson, develop a file containing a +package for set operations based upon either property-lists or sorting. + +This is the end of lesson 6. When you are ready to run the final lesson +7, load a fresh copy of REDUCE. + +;END; Index: r36/LESS7 ================================================================== --- r36/LESS7 +++ r36/LESS7 @@ -1,398 +1,398 @@ -COMMENT - - REDUCE INTERACTIVE LESSON NUMBER 7 - - David R. Stoutemyer - University of Hawaii - - -COMMENT This is lesson 7 of 7 REDUCE lessons. It was suggested that -you bring a REDUCE source listing, together with a cross-reference -(CREF) thereof, but this lesson is beneficial even without them. - -Sometimes it is desired to have a certain facility available to -algebraic mode, no such facility is described in the REDUCE User's -manual, and there is no easy way to implement the facility directly -in algebraic mode. The possibilities are: - 1. The facility exists for algebraic mode, but is undocumented. - 2. The facility exists, but is available only in symbolic mode. - 3. The facility is not built-in for either mode. - -Perusal of the source listing and CREF, together with experimentation -can reveal which of these alternatives is true. (Even in case 3, an -inquiry to A.C. Hearn at the Rand Corporation may reveal that someone -else has already implemented the supplementary facility and can send a -copy.) - -;PAUSE;COMMENT - -A type of statement is available to both modes if its leading keyword -appears in either of the equivalent statements - - PUT (..., 'STAT, ...) -or - DEFLIST('(...), 'STAT) . - -A symbolic-mode global variable is available to algebraic mode and -vice-versa if the name of the variable appears in either of the -equivalent statements - - SHARE ..., -or - FLAG('(...), 'SHARE) . - -A function defined in symbolic mode is directly available to -algebraic mode if the function name appears in one of the statements - - SYMBOLIC OPERATOR ..., - PUT(..., 'SIMPFN, ...), - DEFLIST('(...), 'SIMPFN), - FLAG('(...), 'OPFN), - -In addition, if you want a function to be used as a predicate in -in IF or WHILE statements, it should be flagged BOOLEAN, as in - - FLAG('(...),'BOOLEAN); - -;PAUSE;COMMENT - -Other functions which are used but not defined in RLISP are the built-in -LISP functions. See a description of the underlying LISP system for -documentation on these functions. - -Particularly notable built-in features available only to symbolic -mode include - 1. A function named FIX, which returns the truncated integer - portion of its floating-point argument. - 2. A function named SPACES, which prints the number of blanks - indicated by its integer argument. - 3. A function named REDERR, which provokes an error interrupt - after printing its arguments. - 4. A predicate named KERNP, which returns NIL if its argument - is not an indeterminate or a functional form. - 5. A function named MATHPRINT, which prints its argument in - natural mathematical notation, beginning on a new line. - 6. A function named MAPRIN, which is like MATHPRINT, but does not - automatically start or end a new line. - 7. A function named TERPRI!*, which ends the current print-line. - -Thus, for example, all that we have to do to make the predicate -KERNP and the function FIX available to algebraic mode is to type - - FLAG('(KERNP), 'BOOLEAN), - SYMBOLIC OPERATOR FIX . - -When such simple remedies are unavailable, we can introduce our own -statements or write our own SYMBOLIC-mode variables and procedures, then -use these techniques to make them available to algebraic mode. In order -to do so, it is usually necessary to understand how REDUCE represents -and simplifies algebraic expressions. - -;PAUSE;COMMENT - -One of the REDUCE representations is called Cambridge Prefix. An -expression is either an atom or a list consisting of a literal atom, -denoting a function or operator name, followed by arguments which are -Cambridge Prefix expressions. The most common unary operator names are -MINUS, LOG, SIN, and COS. The most common binary operator names are -DIFFERENCE, QUOTIENT, and EXPT. The most common nary operator names are -PLUS and TIMES. Thus, for example, the expression - - 3*x**2*y + x**(1/2) + e**(-x) - -could be represented as - -'(PLUS (TIMES 3 (EXPT X 2) Y) (EXPT X (QUOTIENT 1 2)) (EXPT E (MINUS X)) - -The parser produces an unsimplified Cambridge Prefix version of -algebraic-mode expressions typed by the user, then the simplifier -returns a simplified prefix version. When a symbolic procedure that has -been declared a symbolic operator is invoked from algebraic mode, the -procedure is given simplified Cambridge Prefix versions of the -arguments. To illustrate these ideas, here is an infix function named -ISFREEOF, which determines whether its left argument is free of the -indeterminate, function name, or literal subexpression which is the -right argument. Isfreeof is similar to the REDUCE FREEOF function but -less general; - -PAUSE; - -FLAG('(ISFREEOF), 'BOOLEAN); -INFIX ISFREEOF; -SYMBOLIC PROCEDURE CAMPRE1 ISFREEOF CAMPRE2; - IF CAMPRE1=CAMPRE2 THEN NIL - ELSE IF ATOM CAMPRE1 THEN T - ELSE (CAR CAMPRE1 ISFREEOF CAMPRE2) - AND (CDR CAMPRE1 ISFREEOF CAMPRE2); - -ALGEBRAIC IF LOG(5+X+COS(Y)) ISFREEOF SIN(Z-7) - THEN WRITE "WORKS ONE WAY"; -ALGEBRAIC IF NOT(LOG(5+X+COS(Y)) ISFREEOF COS(Y)) - THEN WRITE "WORKS OTHER WAY TOO"; - -COMMENT Conceivably we might wish to distinguish when CAMPRE2 is a -literal atom occurring as a function name from the case when CAMPRE2 is -a literal atom and occurs as an indeterminate. Accordingly, see if you -can write two such more specialized infix predicates named ISFREEOFINDET -and ISFREEOFFUNCTION; - -PAUSE; - -COMMENT When writing a symbolic-mode function, it is often desired -to invoke the algebraic simplifier from within the function. This -can be done by using the function named REVAL, which returns a -simplified Cambridge Prefix version of its prefix argument. - -Usually, REDUCE uses and produces a different representation, -which I call REDUCE prefix. The symbolic function AEVAL returns a -simplified REDUCE-prefix version of its prefix argument. Both REVAL -and AEVAL can take either type of prefix argument. - -A REDUCE-prefix expression is an integer, a floating-point number, an -indeterminate, or an expression of the form - - ('!*SQ standardquotient . !*SQVAR!*). - -!*SQVAR!* is a global variable which is set to T when the REDUCE- -prefix expression is originally formed. The values of !*SQVAR!* is -reset to NIL if subsequent LET, MATCH, or computational ON -statements could change the environment is such a way that the -expression might require resimplification next time it is used. - -;PAUSE;COMMENT - -Standard quotients are neither Cambridge nor REDUCE prefix, so the -purpose of the atom '!*SQ is to make the value of all algebraic-mode -variables always be some type of prefix form at the top level. - -A standard quotient is a unit-normal dotted pair of 2 standard forms, -and a standard form is the REDUCE representation for a polynomial. -Unit-normal means that the leading coefficient of the denominator is -positive. - -REDUCE has a built-in symbolic function SIMP!*, which returns the -simplified standard quotient representation of its argument, which can -be either Cambridge or REDUCE prefix. REDUCE also has symbolic -functions named NEGSQ, INVSQ, ADDSQ, MULTSQ, DIVSQ, DIFFSQ, and CANONSQ -which respectively negate, reciprocate, add, multiply, divide, -differentiate, and unit-normalize standard quotients. There is also a -function named ABSQ, which negates a standard quotient if the leading -coefficient of its numerator is negative, and there is a function named -EXPTSQ which raises a standard quotient to an integer power. Finally, -there is a function named MK!*SQ, which returns a REDUCE prefix version -of its standard-quotient argument, and there is also a function named -PREPSQ which returns a Cambridge prefix version of its standard-quotient -argument. - -If there is a sequence of operations, rather than converting from -prefix to standard quotient and back at each step, it is usually more -efficient to do the operations on standard quotients, then use MK!*SQ -to make the final result be REDUCE prefix. Also it is often more -efficient to work with polynomials rather than rational functions -during the intermediate steps. - -;PAUSE;COMMENT - -The coefficient domain of polynomials is floating-point numbers, -integers, integers modulo an arbitrary integer modulus, or rational -numbers. However, zero is represented as NIL. - -The polynomial variables are called kernels, which can be -indeterminates or uniquely-stored fully simplified Cambridge-prefix -functional forms. The latter alternative permits the representation -of expressions which could not otherwise be represented as the ratio -of two expanded polynomials, such as - 1. subexpressions of the form LOG(...) or SIN(...). - 2. subexpressions of the form indeterminate**noninteger. - 3. unexpanded polynomials, each polynomial factor being - represented as a functional form. - 4. rational expressions not placed over a common denominator, - each quotient subexrpession being represented as a functional - form. - -A polynomial is represented as a list of its nonzero terms in -decreasing order of the degree of the leading "variable". Each term -is represented as a standard power dotted with its coefficient, which -is a standard form in the remaining variables. A standard power is -represented as a variable dotted with a positive integer degree. - -;PAUSE;COMMENT - -Letting ::= denote "is defined as" and letting | denote "or", -we can summarize the REDUCE data representations as follows: - - reduceprefix ::= ('!*SQ standardquotient . !*SQVAR!*) - standardquotient ::= NUMR(standardquotient) ./ - DENR(standardquotient) - NUMR(standardquotient) ::= standardform - DENR(standardquotient) ::= unitnormalstandardform - domainelement ::= NIL | nonzerointeger | nonzerofloat | - nonzerointeger . positiveinteger - standardform ::= domainelement | - LT(standardform) .+ RED(standardform) - RED(standardform) ::= standardform - LT(standardform) := LPOW(standardform) .* LC(standardform) - LPOW(standardform) := MVAR(standardform) .** LDEG(standardform) - LC(standardform) ::= standardform - MVAR(standardform) ::= kernel - kernel ::= indeterminate | functionalform - functionalform ::= (functionname Cambridgeprefix1 Cambridgeprefix2 - ...) - Cambridgeprefix ::= integer | float | indeterminate | - functionalform - LC(unitnormalstandardform) ::= positivedomainelement | - unitnormalstandardform - -I have taken this opportunity to also introduce the major REDUCE -selector macros named NUMR, DENR, LT, RED, LPOW, LC, MVAR, and LDEG, -together with the major constructor macros named ./, .+, .*, and .** . -The latter are just mnemonic aliases for "." A comparison of my verbal -and more formal definitions also reveals that the selectors are -respectively just aliases for CAR, CDR, CAR, CDR, CAAR, CDAR, CAAAR, and -CDAAR. Since these selectors and constructors are macros rather than -functions, they afford a more readable and modifiable programming style -at no cost in ultimate efficiency. Thus you are encouraged to use them -and to invent your own when convenient. As an example of how this can -be done, here is the macro definition for extracting the main variable -of a standard term; - - SYMBOLIC SMACRO PROCEDURE TVAR TRM; CAAR TRM; - -PAUSE; - -COMMENT It turns out that there are already built-in selectors named TC, -TPOW, and TDEG, which respectively extract the coefficient, leading -power, and leading degree of a standard term. There are also built-in -constructors named !*P2F, !*K2F, !*K2Q, and !*T2Q, which respectively -make a power into a standard form, a kernel into a standard form, a -kernel into a standard quotient, and a term into a standard quotient. -See the User's Manual for a complete list. - -The unary functions NEGF and ABSF respectively negate, and unit- -normalize their standard-form arguments. The binary functions ADDF, -MULTF, QUOTF, SUBF, EXPTF, and GCDF respectively add, multiply, divide, -substitute into, raise to a positive integer power, and determine the -greatest common divisor of standard forms. See if you can use them to -define a macro which subtracts standard forms; - -PAUSE; - -COMMENT The best way to become adept at working with standard forms and -standard quotients is to study the corresponding portions of the REDUCE -source listing. The listing of ADDF and its subordinates is -particularly instructive. As an exercise, see if you can write a -function named ISFREEOFKERN which determines whether or not its left -argument is free of the kernel which is the right argument, using REDUCE -prefix rather than Cambridge prefix for the left argument; - -PAUSE; - -COMMENT As a final example of the interaction between modes, here -is a function which produces simple print plots; - -SHARE NCOLS; -NCOLS := 66; -SYMBOLIC OPERATOR PLOT; -SYMBOLIC PROCEDURE PLOT(EX, XINIT, DX, NDX, YINIT, DY); - BEGIN COMMENT This procedure produces a print-plot of univariate - expression EX where, - XINIT is the initial value of the indeterminate, - DX is the increment per line of the indeterminate, - NDX is the number of lines plotted, - YINIT is the value represented at the left edge, - DY is incremental value per column. - The shared variable NCOLS, initially 66, is the number of columns - used. Points are plotted using "*", except "<" and ">" are used - at the left and right edges to indicate out of bounds points. - Without supplementary rules, many REDUCE implementations will be - unable to numerically evaluate expressions involving operations - other than +, -, *, /, and integer powers; - - SCALAR X, F, Y; INTEGER COL, NCOLSMINUS1; - NCOLSMINUS1 := NCOLS - 1; - WRITE "Starting the plot of ",EX; - X := LISTOFVARS EX; % find indeterminates; - IF LENGTH X > 1 THEN REDERR - "ERROR: PLOT expression can have at most 1 indeterminate"; - IF NULL X THEN << - WRITE "ERROR: no indeterminates in ", EX; - REDERR "" >> - ELSE X := CAR X; - WRITE " in variable ",x;terpri(); - COMMENT Convert args from algebraic to symbolic values; - XINIT := REVALX XINIT; - DX := REVALX DX; - YINIT := REVALX YINIT; - DY := REVALX DY; - - FOR J:= 0:NDX DO << - - % generate expression with current value substituted for x - F := SUBST(XINIT + J*DX, X, EX); - Y := EVAL(F); % eval expression - COL := RND((Y - YINIT)/DY); % scale and round for cols - - IF COL<0 THEN WRITE "<" - ELSE IF COL > NCOLSMINUS1 THEN << SPACES(NCOLSMINUS1); - PRIN2 ">"; - TERPRI() >> - ELSE << SPACES(COL); - PRIN2 "*"; - TERPRI() >> - >> ; - IF NULL Y THEN REDERR - "ERROR: UNABLE TO PERFORM FLOATING-POINT EVALUATION OF 1ST ARG" - END; - -PAUSE; - -SYMBOLIC PROCEDURE LISTOFVARS CAMPRE; - IF NULL CAMPRE OR NUMBERP CAMPRE THEN NIL - ELSE IF ATOM CAMPRE THEN LIST CAMPRE - ELSE VARSINARGS CDR CAMPRE; - -SYMBOLIC PROCEDURE VARSINARGS LISTOFCAMPRE; - BEGIN SCALAR X; - RETURN IF NULL LISTOFCAMPRE THEN NIL - ELSE UNION(LISTOFVARS CAR LISTOFCAMPRE, VARSINARGS CDR LISTOFCAMPRE); - END; - -SYMBOLIC PROCEDURE RND X; - BEGIN SCALAR ANS; - ANS := REVALX X; - IF NOT NUMBERP X THEN REDDERR "RND GIVEN NON-NUMERIC ARGUMENT"; - IF ANS >=0 THEN ANS := FIX(ANS+00.5) - ELSE ANS:= FIX(ANS-0.5); - RETURN ANS - END; - -SYMBOLIC PROCEDURE REVALX U; - % MAKE SURE WE GET TRUE FLOATS IN SYMBOLIC MODE. - IF EQCAR(U,'!:RD!:) THEN RDPREPX U ELSE U; - -SYMBOLIC PROCEDURE RDPREPX U; - IF FLOATP CDR U THEN CDR U ELSE BF2FLR U; - -PAUSE; - -ON ROUNDED; - -PLOT(Y**2, 0, 0.25, 10, 0, 0.25); -PAUSE; - -PLOT((A+1)**2, 0, 0.25, 10, 0, 0.25); -PAUSE; - -B := A*2; - -PLOT(A*B, 0, 0.25, 10, 0, 0.25); -PAUSE; - -COMMENT We leave it as an exercise to write a more elaborate plot -procedure which offers amenities such as automatic scaling, numbered -ordinates, etc. - -Good luck with these exercises, with REDUCE, with computer algebra and -with all of your endeavors. - -;END; +COMMENT + + REDUCE INTERACTIVE LESSON NUMBER 7 + + David R. Stoutemyer + University of Hawaii + + +COMMENT This is lesson 7 of 7 REDUCE lessons. It was suggested that +you bring a REDUCE source listing, together with a cross-reference +(CREF) thereof, but this lesson is beneficial even without them. + +Sometimes it is desired to have a certain facility available to +algebraic mode, no such facility is described in the REDUCE User's +manual, and there is no easy way to implement the facility directly +in algebraic mode. The possibilities are: + 1. The facility exists for algebraic mode, but is undocumented. + 2. The facility exists, but is available only in symbolic mode. + 3. The facility is not built-in for either mode. + +Perusal of the source listing and CREF, together with experimentation +can reveal which of these alternatives is true. (Even in case 3, an +inquiry to A.C. Hearn at the Rand Corporation may reveal that someone +else has already implemented the supplementary facility and can send a +copy.) + +;PAUSE;COMMENT + +A type of statement is available to both modes if its leading keyword +appears in either of the equivalent statements + + PUT (..., 'STAT, ...) +or + DEFLIST('(...), 'STAT) . + +A symbolic-mode global variable is available to algebraic mode and +vice-versa if the name of the variable appears in either of the +equivalent statements + + SHARE ..., +or + FLAG('(...), 'SHARE) . + +A function defined in symbolic mode is directly available to +algebraic mode if the function name appears in one of the statements + + SYMBOLIC OPERATOR ..., + PUT(..., 'SIMPFN, ...), + DEFLIST('(...), 'SIMPFN), + FLAG('(...), 'OPFN), + +In addition, if you want a function to be used as a predicate in +in IF or WHILE statements, it should be flagged BOOLEAN, as in + + FLAG('(...),'BOOLEAN); + +;PAUSE;COMMENT + +Other functions which are used but not defined in RLISP are the built-in +LISP functions. See a description of the underlying LISP system for +documentation on these functions. + +Particularly notable built-in features available only to symbolic +mode include + 1. A function named FIX, which returns the truncated integer + portion of its floating-point argument. + 2. A function named SPACES, which prints the number of blanks + indicated by its integer argument. + 3. A function named REDERR, which provokes an error interrupt + after printing its arguments. + 4. A predicate named KERNP, which returns NIL if its argument + is not an indeterminate or a functional form. + 5. A function named MATHPRINT, which prints its argument in + natural mathematical notation, beginning on a new line. + 6. A function named MAPRIN, which is like MATHPRINT, but does not + automatically start or end a new line. + 7. A function named TERPRI!*, which ends the current print-line. + +Thus, for example, all that we have to do to make the predicate +KERNP and the function FIX available to algebraic mode is to type + + FLAG('(KERNP), 'BOOLEAN), + SYMBOLIC OPERATOR FIX . + +When such simple remedies are unavailable, we can introduce our own +statements or write our own SYMBOLIC-mode variables and procedures, then +use these techniques to make them available to algebraic mode. In order +to do so, it is usually necessary to understand how REDUCE represents +and simplifies algebraic expressions. + +;PAUSE;COMMENT + +One of the REDUCE representations is called Cambridge Prefix. An +expression is either an atom or a list consisting of a literal atom, +denoting a function or operator name, followed by arguments which are +Cambridge Prefix expressions. The most common unary operator names are +MINUS, LOG, SIN, and COS. The most common binary operator names are +DIFFERENCE, QUOTIENT, and EXPT. The most common nary operator names are +PLUS and TIMES. Thus, for example, the expression + + 3*x**2*y + x**(1/2) + e**(-x) + +could be represented as + +'(PLUS (TIMES 3 (EXPT X 2) Y) (EXPT X (QUOTIENT 1 2)) (EXPT E (MINUS X)) + +The parser produces an unsimplified Cambridge Prefix version of +algebraic-mode expressions typed by the user, then the simplifier +returns a simplified prefix version. When a symbolic procedure that has +been declared a symbolic operator is invoked from algebraic mode, the +procedure is given simplified Cambridge Prefix versions of the +arguments. To illustrate these ideas, here is an infix function named +ISFREEOF, which determines whether its left argument is free of the +indeterminate, function name, or literal subexpression which is the +right argument. Isfreeof is similar to the REDUCE FREEOF function but +less general; + +PAUSE; + +FLAG('(ISFREEOF), 'BOOLEAN); +INFIX ISFREEOF; +SYMBOLIC PROCEDURE CAMPRE1 ISFREEOF CAMPRE2; + IF CAMPRE1=CAMPRE2 THEN NIL + ELSE IF ATOM CAMPRE1 THEN T + ELSE (CAR CAMPRE1 ISFREEOF CAMPRE2) + AND (CDR CAMPRE1 ISFREEOF CAMPRE2); + +ALGEBRAIC IF LOG(5+X+COS(Y)) ISFREEOF SIN(Z-7) + THEN WRITE "WORKS ONE WAY"; +ALGEBRAIC IF NOT(LOG(5+X+COS(Y)) ISFREEOF COS(Y)) + THEN WRITE "WORKS OTHER WAY TOO"; + +COMMENT Conceivably we might wish to distinguish when CAMPRE2 is a +literal atom occurring as a function name from the case when CAMPRE2 is +a literal atom and occurs as an indeterminate. Accordingly, see if you +can write two such more specialized infix predicates named ISFREEOFINDET +and ISFREEOFFUNCTION; + +PAUSE; + +COMMENT When writing a symbolic-mode function, it is often desired +to invoke the algebraic simplifier from within the function. This +can be done by using the function named REVAL, which returns a +simplified Cambridge Prefix version of its prefix argument. + +Usually, REDUCE uses and produces a different representation, +which I call REDUCE prefix. The symbolic function AEVAL returns a +simplified REDUCE-prefix version of its prefix argument. Both REVAL +and AEVAL can take either type of prefix argument. + +A REDUCE-prefix expression is an integer, a floating-point number, an +indeterminate, or an expression of the form + + ('!*SQ standardquotient . !*SQVAR!*). + +!*SQVAR!* is a global variable which is set to T when the REDUCE- +prefix expression is originally formed. The values of !*SQVAR!* is +reset to NIL if subsequent LET, MATCH, or computational ON +statements could change the environment is such a way that the +expression might require resimplification next time it is used. + +;PAUSE;COMMENT + +Standard quotients are neither Cambridge nor REDUCE prefix, so the +purpose of the atom '!*SQ is to make the value of all algebraic-mode +variables always be some type of prefix form at the top level. + +A standard quotient is a unit-normal dotted pair of 2 standard forms, +and a standard form is the REDUCE representation for a polynomial. +Unit-normal means that the leading coefficient of the denominator is +positive. + +REDUCE has a built-in symbolic function SIMP!*, which returns the +simplified standard quotient representation of its argument, which can +be either Cambridge or REDUCE prefix. REDUCE also has symbolic +functions named NEGSQ, INVSQ, ADDSQ, MULTSQ, DIVSQ, DIFFSQ, and CANONSQ +which respectively negate, reciprocate, add, multiply, divide, +differentiate, and unit-normalize standard quotients. There is also a +function named ABSQ, which negates a standard quotient if the leading +coefficient of its numerator is negative, and there is a function named +EXPTSQ which raises a standard quotient to an integer power. Finally, +there is a function named MK!*SQ, which returns a REDUCE prefix version +of its standard-quotient argument, and there is also a function named +PREPSQ which returns a Cambridge prefix version of its standard-quotient +argument. + +If there is a sequence of operations, rather than converting from +prefix to standard quotient and back at each step, it is usually more +efficient to do the operations on standard quotients, then use MK!*SQ +to make the final result be REDUCE prefix. Also it is often more +efficient to work with polynomials rather than rational functions +during the intermediate steps. + +;PAUSE;COMMENT + +The coefficient domain of polynomials is floating-point numbers, +integers, integers modulo an arbitrary integer modulus, or rational +numbers. However, zero is represented as NIL. + +The polynomial variables are called kernels, which can be +indeterminates or uniquely-stored fully simplified Cambridge-prefix +functional forms. The latter alternative permits the representation +of expressions which could not otherwise be represented as the ratio +of two expanded polynomials, such as + 1. subexpressions of the form LOG(...) or SIN(...). + 2. subexpressions of the form indeterminate**noninteger. + 3. unexpanded polynomials, each polynomial factor being + represented as a functional form. + 4. rational expressions not placed over a common denominator, + each quotient subexrpession being represented as a functional + form. + +A polynomial is represented as a list of its nonzero terms in +decreasing order of the degree of the leading "variable". Each term +is represented as a standard power dotted with its coefficient, which +is a standard form in the remaining variables. A standard power is +represented as a variable dotted with a positive integer degree. + +;PAUSE;COMMENT + +Letting ::= denote "is defined as" and letting | denote "or", +we can summarize the REDUCE data representations as follows: + + reduceprefix ::= ('!*SQ standardquotient . !*SQVAR!*) + standardquotient ::= NUMR(standardquotient) ./ + DENR(standardquotient) + NUMR(standardquotient) ::= standardform + DENR(standardquotient) ::= unitnormalstandardform + domainelement ::= NIL | nonzerointeger | nonzerofloat | + nonzerointeger . positiveinteger + standardform ::= domainelement | + LT(standardform) .+ RED(standardform) + RED(standardform) ::= standardform + LT(standardform) := LPOW(standardform) .* LC(standardform) + LPOW(standardform) := MVAR(standardform) .** LDEG(standardform) + LC(standardform) ::= standardform + MVAR(standardform) ::= kernel + kernel ::= indeterminate | functionalform + functionalform ::= (functionname Cambridgeprefix1 Cambridgeprefix2 + ...) + Cambridgeprefix ::= integer | float | indeterminate | + functionalform + LC(unitnormalstandardform) ::= positivedomainelement | + unitnormalstandardform + +I have taken this opportunity to also introduce the major REDUCE +selector macros named NUMR, DENR, LT, RED, LPOW, LC, MVAR, and LDEG, +together with the major constructor macros named ./, .+, .*, and .** . +The latter are just mnemonic aliases for "." A comparison of my verbal +and more formal definitions also reveals that the selectors are +respectively just aliases for CAR, CDR, CAR, CDR, CAAR, CDAR, CAAAR, and +CDAAR. Since these selectors and constructors are macros rather than +functions, they afford a more readable and modifiable programming style +at no cost in ultimate efficiency. Thus you are encouraged to use them +and to invent your own when convenient. As an example of how this can +be done, here is the macro definition for extracting the main variable +of a standard term; + + SYMBOLIC SMACRO PROCEDURE TVAR TRM; CAAR TRM; + +PAUSE; + +COMMENT It turns out that there are already built-in selectors named TC, +TPOW, and TDEG, which respectively extract the coefficient, leading +power, and leading degree of a standard term. There are also built-in +constructors named !*P2F, !*K2F, !*K2Q, and !*T2Q, which respectively +make a power into a standard form, a kernel into a standard form, a +kernel into a standard quotient, and a term into a standard quotient. +See the User's Manual for a complete list. + +The unary functions NEGF and ABSF respectively negate, and unit- +normalize their standard-form arguments. The binary functions ADDF, +MULTF, QUOTF, SUBF, EXPTF, and GCDF respectively add, multiply, divide, +substitute into, raise to a positive integer power, and determine the +greatest common divisor of standard forms. See if you can use them to +define a macro which subtracts standard forms; + +PAUSE; + +COMMENT The best way to become adept at working with standard forms and +standard quotients is to study the corresponding portions of the REDUCE +source listing. The listing of ADDF and its subordinates is +particularly instructive. As an exercise, see if you can write a +function named ISFREEOFKERN which determines whether or not its left +argument is free of the kernel which is the right argument, using REDUCE +prefix rather than Cambridge prefix for the left argument; + +PAUSE; + +COMMENT As a final example of the interaction between modes, here +is a function which produces simple print plots; + +SHARE NCOLS; +NCOLS := 66; +SYMBOLIC OPERATOR PLOT; +SYMBOLIC PROCEDURE PLOT(EX, XINIT, DX, NDX, YINIT, DY); + BEGIN COMMENT This procedure produces a print-plot of univariate + expression EX where, + XINIT is the initial value of the indeterminate, + DX is the increment per line of the indeterminate, + NDX is the number of lines plotted, + YINIT is the value represented at the left edge, + DY is incremental value per column. + The shared variable NCOLS, initially 66, is the number of columns + used. Points are plotted using "*", except "<" and ">" are used + at the left and right edges to indicate out of bounds points. + Without supplementary rules, many REDUCE implementations will be + unable to numerically evaluate expressions involving operations + other than +, -, *, /, and integer powers; + + SCALAR X, F, Y; INTEGER COL, NCOLSMINUS1; + NCOLSMINUS1 := NCOLS - 1; + WRITE "Starting the plot of ",EX; + X := LISTOFVARS EX; % find indeterminates; + IF LENGTH X > 1 THEN REDERR + "ERROR: PLOT expression can have at most 1 indeterminate"; + IF NULL X THEN << + WRITE "ERROR: no indeterminates in ", EX; + REDERR "" >> + ELSE X := CAR X; + WRITE " in variable ",x;terpri(); + COMMENT Convert args from algebraic to symbolic values; + XINIT := REVALX XINIT; + DX := REVALX DX; + YINIT := REVALX YINIT; + DY := REVALX DY; + + FOR J:= 0:NDX DO << + + % generate expression with current value substituted for x + F := SUBST(XINIT + J*DX, X, EX); + Y := EVAL(F); % eval expression + COL := RND((Y - YINIT)/DY); % scale and round for cols + + IF COL<0 THEN WRITE "<" + ELSE IF COL > NCOLSMINUS1 THEN << SPACES(NCOLSMINUS1); + PRIN2 ">"; + TERPRI() >> + ELSE << SPACES(COL); + PRIN2 "*"; + TERPRI() >> + >> ; + IF NULL Y THEN REDERR + "ERROR: UNABLE TO PERFORM FLOATING-POINT EVALUATION OF 1ST ARG" + END; + +PAUSE; + +SYMBOLIC PROCEDURE LISTOFVARS CAMPRE; + IF NULL CAMPRE OR NUMBERP CAMPRE THEN NIL + ELSE IF ATOM CAMPRE THEN LIST CAMPRE + ELSE VARSINARGS CDR CAMPRE; + +SYMBOLIC PROCEDURE VARSINARGS LISTOFCAMPRE; + BEGIN SCALAR X; + RETURN IF NULL LISTOFCAMPRE THEN NIL + ELSE UNION(LISTOFVARS CAR LISTOFCAMPRE, VARSINARGS CDR LISTOFCAMPRE); + END; + +SYMBOLIC PROCEDURE RND X; + BEGIN SCALAR ANS; + ANS := REVALX X; + IF NOT NUMBERP X THEN REDDERR "RND GIVEN NON-NUMERIC ARGUMENT"; + IF ANS >=0 THEN ANS := FIX(ANS+00.5) + ELSE ANS:= FIX(ANS-0.5); + RETURN ANS + END; + +SYMBOLIC PROCEDURE REVALX U; + % MAKE SURE WE GET TRUE FLOATS IN SYMBOLIC MODE. + IF EQCAR(U,'!:RD!:) THEN RDPREPX U ELSE U; + +SYMBOLIC PROCEDURE RDPREPX U; + IF FLOATP CDR U THEN CDR U ELSE BF2FLR U; + +PAUSE; + +ON ROUNDED; + +PLOT(Y**2, 0, 0.25, 10, 0, 0.25); +PAUSE; + +PLOT((A+1)**2, 0, 0.25, 10, 0, 0.25); +PAUSE; + +B := A*2; + +PLOT(A*B, 0, 0.25, 10, 0, 0.25); +PAUSE; + +COMMENT We leave it as an exercise to write a more elaborate plot +procedure which offers amenities such as automatic scaling, numbered +ordinates, etc. + +Good luck with these exercises, with REDUCE, with computer algebra and +with all of your endeavors. + +;END; Index: r36/announce.tex ================================================================== --- r36/announce.tex +++ r36/announce.tex @@ -1,134 +1,134 @@ - -% From hearn@rand.orgSat Sep 16 16:53:08 1995 -% Date: Fri, 15 Sep 95 10:10:44 -0700 -% From: Tony Hearn -% To: John Fitch , Arthur Norman , -% Winfried Neun -% Subject: Final announcement -% -% I hope this is ok: - -\documentstyle[11pt]{article} -\setlength{\parindent}{0pt} -\setlength{\parskip}{6pt} -\raggedbottom -\setlength{\textwidth}{6.2in} -\setlength{\oddsidemargin}{0.2in} -\setlength{\evensidemargin}{0in} -\setlength{\textheight}{8.7in} -\setlength{\topmargin}{-0.5in} -\newlength{\redboxwidth} -\setlength{\redboxwidth}{4in} -\newcommand{\REDUCE}{REDUCE} -\pagestyle{empty} -\begin{document} -\begin{center} -\fbox{\rule[-0.2cm]{0cm}{0.8cm}{\Large \bf ANNOUNCING REDUCE 3.6}}% - \rule[-0.31cm]{3pt}{1.0cm}\\[-0.6mm] - \hspace*{1pt}\rule{82mm}{3pt}\\[0.2in] -\end{center} - -Version 3.6 of REDUCE is now available for distribution. This is the -first major update since the release of {\REDUCE} 3.5 in October 1993. As -is usual for a new release, a large number of bugs and awkward features -(including those documented in the {\em patches.red} file available from the -REDUCE Network Library) have been corrected. Taken together with the many -new features that have been added, {\REDUCE} 3.6 represents a significant -enhancement over previous versions. - -In addition to the capabilities of the original release of {\REDUCE} 3.5, -this new version supports, among other things: - -\vspace*{-0.1in} -\begin{itemize} -\item {definite integration} -\item {noncommutative Gr\"obner bases} -\item {expanded special function handling} -\item {improved solve capabilities} -\item {improved trigonometric simplification} -\item {linear algebra and linear programming} -\item {matrix normal forms} -\item {operations on sets} -\item {residue computations.} -\end{itemize} - -The {\REDUCE} algebraic mode has been improved substantially since the -last release, and in particular offers improved rule list capabilities, -including free operators, conditional binding of variables and better -matching facilities for quotients. The {\REDUCE} graphics interface has -also been improved. For example, a user is now able to plot an implicitly -defined function. - -A large number of different people are responsible for these improvements. -Other special purpose packages contributed by users include: - -\begin{itemize} -\item {APPLYSYM: Infinitesimal symmetries of differential equations} - -\item {BOOLEAN: Boolean algebra} - -\item {DUMMY: Canonical form of expressions with dummy variables} - -\item {FPS: Calculation of formal power series} - -\item {INVBASE: Computation of involutive bases} - -\item {NCPOLY: Non--commutative polynomial ideals} - -\item {NORMFORM: Computation of matrix normal forms} - -\item {RANDPOLY: A random polynomial generator} - -\item {XCOLOR: Color factor in non-abelian gauge field theories} - -\item {XIDEAL: Gr\"obner Bases for exterior algebra} - -\item {ZEILBERG: Indefinite and definite summation} - -\item{ZTRANS: Calculations with the $Z$ and inverse $Z$ transform.} -\end{itemize} - -Updated documentation includes an improved User's Manual in {\LaTeX} -format, a more detailed online help system for MS/Windows and Unix/X11 -Systems and a bibliography listing over 800 references to REDUCE-related -publications. - -A complete information package is obtainable from: -% \vspace*{-0.1in} -\begin{quote} - REDUCE Secretary \\ - RAND \\ - 1700 Main Street \\ - P.O. Box 2138 \\ - Santa Monica CA 90407-2138 U.S.A. \\ - Telephone: +1-310-393-0411 Ext. 7681 \\ - Facsimile: +1-310-393-4818 \\ - Electronic Mail: reduce@rand.org -\end{quote} -\vspace*{-0.1in} - -If you have e-mail access to the Internet, you can also obtain current -information by sending the message {\em send info-package} to -reduce-netlib@rand.org, reduce-netlib@can.nl or -reduce-netlib@pi.cc.u-tokyo.ac.jp. The single line message can either be -the subject of the message or the body. This message is answered by an -automated server for the REDUCE network library. The library will in time -contain any packages made available since the release of REDUCE 3.6 and -patches to correct any bugs that may be discovered. Further information -on this library, as well as instructions on how to join the REDUCE -electronic forum, can be obtained by including the word {\em help} on a -separate line in the message. - -The same information is available from an Internet gopher server with -the address info.rand.org. The network library files are in a ``REDUCE -Library'' directory under the directory ``Publicly Available Software''. -The relevant URL is gopher://info.rand.org/11/software/reduce . - -A World Wide Web REDUCE server with URL http://www.rrz.uni-koeln.de/REDUCE/ -is also supported. In addition to general information about REDUCE, this -server has pointers to the network library, the demonstration versions, -examples of REDUCE programming, a set of manuals, and the REDUCE online -help system. -\end{document} - + +% From hearn@rand.orgSat Sep 16 16:53:08 1995 +% Date: Fri, 15 Sep 95 10:10:44 -0700 +% From: Tony Hearn +% To: John Fitch , Arthur Norman , +% Winfried Neun +% Subject: Final announcement +% +% I hope this is ok: + +\documentstyle[11pt]{article} +\setlength{\parindent}{0pt} +\setlength{\parskip}{6pt} +\raggedbottom +\setlength{\textwidth}{6.2in} +\setlength{\oddsidemargin}{0.2in} +\setlength{\evensidemargin}{0in} +\setlength{\textheight}{8.7in} +\setlength{\topmargin}{-0.5in} +\newlength{\redboxwidth} +\setlength{\redboxwidth}{4in} +\newcommand{\REDUCE}{REDUCE} +\pagestyle{empty} +\begin{document} +\begin{center} +\fbox{\rule[-0.2cm]{0cm}{0.8cm}{\Large \bf ANNOUNCING REDUCE 3.6}}% + \rule[-0.31cm]{3pt}{1.0cm}\\[-0.6mm] + \hspace*{1pt}\rule{82mm}{3pt}\\[0.2in] +\end{center} + +Version 3.6 of REDUCE is now available for distribution. This is the +first major update since the release of {\REDUCE} 3.5 in October 1993. As +is usual for a new release, a large number of bugs and awkward features +(including those documented in the {\em patches.red} file available from the +REDUCE Network Library) have been corrected. Taken together with the many +new features that have been added, {\REDUCE} 3.6 represents a significant +enhancement over previous versions. + +In addition to the capabilities of the original release of {\REDUCE} 3.5, +this new version supports, among other things: + +\vspace*{-0.1in} +\begin{itemize} +\item {definite integration} +\item {noncommutative Gr\"obner bases} +\item {expanded special function handling} +\item {improved solve capabilities} +\item {improved trigonometric simplification} +\item {linear algebra and linear programming} +\item {matrix normal forms} +\item {operations on sets} +\item {residue computations.} +\end{itemize} + +The {\REDUCE} algebraic mode has been improved substantially since the +last release, and in particular offers improved rule list capabilities, +including free operators, conditional binding of variables and better +matching facilities for quotients. The {\REDUCE} graphics interface has +also been improved. For example, a user is now able to plot an implicitly +defined function. + +A large number of different people are responsible for these improvements. +Other special purpose packages contributed by users include: + +\begin{itemize} +\item {APPLYSYM: Infinitesimal symmetries of differential equations} + +\item {BOOLEAN: Boolean algebra} + +\item {DUMMY: Canonical form of expressions with dummy variables} + +\item {FPS: Calculation of formal power series} + +\item {INVBASE: Computation of involutive bases} + +\item {NCPOLY: Non--commutative polynomial ideals} + +\item {NORMFORM: Computation of matrix normal forms} + +\item {RANDPOLY: A random polynomial generator} + +\item {XCOLOR: Color factor in non-abelian gauge field theories} + +\item {XIDEAL: Gr\"obner Bases for exterior algebra} + +\item {ZEILBERG: Indefinite and definite summation} + +\item{ZTRANS: Calculations with the $Z$ and inverse $Z$ transform.} +\end{itemize} + +Updated documentation includes an improved User's Manual in {\LaTeX} +format, a more detailed online help system for MS/Windows and Unix/X11 +Systems and a bibliography listing over 800 references to REDUCE-related +publications. + +A complete information package is obtainable from: +% \vspace*{-0.1in} +\begin{quote} + REDUCE Secretary \\ + RAND \\ + 1700 Main Street \\ + P.O. Box 2138 \\ + Santa Monica CA 90407-2138 U.S.A. \\ + Telephone: +1-310-393-0411 Ext. 7681 \\ + Facsimile: +1-310-393-4818 \\ + Electronic Mail: reduce@rand.org +\end{quote} +\vspace*{-0.1in} + +If you have e-mail access to the Internet, you can also obtain current +information by sending the message {\em send info-package} to +reduce-netlib@rand.org, reduce-netlib@can.nl or +reduce-netlib@pi.cc.u-tokyo.ac.jp. The single line message can either be +the subject of the message or the body. This message is answered by an +automated server for the REDUCE network library. The library will in time +contain any packages made available since the release of REDUCE 3.6 and +patches to correct any bugs that may be discovered. Further information +on this library, as well as instructions on how to join the REDUCE +electronic forum, can be obtained by including the word {\em help} on a +separate line in the message. + +The same information is available from an Internet gopher server with +the address info.rand.org. The network library files are in a ``REDUCE +Library'' directory under the directory ``Publicly Available Software''. +The relevant URL is gopher://info.rand.org/11/software/reduce . + +A World Wide Web REDUCE server with URL http://www.rrz.uni-koeln.de/REDUCE/ +is also supported. In addition to general information about REDUCE, this +server has pointers to the network library, the demonstration versions, +examples of REDUCE programming, a set of manuals, and the REDUCE online +help system. +\end{document} +  Index: r36/copyrt/release ================================================================== --- r36/copyrt/release +++ r36/copyrt/release @@ -1,60 +1,60 @@ - REDUCE PROGRAM CONTRIBUTION FORM - - -Description of Program Material: - - - - - - - -Principal Author: - - -Organization (if applicable): - - -Postal Address: - - - - - - -Electronic Mail Address: - - -Telephone: - - -Are you the sole author of this software? - - -If not, please write the names of the other authors here and attach their -addresses and telephone numbers. - - - - - - - Acknowledgment and Agreement - -------------- --- --------- - -To the best of my knowledge, I have the right to contribute this program -material without breaching any obligation concerning nondisclosure of -proprietary or confidential information of other persons or organizations. -I am contributing this program material on a nonconfidential, nonobligatory -basis to Anthony C. Hearn ("Hearn") for possible use in the REDUCE algebraic -computation system and its associated program libraries and to Arthur C. -Norman/Codemist Ltd ("Codemist") for possible use in the CSL Lisp system -and associated software. I agree that Hearn and Codemist -may use, duplicate, modify, publish, distribute and market the program -material, and authorize others to do so without obligation or liability of -any kind. They may publish my name and address, as the contributor, to -facilitate user inquiries pertaining to this program material. - - - -Signature ____________________________________ Date __________________ + REDUCE PROGRAM CONTRIBUTION FORM + + +Description of Program Material: + + + + + + + +Principal Author: + + +Organization (if applicable): + + +Postal Address: + + + + + + +Electronic Mail Address: + + +Telephone: + + +Are you the sole author of this software? + + +If not, please write the names of the other authors here and attach their +addresses and telephone numbers. + + + + + + + Acknowledgment and Agreement + -------------- --- --------- + +To the best of my knowledge, I have the right to contribute this program +material without breaching any obligation concerning nondisclosure of +proprietary or confidential information of other persons or organizations. +I am contributing this program material on a nonconfidential, nonobligatory +basis to Anthony C. Hearn ("Hearn") for possible use in the REDUCE algebraic +computation system and its associated program libraries and to Arthur C. +Norman/Codemist Ltd ("Codemist") for possible use in the CSL Lisp system +and associated software. I agree that Hearn and Codemist +may use, duplicate, modify, publish, distribute and market the program +material, and authorize others to do so without obligation or liability of +any kind. They may publish my name and address, as the contributor, to +facilitate user inquiries pertaining to this program material. + + + +Signature ____________________________________ Date __________________ Index: r36/copyrt/submit ================================================================== --- r36/copyrt/submit +++ r36/copyrt/submit @@ -1,44 +1,44 @@ - - INSTRUCTIONS FOR SUBMITTING MATERIAL TO THE REDUCE NETWORK LIBRARY - -We encourage users to send contributions to the REDUCE network library. The -rules are simple, and are designed to increase the effectiveness of the -contribution rather than make more work for the contributor. - -Messages (and also code comments if possible) should be in English. REDUCE -is an international system, used by scientists in many countries who speak -many different languages. The only way to make such a system effective is -to have all dialog in one language, which for obvious reasons is English. - -Lines of code should have a maximum length of 71 characters, and only -contain the symbols listed in the REDUCE User's Manual. Other files -should not contain lines longer than 80 characters. No file should be -more than 100,000 bytes long. This is required so that all known REDUCE -systems can process the code, and electronic mail systems handle the -transmission of the relevant files. - -In the case of a complete package, the following is required: - - 1. A header comment listing - a) the title of the program, - b) the name and address of the author(s), including network address, - c) the date of the program, - d) a brief abstract, - e) the version of REDUCE required, - f) relevant publications, - g) appropriate keywords. - - 2. A separate document file describing the use of the program, preferably - in LaTeX using the style file reduce.sty in the documents directory. - - 3. A test file. This should consist of a sequence of commands that neither - read input nor output to files other than the standard output device. - - 4. A log of the output from running the test file. - - 5. A signed REDUCE Contribution Form giving us rights to the - distribution of the code. - -For smaller code fragments and other material, only the signed form is -needed. This form follows. - + + INSTRUCTIONS FOR SUBMITTING MATERIAL TO THE REDUCE NETWORK LIBRARY + +We encourage users to send contributions to the REDUCE network library. The +rules are simple, and are designed to increase the effectiveness of the +contribution rather than make more work for the contributor. + +Messages (and also code comments if possible) should be in English. REDUCE +is an international system, used by scientists in many countries who speak +many different languages. The only way to make such a system effective is +to have all dialog in one language, which for obvious reasons is English. + +Lines of code should have a maximum length of 71 characters, and only +contain the symbols listed in the REDUCE User's Manual. Other files +should not contain lines longer than 80 characters. No file should be +more than 100,000 bytes long. This is required so that all known REDUCE +systems can process the code, and electronic mail systems handle the +transmission of the relevant files. + +In the case of a complete package, the following is required: + + 1. A header comment listing + a) the title of the program, + b) the name and address of the author(s), including network address, + c) the date of the program, + d) a brief abstract, + e) the version of REDUCE required, + f) relevant publications, + g) appropriate keywords. + + 2. A separate document file describing the use of the program, preferably + in LaTeX using the style file reduce.sty in the documents directory. + + 3. A test file. This should consist of a sequence of commands that neither + read input nor output to files other than the standard output device. + + 4. A log of the output from running the test file. + + 5. A signed REDUCE Contribution Form giving us rights to the + distribution of the code. + +For smaller code fragments and other material, only the signed form is +needed. This form follows. + Index: r36/cslbase/eval1.c ================================================================== --- r36/cslbase/eval1.c +++ r36/cslbase/eval1.c @@ -1,1775 +1,1775 @@ -/* eval1.c Copyright (C) 1989-96 Codemist Ltd */ - -/* - * Interpreter (part 1). - */ - -/* Signature: 47f1cfe1 31-May-1997 */ - -#include -#include -#include - -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "entries.h" -#ifdef TIMEOUT -#include "timeout.h" -#endif - - -Lisp_Object nreverse(Lisp_Object a) -{ - Lisp_Object nil = C_nil; - Lisp_Object b = nil; - while (consp(a)) - { Lisp_Object c = a; - a = qcdr(a); - qcdr(c) = b; - b = c; - } - return b; -} - -/* - * Environments are represented as association lists, and have to cope - * with several sorts of things. The items in an environment can be - * in one of the following forms: - * - * (a) (symbol . value) normal lexical variable binding - * (b) (symbol . ~magic~) given symbol is (locally) special - * (c) (0 . tag) (block tag ...) marker - * (d) (1 . (tag ...)) (tagbody ... tag ...) marker - * (e) (2 . ) case (c) or (d) but now invalidated - * (f) (def . symbol) (flet ...) or (macrolet ...) binding, - * where the def is non-atomic. - * - * Format for def in case (f) - * - * (1) (funarg env bvl ...) flet and labels - * (2) (bvl ...) macrolet - * Note that 'funarg is not valid as a bvl - * and indeed in this case bvl is a list - */ - -/* - * In CSL mode flet, macrolet and local declarations are not supported. - */ - -Lisp_Object Ceval(Lisp_Object u, Lisp_Object env) -{ - Lisp_Object nil = C_nil; -#ifdef COMMON - int t; -#ifdef CHECK_STACK - if (check_stack(__FILE__,__LINE__)) return aerror("deep stack in eval"); -#endif -restart: - t = (int)u & TAG_BITS; -/* - * The first case considered is of symbols - lexical and special bindings - * have to be sorted out. - */ - if (t == TAG_SYMBOL) - { - Header h = qheader(u); - if (h & SYM_SPECIAL_VAR) - { Lisp_Object v = qvalue(u); - if (v == unset_var) return error(1, err_unset_var, u); - else return onevalue(v); - } - else - { - while (env != nil) - { Lisp_Object p = qcar(env); - if (qcar(p) == u) - { Lisp_Object v =qcdr(p); -/* - * If a variable is lexically bound to the value work_symbol that means - * that the symbol has been (lexically) declared to be special, so its - * value cell should be inspected. - */ - if (v == work_symbol) - { v = qvalue(u); - if (v == unset_var) return error(1, err_unset_var, u); - } - return onevalue(v); - } - env = qcdr(env); - } -#ifdef ARTHURS_ORIGINAL_INTERPRETATION - return error(1, err_unbound_lexical, u); -#else - { Lisp_Object v = qvalue(u); - if (v == unset_var) return error(1, err_unset_var, u); - else return onevalue(v); - } -#endif - } - } -/* - * Things that are neither symbols nor lists evaluate to themselves, - * e.g. numbers and vectors. - */ - else if (t != TAG_CONS) return onevalue(u); - else -#endif /* COMMON */ - { -/* - * The final case is that of a list (fn ...), and one case that has to - * be checked is if fn is lexically bound. - */ - Lisp_Object fn, args; -#ifdef COMMON -/* - * The test for nil here is because although nil is a symbol the tagging - * structure tested here marks it as a list. - */ - if (u == nil) return onevalue(nil); -#endif - stackcheck2(0, u, env); - fn = qcar(u); - args = qcdr(u); -#ifdef COMMON -/* - * Local function bindings must be looked for first. - */ - { Lisp_Object p; - for (p=env; p!=nil; p=qcdr(p)) - { Lisp_Object w = qcar(p); -/* - * The form ( . sym) is used in an environment to indicate a local - * binding of a function, either as a regular function or as a macro - * (i.e. flet or macrolet). The structure of the list distinguishes - * between these two cases. - */ - if (qcdr(w) == fn && is_cons(w = qcar(w)) && w!=nil) - { - p = qcar(w); - if (p == funarg) /* ordinary function */ - { fn = w; /* (funarg ...) is OK to apply */ - goto ordinary_function; - } -/* - * Here it is a local macro. Observe that the macroexpansion is done - * with respect to an empty environment. Macros that are defined at the same - * time may seem to be mutually recursive but there is a sense in which they - * are not (as well as a sense in which they are) - self and cross references - * only happen AFTER an expansion and can not happen during one. - */ - push2(u, env); - w = cons(lambda, w); - nil = C_nil; - if (!exception_pending()) - p = Lfuncalln(nil, 4, qvalue(macroexpand_hook), - w, u, nil); - pop2(env, u); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - if ((exit_reason & UNWIND_ERROR) != 0) - { err_printf("\nMacroexpanding: "); - loop_print_error(u); - nil = C_nil; - if (exception_pending()) flip_exception(); - } - flip_exception(); - return nil; - } - u = p; - goto restart; - } - } - } -#endif - if (is_symbol(fn)) - { -/* - * Special forms and macros are checked for next. Special forms - * take precedence over macros. - */ - Header h = qheader(fn); - if (h & SYM_SPECIAL_FORM) - { Lisp_Object v; -#ifdef DEBUG - if (qfn1(fn) == NULL) - { term_printf("Illegal special form\n"); - my_exit(EXIT_FAILURE); - } -#endif - v = ((Special_Form *)qfn1(fn))(args, env); - return v; - } - else if (h & SYM_MACRO) - { - push2(u, env); -/* - * the environment passed to macroexpand should only be needed to cope - * with macrolet, I think. Since I use just one datastructure for the - * whole environment I also pass along lexical bindings etc, but I hope that - * they will never be accessed. I do not think that macrolet is important - * enough to call for complication and slow-down in the interpreter this - * way - but then I am not exactly what you would call a Common Lisp Fan! - */ - fn = macroexpand(u, env); - pop2(env, u); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - if ((exit_reason & UNWIND_ERROR) != 0) - { err_printf("\nMacroexpanding: "); - loop_print_error(u); - nil = C_nil; - if (exception_pending()) flip_exception(); - } - flip_exception(); - return nil; - } - return eval(fn, env); - } - } -/* - * Otherwise we have a regular function call. I prepare the args and - * call APPLY. - */ -#ifdef COMMON -ordinary_function: -#endif - { int nargs = 0; - Lisp_Object *save_stack = stack; -/* - * Args are built up on the stack here... - */ - while (consp(args)) - { Lisp_Object w; - push3(fn, args, env); - w = qcar(args); - w = eval(w, env); - pop3(env, args, fn); -/* - * nil having its mark bit set indicates that a special sort of exit - * is in progress. Multiple values can be ignored in this case. - */ - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack = save_stack; - if ((exit_reason & UNWIND_ERROR) != 0) - { err_printf("\nEvaluating: "); - loop_print_error(qcar(args)); - nil = C_nil; - if (exception_pending()) flip_exception(); - } - flip_exception(); - return nil; - } - push(w); /* args build up on the Lisp stack */ - nargs++; - args = qcdr(args); - } - -/* - * I pass the environment down to apply() because it will be used if the - * function was a simple lambda expression. If the function is a symbol - * or a closure, env will be irrelevant. The arguments are on the Lisp - * stack, and it is the responsibility of apply() to pop them. - */ - return apply(fn, nargs, env, fn); - } - } -} - -#ifdef COMMON -/* - * Keyword arguments are not supported in CSL mode - but &optional - * and &rest and &aux will be (at least for now). Removal of - * support for keywords will save a little space and an even smaller - * amount of time. - */ - -static bool check_no_unwanted_keys(Lisp_Object restarg, Lisp_Object ok_keys) -/* - * verify that there were no unwanted keys in the actual arg list - */ -{ - Lisp_Object nil = C_nil; - bool odd_key_found = NO; - while (restarg!=nil) - { Lisp_Object k = qcar(restarg); - Lisp_Object w; - for (w=ok_keys; w!=nil; w=qcdr(w)) - if (k == qcar(w)) goto is_ok; - odd_key_found = YES; - is_ok: - restarg = qcdr(restarg); - if (restarg==nil) return YES; /* odd length list */ - if (k == allow_key_key && qcar(restarg) != nil) return NO; /* OK */ - restarg = qcdr(restarg); - } - return odd_key_found; -} - -static bool check_keyargs_even(Lisp_Object restarg) -/* - * check that list is even length with alternate items symbols in - * the keyword package. - */ -{ - Lisp_Object nil = C_nil; - while (restarg!=nil) - { Lisp_Object q = qcar(restarg); - if (!is_symbol(q) || qpackage(q) != qvalue(keyword_package)) return YES; - restarg = qcdr(restarg); - if (restarg==nil) return YES; /* Odd length is wrong */ - restarg = qcdr(restarg); - } - return NO; /* OK */ -} - -static Lisp_Object keywordify(Lisp_Object v) -{ -/* - * arg is a non-nil symbol. Should nil be permitted - I think not - * since there seems too much chance of confusion. - */ - Lisp_Object nil, name = get_pname(v); - errexit(); - return Lintern_2(nil, name, qvalue(keyword_package)); -} - -static Lisp_Object key_lookup(Lisp_Object keyname, Lisp_Object args) -{ - Lisp_Object nil = C_nil; - while (args!=nil) - { Lisp_Object next = qcdr(args); - if (next==nil) return nil; - if (qcar(args) == keyname) return next; - else args = qcdr(next); - } - return nil; -} - -#endif - -Lisp_Object apply_lambda(Lisp_Object def, int nargs, - Lisp_Object env, Lisp_Object name) -/* - * Here def is a lambda expression (sans the initial lambda) that is to - * be applied. Much horrible messing about is needed so that I can cope - * with &optional and &rest args (including initialisers and supplied-p - * variables, also &key, &allow-other-keys and &aux). Note the need to find - * any special declarations at the head of the body of the lambda-form. - * Must pop (nargs) items from the stack at exit. - */ -{ -/* - * lambda-lists are parsed using a finite state engine with the - * following states, plus an exit state. - */ -#define STATE_NULL 0 /* at start and during regular args */ -#define STATE_OPT 1 /* after &optional */ -#define STATE_OPT1 2 /* after &optional + at least one var */ -#define STATE_REST 3 /* immediately after &rest */ -#define STATE_REST1 4 /* after &rest vv */ -#ifdef COMMON -#define STATE_KEY 5 /* &key with no &rest */ -#define STATE_ALLOW 6 /* &allow-other-keys */ -#endif -#define STATE_AUX 7 /* &aux */ - - Lisp_Object nil = C_nil; - int opt_rest_state = STATE_NULL; - Lisp_Object *next_arg; - int args_left = nargs; - Lisp_Object w; - if (!consp(def)) - { popv(nargs); - return onevalue(nil); /* Should never happen */ - } - stackcheck3(0, def, env, name); - w = qcar(def); - next_arg = &stack[1-nargs]; /* Points to arg1 */ - push4(w, /* bvl */ - qcdr(def), /* body */ - env, name); -/* - * Here I need to macroexpand the first few items in body and - * look for declare/special items. I will only bother with SPECIAL decls. - * Note that args have been pushed onto the stack first to avoid corruption - * while the interpreter performs macroexpansion. This is the sort of place - * where I feel that Common Lisp has built in causes of inefficiency. - * Well oh well!!! The Common Lisp standardisation group thought so too, - * and have now indicated that DECLARE forms can not be hidden away as - * the result of macros, so some of this is unnecessary. - */ - push5(nil, nil, /* local_decs, ok_keys */ - nil, nil, nil); /* restarg, specenv, val1 */ - push5(nil, nil, /* arg, v1 */ - nil, nil, nil); /* v, p, w */ -/* - * On computers which have unsigned offsets in indexed memory reference - * instructions the negative indexes off the stack suggested here might - * be more expensive than I would like - maybe on such machines the stack - * pointer should be kept offset by 64 bytes (say). Doing so in general - * would be to the disadvantage of machines with auto-index address modes - * that might be used when pushing/popping single items on the stack. - */ -#define w stack[0] -#define p stack[-1] -#define v stack[-2] -#define v1 stack[-3] -#define arg stack[-4] -#define val1 stack[-5] -#define specenv stack[-6] -#define restarg stack[-7] -#ifdef COMMON -#define ok_keys stack[-8] -#define local_decs stack[-9] -#endif -#define name stack[-10] -#define env stack[-11] -#define body stack[-12] -#define bvl stack[-13] -#define arg1 stack[-14] -#define stack_used ((int)(nargs + 14)) - -#ifdef COMMON - for (;;) - { if (!consp(body)) break; - p = macroexpand(qcar(body), env); - nil = C_nil; - if (exception_pending()) - { Lisp_Object qname = name; - popv(stack_used); - return qname; - } - body = qcdr(body); - if (!consp(p)) - { if (stringp(p) && consp(body)) continue; - body = cons(p, body); - break; - } - if (qcar(p) != declare_symbol) - { body = cons(p, body); - break; - } - for (v = qcdr(v); consp(v); v = qcdr(v)) - { v1 = qcar(v); - if (!consp(v1) || qcar(v1) != special_symbol) continue; - /* here v1 says (special ...) */ - for (v1=qcdr(v1); consp(v1); v1 = qcdr(v1)) - { local_decs = cons(qcar(v1), local_decs); - if (exception_pending()) break; - } - } - } - nil = C_nil; - if (exception_pending()) - { Lisp_Object qname = name; - popv(stack_used); - return qname; - } -#endif -/* - * Parse the BVL - */ - for (p = bvl; consp(p); p=qcdr(p)) - { v = qcar(p); - v1 = nil; - arg = nil; - val1 = nil; -/* - * I can break from this switch statement with v a variable to bind - * and arg the value to bind to it, also v1 (if not nil) is a second - * variable to be bound (a supplied-p value) and val1 the value to bind it to. - * If I see &rest or &key the remaining actual args get collected into - * restarg, which takes the place of arg in some respects. - */ - switch (opt_rest_state) - { - - case STATE_NULL: - if (v == opt_key) - { opt_rest_state = STATE_OPT; - continue; - } - -#define BAD1(msg) { error(0, msg); goto unwind_special_bindings; } -#define BAD2(msg, a) { error(1, msg, a); goto unwind_special_bindings; } - -#define collect_rest_arg() \ - while (args_left-- != 0) \ - { if (!exception_pending()) \ - restarg = cons(next_arg[args_left], restarg); \ - nil = C_nil; \ - } - - if (v == rest_key) - { collect_rest_arg(); - if (exception_pending()) goto unwind_special_bindings; - opt_rest_state = STATE_REST; - continue; - } -#ifdef COMMON - if (v == key_key) - { collect_rest_arg(); - if (exception_pending()) goto unwind_special_bindings; - if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); - opt_rest_state = STATE_KEY; - continue; - } - - if (v == aux_key) - { if (args_left != 0) BAD1(err_excess_args); - opt_rest_state = STATE_AUX; - continue; - } - if (v == allow_other_keys) BAD2(err_bad_bvl, v); -#endif - if (args_left == 0) BAD1(err_insufficient_args); - arg = *next_arg++; - args_left--; - v1 = nil; /* no suppliedp mess here, I'm glad to say */ - break; - - case STATE_OPT: - if (v == opt_key - || v == rest_key -#ifdef COMMON - || v == key_key - || v == allow_other_keys - || v == aux_key -#endif - ) BAD2(err_bad_bvl, v); -/* - * Here v may be a simple variable, or a list (var init suppliedp) - */ - opt_rest_state = STATE_OPT1; -process_optional_parameter: - if (args_left != 0) - { arg = *next_arg++; - args_left--; - val1 = lisp_true; - } - else - { arg = nil; - val1 = nil; - } - v1 = nil; - if (!consp(v)) break; /* Simple case */ - { w = qcdr(v); - v = qcar(v); - if (!consp(w)) break; /* (var) */ - if (val1 == nil) /* use the init form */ - { arg = qcar(w); - arg = eval(arg, env); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - } - w = qcdr(w); - if (consp(w)) v1 = qcar(w); /* suppliedp name */ - break; - } - - case STATE_OPT1: - if (v == rest_key) - { collect_rest_arg(); - if (exception_pending()) goto unwind_special_bindings; - opt_rest_state = STATE_REST; - continue; - } -#ifdef COMMON - if (v == key_key) - { collect_rest_arg(); - if (exception_pending()) goto unwind_special_bindings; - if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); - opt_rest_state = STATE_KEY; - continue; - } - if (v == aux_key) - { if (args_left != 0) BAD1(err_excess_args); - opt_rest_state = STATE_AUX; - continue; - } -#endif - if (v == opt_key -#ifdef COMMON - || v == allow_other_keys -#endif - ) BAD2(err_bad_bvl, v); - goto process_optional_parameter; - - case STATE_REST: - if (v == opt_key - || v == rest_key -#ifdef COMMON - || v == key_key - || v == allow_other_keys - || v == aux_key -#endif - ) BAD2(err_bad_bvl, v); - opt_rest_state = STATE_REST1; - arg = restarg; - break; - - case STATE_REST1: -#ifdef COMMON - if (v == key_key) - { if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); - opt_rest_state = STATE_KEY; - continue; - } - if (v == aux_key) - { - opt_rest_state = STATE_AUX; - continue; - } -#endif - BAD2(err_bad_bvl, rest_key); - -#ifdef COMMON - case STATE_KEY: - if (v == allow_other_keys) - { opt_rest_state = STATE_ALLOW; - continue; - } - if (v == aux_key) - { if (check_no_unwanted_keys(restarg, ok_keys)) - BAD2(err_bad_keyargs, restarg); - opt_rest_state = STATE_AUX; - continue; - } - if (v == opt_key || v == rest_key || v == key_key) - BAD2(err_bad_bvl, v); -process_keyword_parameter: -/* - * v needs to expand to ((:kv v) init svar) in effect here. - */ - { Lisp_Object keyname = nil; - w = nil; - if (!consp(v)) - { if (!is_symbol(v)) BAD2(err_bad_bvl, v); - keyname = keywordify(v); - } - else - { w = qcdr(v); - v = qcar(v); - if (!consp(v)) - { if (!is_symbol(v)) BAD2(err_bad_bvl, v); - keyname = keywordify(v); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - } - else - { keyname = qcar(v); - if (!is_symbol(keyname)) BAD2(err_bad_bvl, v); - keyname = keywordify(keyname); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - v = qcdr(v); - if (consp(v)) v = qcar(v); - else BAD2(err_bad_bvl, v); - } - } - ok_keys = cons(keyname, ok_keys); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - arg = key_lookup(qcar(ok_keys), restarg); - if (arg == nil) val1 = nil; - else - { arg = qcar(arg); - val1 = lisp_true; - } - v1 = nil; - if (!consp(w)) break; /* (var) */ - if (val1 == nil) /* use the init form */ - { arg = qcar(w); - arg = eval(arg, env); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - } - w = qcdr(w); - if (consp(w)) v1 = qcar(w); /* suppliedp name */ - break; - } - - case STATE_ALLOW: - if (v == aux_key) - { opt_rest_state = STATE_AUX; - continue; - } - if (v == opt_key || v == rest_key || v == key_key || - v == allow_other_keys) BAD2(err_bad_bvl, v); - goto process_keyword_parameter; - - case STATE_AUX: - if (v == opt_key || v == rest_key || - v == key_key || v == allow_other_keys || - v == aux_key) BAD2(err_bad_bvl, v); - if (consp(v)) - { w = qcdr(v); - v = qcar(v); - if (consp(w)) - { arg = qcar(w); - arg = eval(arg, env); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - } - } - else arg = nil; - v1 = nil; - break; -#endif - } -/* - * This is where I get when I have one or two vars to bind. - */ - -#ifndef COMMON -/* - * CSL mode does not have to mess about looking for local special bindings - * and so is MUCH shorter and neater. I always shallow bind - */ -#define instate_binding(var, val, local_decs1, lab) \ - { if (!is_symbol(var)) BAD2(err_bad_bvl, var); \ - w = acons(var, qvalue(var), specenv); \ - nil = C_nil; \ - if (exception_pending()) goto unwind_special_bindings; \ - specenv = w; \ - qvalue(var) = val; \ - } -#else -#define instate_binding(var, val, local_decs1, lab) \ - { Header h; \ - if (!is_symbol(var)) BAD2(err_bad_bvl, var); \ - h = qheader(var); \ - if ((h & SYM_SPECIAL_VAR) != 0) \ - { w = acons(var, qvalue(var), specenv); \ - nil = C_nil; \ - if (exception_pending()) goto unwind_special_bindings; \ - specenv = w; \ - qvalue(var) = val; \ - } \ - else \ - { for (w = local_decs1; w!=nil; w = qcdr(w)) \ - { if (qcar(w) == var) \ - { qcar(w) = fixnum_of_int(0);/* decl is used up */\ - w = acons(var, work_symbol, env); \ - nil = C_nil; \ - if (exception_pending()) \ - goto unwind_special_bindings; \ - env = w; \ - w = acons(var, qvalue(var), specenv); \ - nil = C_nil; \ - if (exception_pending()) \ - goto unwind_special_bindings; \ - specenv = w; \ - qvalue(var) = val; \ - goto lab; \ - } \ - } \ - w = acons(var, val, env); \ - nil = C_nil; \ - if (exception_pending()) goto unwind_special_bindings; \ - env = w; \ - lab: ; \ - } \ - } -#endif - -#ifdef COMMON -/* - * Must check about local special declarations here... - */ -#endif - instate_binding(v, arg, local_decs, label1); - if (v1 != nil) instate_binding(v1, val1, local_decs, label2); - - } /* End of for loop that scans BVL */ - -#ifdef COMMON -/* - * As well as local special declarations that have applied to bindings here - * there can be some that apply just to variable references within the body. - */ - while (local_decs!=nil) - { Lisp_Object q = qcar(local_decs); - local_decs=qcdr(local_decs); - if (!is_symbol(q)) continue; - w = acons(q, work_symbol, env); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - env = w; - } -#endif - - switch (opt_rest_state) - { -case STATE_NULL: -case STATE_OPT1: /* Ensure there had not been too many args */ - if (args_left != 0) BAD1(err_excess_args); - break; - -case STATE_OPT: /* error if bvl finishes here */ -case STATE_REST: - BAD2(err_bad_bvl, opt_rest_state == STATE_OPT ? opt_key : rest_key); - -#ifdef COMMON -case STATE_KEY: /* ensure only valid keys were given */ - if (check_no_unwanted_keys(restarg, ok_keys)) - BAD2(err_bad_keyargs, restarg); - break; -#endif - -default: -/* in the following cases all is known to be well -case STATE_REST1: -case STATE_ALLOW: -case STATE_AUX: -*/ - break; - } - -/* - * Now all the argument bindings have been performed - it remains to - * process the body of the lambda-expression. - */ - if (specenv == nil) - { Lisp_Object bodyx = body, envx = env; - Lisp_Object qname = name; - popv(stack_used); - push(qname); - bodyx = progn_fn(bodyx, envx); - pop(qname); - nil = C_nil; - if (exception_pending()) return qname; - return bodyx; - } - { body = progn_fn(body, env); - nil = C_nil; - if (exception_pending()) goto unwind_special_bindings; - while (specenv != nil) - { - Lisp_Object bv = qcar(specenv); - qvalue(qcar(bv)) = qcdr(bv); - specenv = qcdr(specenv); - } - { Lisp_Object bodyx = body; - popv(stack_used); -/* - * note that exit_count has not been disturbed since I called progn_fn, - * so the numbert of values that will be returned remains correctly - * established (in Common Lisp mode where it is needed. - */ - return bodyx; - } - } - -unwind_special_bindings: -/* - * I gete here ONLY if nil has its mark bit set, which means that (for - * one reason or another) I am having to unwind the stack, restoring - * special bindings as I go. - */ - nil = C_nil; - flip_exception(); - while (specenv != nil) - { Lisp_Object bv = qcar(specenv); - qvalue(qcar(bv)) = qcdr(bv); - specenv = qcdr(specenv); - } - flip_exception(); - { Lisp_Object qname = name; - popv(stack_used); - return qname; - } -#undef w -#undef p -#undef v -#undef v1 -#undef arg -#undef val1 -#undef specenv -#undef restarg -#undef ok_keys -#undef local_decs -#undef name -#undef env -#undef body -#undef bvl -#undef stack_used -} - -Lisp_Object Leval(Lisp_Object nil, Lisp_Object a) -{ - return eval(a, nil); /* Multiple values may be returned */ -} - -Lisp_Object Levlis(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object r; - stackcheck1(0, a); - r = nil; - while (consp(a)) - { push2(qcdr(a), r); - a = qcar(a); - a = eval(a, nil); - errexitn(2); - pop(r); - r = cons(a, r); - pop(a); - errexit(); - } - return onevalue(nreverse(r)); -} - -Lisp_Object MS_CDECL Lapply_n(Lisp_Object nil, int nargs, ...) -{ - va_list a; - int i; - Lisp_Object *stack_save = stack, last, fn; - if (nargs == 0) return aerror("apply"); - if (nargs > 1) - { va_start(a, nargs); - fn = va_arg(a, Lisp_Object); - push_args_1(a, nargs); - pop(last); - i = nargs-2; - while (consp(last)) - { push(qcar(last)); - last = qcdr(last); - i++; - } - } - else i = 0; - stackcheck1(stack-stack_save, fn); - return apply(fn, i, nil, fn); -} - -Lisp_Object Lapply_1(Lisp_Object nil, Lisp_Object fn) -{ - return Lapply_n(nil, 1, fn); -} - -Lisp_Object Lapply_2(Lisp_Object nil, Lisp_Object fn, Lisp_Object a1) -{ - return Lapply_n(nil, 2, fn, a1); -} - -Lisp_Object Lapply0(Lisp_Object nil, Lisp_Object fn) -{ - if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 0); - stackcheck1(0, fn); - return apply(fn, 0, C_nil, fn); -} - -Lisp_Object Lapply1(Lisp_Object nil, Lisp_Object fn, Lisp_Object a) -{ - if (is_symbol(fn)) return (*qfn1(fn))(qenv(fn), a); - push(a); - stackcheck1(1, fn); - return apply(fn, 1, C_nil, fn); -} - -Lisp_Object MS_CDECL Lapply2(Lisp_Object nil, int nargs, ...) -{ - va_list aa; - Lisp_Object fn, a, b; - argcheck(nargs, 3, "apply2"); - va_start(aa, nargs); - fn = va_arg(aa, Lisp_Object); - a = va_arg(aa, Lisp_Object); - b = va_arg(aa, Lisp_Object); - va_end(aa); - if (is_symbol(fn)) return (*qfn2(fn))(qenv(fn), a, b); - push2(a, b); - stackcheck1(2, fn); - return apply(fn, 2, C_nil, fn); -} - -Lisp_Object MS_CDECL Lapply3(Lisp_Object nil, int nargs, ...) -{ - va_list aa; - Lisp_Object fn, a, b, c; - argcheck(nargs, 4, "apply3"); - va_start(aa, nargs); - fn = va_arg(aa, Lisp_Object); - a = va_arg(aa, Lisp_Object); - b = va_arg(aa, Lisp_Object); - c = va_arg(aa, Lisp_Object); - va_end(aa); - if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 3, a, b, c); - push3(a, b, c); - stackcheck1(3, fn); - return apply(fn, 3, C_nil, fn); -} - -Lisp_Object Lfuncall1(Lisp_Object nil, Lisp_Object fn) -{ - if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 0); - stackcheck1(0, fn); - return apply(fn, 0, nil, fn); -} - -Lisp_Object Lfuncall2(Lisp_Object nil, Lisp_Object fn, Lisp_Object a1) -{ - if (is_symbol(fn)) return (*qfn1(fn))(qenv(fn), a1); - push(a1); - stackcheck1(1, fn); - return apply(fn, 1, nil, fn); -} - -static Lisp_Object MS_CDECL Lfuncalln_sub(Lisp_Object nil, int nargs, va_list a) -{ - Lisp_Object *stack_save = stack, fn; - fn = va_arg(a, Lisp_Object); - push_args_1(a, nargs); - stackcheck1(stack-stack_save, fn); - return apply(fn, nargs-1, nil, fn); -} - -Lisp_Object MS_CDECL Lfuncalln(Lisp_Object nil, int nargs, ...) -{ - va_list a; - Lisp_Object fn, a1, a2, a3, a4; - va_start(a, nargs); - switch (nargs) - { -case 0: return aerror("funcall"); -case 1: /* cases 1 and 2 should go through Lfuncall1,2 not here */ -case 2: return aerror("funcall wrong call"); -case 3: fn = va_arg(a, Lisp_Object); - a1 = va_arg(a, Lisp_Object); - a2 = va_arg(a, Lisp_Object); - if (is_symbol(fn)) return (*qfn2(fn))(qenv(fn), a1, a2); - push2(a1, a2); - return apply(fn, 2, nil, fn); -case 4: fn = va_arg(a, Lisp_Object); - a1 = va_arg(a, Lisp_Object); - a2 = va_arg(a, Lisp_Object); - a3 = va_arg(a, Lisp_Object); - if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 3, a1, a2, a3); - push3(a1, a2, a3); - return apply(fn, 3, nil, fn); -case 5: fn = va_arg(a, Lisp_Object); - a1 = va_arg(a, Lisp_Object); - a2 = va_arg(a, Lisp_Object); - a3 = va_arg(a, Lisp_Object); - a4 = va_arg(a, Lisp_Object); - if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 4, a1, a2, a3, a4); - push4(a1, a2, a3, a4); - return apply(fn, 4, nil, fn); -default: - return Lfuncalln_sub(nil, nargs, a); - } -} - -#ifdef COMMON - -Lisp_Object MS_CDECL Lvalues(Lisp_Object nil, int nargs, ...) -{ - va_list a; - Lisp_Object *p = &mv_2, w; - int i; -/* - * Because multiple-values get passed back in static storage there is - * a fixed upper limit to how many I can handle - truncate here to allow - * for that. - */ - if (nargs > 50) nargs = 50; - if (nargs == 0) return nvalues(nil, 0); - va_start(a, nargs); - push_args(a, nargs); - for (i=1; i nil */ - stackcheck2(0, args, env); - push2(args, env); - fn = qcar(args); - fn = eval(fn, env); - pop2(env, args); - errexit(); - args = qcdr(args); - while (consp(args)) - { Lisp_Object r1; - push2(args, env); - r1 = qcar(args); - r1 = eval(r1, env); - nil = C_nil; - if (exception_pending()) - { stack = stack_save; - return nil; - } -/* - * It is critical here that push does not check for stack overflow and - * thus can not call the garbage collector, or otherwise lead to calculation - * that could possibly clobber the multiple results that I am working with - * here. - */ - pop2(env, args); - push(r1); - i++; - for (j = 2; j<=exit_count; j++) - { push((&work_0)[j]); - i++; - } - args = qcdr(args); - } - stackcheck2(stack-stack_save, fn, env); - return apply(fn, i, env, fn); -} - -#endif - -Lisp_Object interpreted1(Lisp_Object def, Lisp_Object a1) -{ - Lisp_Object nil = C_nil; - push(a1); - stackcheck1(1, def); - return apply_lambda(def, 1, nil, def); -} - -Lisp_Object interpreted2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) -{ - Lisp_Object nil = C_nil; - push2(a1, a2); - stackcheck1(2, def); - return apply_lambda(def, 2, nil, def); -} - -Lisp_Object MS_CDECL interpretedn(Lisp_Object def, int nargs, ...) -{ -/* - * The messing about here is to get the (unknown number of) args - * into a nice neat vector so that they can be indexed into. If I knew - * that the args were in consecutive locations on the stack I could - * probably save a copying operation. - */ - Lisp_Object nil = C_nil; - Lisp_Object *stack_save = stack; - va_list a; - if (nargs != 0) - { va_start(a, nargs); - push_args(a, nargs); - } - stackcheck1(stack-stack_save, def); - return apply_lambda(def, nargs, nil, def); -} - -Lisp_Object funarged1(Lisp_Object def, Lisp_Object a1) -{ - Lisp_Object nil = C_nil; - push(a1); - stackcheck1(1, def); - return apply_lambda(qcdr(def), 1, qcar(def), qcdr(def)); -} - -Lisp_Object funarged2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) -{ - Lisp_Object nil = C_nil; - push2(a1, a2); - stackcheck1(2, def); - return apply_lambda(qcdr(def), 2, qcar(def), qcdr(def)); -} - -Lisp_Object MS_CDECL funargedn(Lisp_Object def, int nargs, ...) -{ - Lisp_Object nil = C_nil; - Lisp_Object *stack_save = stack; - va_list a; - if (nargs != 0) - { va_start(a, nargs); - push_args(a, nargs); - } - stackcheck1(stack-stack_save, def); - return apply_lambda(qcdr(def), nargs, qcar(def), qcdr(def)); -} - -/* - * Now some execution-doubling versions... - */ - -Lisp_Object double_interpreted1(Lisp_Object def, Lisp_Object a1) -{ - Lisp_Object nil = C_nil; - push(a1); - stackcheck1(1, def); - return apply_lambda(def, 1, nil, def); -} - -Lisp_Object double_interpreted2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) -{ - Lisp_Object nil = C_nil; - push2(a1, a2); - stackcheck1(2, def); - return apply_lambda(def, 2, nil, def); -} - -Lisp_Object MS_CDECL double_interpretedn(Lisp_Object def, int nargs, ...) -{ -/* - * The messing about here is to get the (unknown number of) args - * into a nice neat vector so that they can be indexed into. If I knew - * that the args were in consecutive locations on the stack I could - * probably save a copying operation. - */ - Lisp_Object nil = C_nil; - Lisp_Object *stack_save = stack; - va_list a; - if (nargs != 0) - { va_start(a, nargs); - push_args(a, nargs); - } - stackcheck1(stack-stack_save, def); - return apply_lambda(def, nargs, nil, def); -} - -Lisp_Object double_funarged1(Lisp_Object def, Lisp_Object a1) -{ - Lisp_Object nil = C_nil; - push(a1); - stackcheck1(1, def); - return apply_lambda(qcdr(def), 1, qcar(def), qcdr(def)); -} - -Lisp_Object double_funarged2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) -{ - Lisp_Object nil = C_nil; - push2(a1, a2); - stackcheck1(2, def); - return apply_lambda(qcdr(def), 2, qcar(def), qcdr(def)); -} - -Lisp_Object MS_CDECL double_funargedn(Lisp_Object def, int nargs, ...) -{ - Lisp_Object nil = C_nil; - Lisp_Object *stack_save = stack; - va_list a; - if (nargs != 0) - { va_start(a, nargs); - push_args(a, nargs); - } - stackcheck1(stack-stack_save, def); - return apply_lambda(qcdr(def), nargs, qcar(def), qcdr(def)); -} - -int trace_depth = 0; - -static void trace_entering(char *s) -{ - int i; - for (i=0; i0)", env); - return (*qfnn(env))(qenv(env), 0); -} - -Lisp_Object f1_as_0(Lisp_Object env, Lisp_Object a) -{ - return (*qfnn(env))(qenv(env), 0); -} - -Lisp_Object f2_as_0(Lisp_Object env, Lisp_Object a, Lisp_Object b) -{ - return (*qfnn(env))(qenv(env), 0); -} - -Lisp_Object MS_CDECL f3_as_0(Lisp_Object env, int nargs, ...) -{ - if (nargs != 3) return aerror1("wrong number of args (3->0)", env); - return (*qfnn(env))(qenv(env), 0); -} - -Lisp_Object f1_as_1(Lisp_Object env, Lisp_Object a) -{ - return (*qfn1(env))(qenv(env), a); -} - -Lisp_Object f2_as_1(Lisp_Object env, Lisp_Object a, Lisp_Object b) -{ - return (*qfn1(env))(qenv(env), a); -} - -Lisp_Object MS_CDECL f3_as_1(Lisp_Object env, int nargs, ...) -{ - va_list a; - Lisp_Object a1; - if (nargs != 3) return aerror1("wrong number of args (3->1)", env); - va_start(a, nargs); - a1 = va_arg(a, Lisp_Object); - va_end(a); - return (*qfn1(env))(qenv(env), a1); -} - -Lisp_Object f2_as_2(Lisp_Object env, Lisp_Object a, Lisp_Object b) -{ - return (*qfn2(env))(qenv(env), a, b); -} - -Lisp_Object MS_CDECL f3_as_2(Lisp_Object env, int nargs, ...) -{ - va_list a; - Lisp_Object a1, a2; - if (nargs != 3) return aerror1("wrong number of args (3->2)", env); - va_start(a, nargs); - a1 = va_arg(a, Lisp_Object); - a2 = va_arg(a, Lisp_Object); - va_end(a); - return (*qfn2(env))(qenv(env), a1, a2); -} - -Lisp_Object MS_CDECL f3_as_3(Lisp_Object env, int nargs, ...) -{ - va_list a; - Lisp_Object a1, a2, a3; - if (nargs != 3) return aerror1("wrong number of args (3->3)", env); - va_start(a, nargs); - a1 = va_arg(a, Lisp_Object); - a2 = va_arg(a, Lisp_Object); - a3 = va_arg(a, Lisp_Object); - va_end(a); - return (*qfnn(env))(qenv(env), 3, a1, a2, a3); -} - -setup_type const eval1_setup[] = -{ - {"bytecounts", wrong_no_na, wrong_no_nb, bytecounts}, - {"apply", Lapply_1, Lapply_2, Lapply_n}, - {"apply0", Lapply0, too_many_1, wrong_no_1}, - {"apply1", too_few_2, Lapply1, wrong_no_2}, - {"apply2", wrong_no_na, wrong_no_nb, Lapply2}, - {"apply3", wrong_no_na, wrong_no_nb, Lapply3}, - {"evlis", Levlis, too_many_1, wrong_no_1}, - {"funcall", Lfuncall1, Lfuncall2, Lfuncalln}, - {"funcall*", Lfuncall1, Lfuncall2, Lfuncalln}, -#ifdef COMMON - {"values", Lvalues_1, Lvalues_2, Lvalues}, - {"macroexpand", Lmacroexpand, Lmacroexpand_2, wrong_no_1}, - {"macroexpand-1", Lmacroexpand_1, Lmacroexpand_1_2, wrong_no_1}, -#else - {"macroexpand", Lmacroexpand, too_many_1, wrong_no_1}, - {"macroexpand-1", Lmacroexpand_1, too_many_1, wrong_no_1}, -#endif - {NULL, 0, 0, 0} -}; - -/* end of eval1.c */ - +/* eval1.c Copyright (C) 1989-96 Codemist Ltd */ + +/* + * Interpreter (part 1). + */ + +/* Signature: 47f1cfe1 31-May-1997 */ + +#include +#include +#include + +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "entries.h" +#ifdef TIMEOUT +#include "timeout.h" +#endif + + +Lisp_Object nreverse(Lisp_Object a) +{ + Lisp_Object nil = C_nil; + Lisp_Object b = nil; + while (consp(a)) + { Lisp_Object c = a; + a = qcdr(a); + qcdr(c) = b; + b = c; + } + return b; +} + +/* + * Environments are represented as association lists, and have to cope + * with several sorts of things. The items in an environment can be + * in one of the following forms: + * + * (a) (symbol . value) normal lexical variable binding + * (b) (symbol . ~magic~) given symbol is (locally) special + * (c) (0 . tag) (block tag ...) marker + * (d) (1 . (tag ...)) (tagbody ... tag ...) marker + * (e) (2 . ) case (c) or (d) but now invalidated + * (f) (def . symbol) (flet ...) or (macrolet ...) binding, + * where the def is non-atomic. + * + * Format for def in case (f) + * + * (1) (funarg env bvl ...) flet and labels + * (2) (bvl ...) macrolet + * Note that 'funarg is not valid as a bvl + * and indeed in this case bvl is a list + */ + +/* + * In CSL mode flet, macrolet and local declarations are not supported. + */ + +Lisp_Object Ceval(Lisp_Object u, Lisp_Object env) +{ + Lisp_Object nil = C_nil; +#ifdef COMMON + int t; +#ifdef CHECK_STACK + if (check_stack(__FILE__,__LINE__)) return aerror("deep stack in eval"); +#endif +restart: + t = (int)u & TAG_BITS; +/* + * The first case considered is of symbols - lexical and special bindings + * have to be sorted out. + */ + if (t == TAG_SYMBOL) + { + Header h = qheader(u); + if (h & SYM_SPECIAL_VAR) + { Lisp_Object v = qvalue(u); + if (v == unset_var) return error(1, err_unset_var, u); + else return onevalue(v); + } + else + { + while (env != nil) + { Lisp_Object p = qcar(env); + if (qcar(p) == u) + { Lisp_Object v =qcdr(p); +/* + * If a variable is lexically bound to the value work_symbol that means + * that the symbol has been (lexically) declared to be special, so its + * value cell should be inspected. + */ + if (v == work_symbol) + { v = qvalue(u); + if (v == unset_var) return error(1, err_unset_var, u); + } + return onevalue(v); + } + env = qcdr(env); + } +#ifdef ARTHURS_ORIGINAL_INTERPRETATION + return error(1, err_unbound_lexical, u); +#else + { Lisp_Object v = qvalue(u); + if (v == unset_var) return error(1, err_unset_var, u); + else return onevalue(v); + } +#endif + } + } +/* + * Things that are neither symbols nor lists evaluate to themselves, + * e.g. numbers and vectors. + */ + else if (t != TAG_CONS) return onevalue(u); + else +#endif /* COMMON */ + { +/* + * The final case is that of a list (fn ...), and one case that has to + * be checked is if fn is lexically bound. + */ + Lisp_Object fn, args; +#ifdef COMMON +/* + * The test for nil here is because although nil is a symbol the tagging + * structure tested here marks it as a list. + */ + if (u == nil) return onevalue(nil); +#endif + stackcheck2(0, u, env); + fn = qcar(u); + args = qcdr(u); +#ifdef COMMON +/* + * Local function bindings must be looked for first. + */ + { Lisp_Object p; + for (p=env; p!=nil; p=qcdr(p)) + { Lisp_Object w = qcar(p); +/* + * The form ( . sym) is used in an environment to indicate a local + * binding of a function, either as a regular function or as a macro + * (i.e. flet or macrolet). The structure of the list distinguishes + * between these two cases. + */ + if (qcdr(w) == fn && is_cons(w = qcar(w)) && w!=nil) + { + p = qcar(w); + if (p == funarg) /* ordinary function */ + { fn = w; /* (funarg ...) is OK to apply */ + goto ordinary_function; + } +/* + * Here it is a local macro. Observe that the macroexpansion is done + * with respect to an empty environment. Macros that are defined at the same + * time may seem to be mutually recursive but there is a sense in which they + * are not (as well as a sense in which they are) - self and cross references + * only happen AFTER an expansion and can not happen during one. + */ + push2(u, env); + w = cons(lambda, w); + nil = C_nil; + if (!exception_pending()) + p = Lfuncalln(nil, 4, qvalue(macroexpand_hook), + w, u, nil); + pop2(env, u); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + if ((exit_reason & UNWIND_ERROR) != 0) + { err_printf("\nMacroexpanding: "); + loop_print_error(u); + nil = C_nil; + if (exception_pending()) flip_exception(); + } + flip_exception(); + return nil; + } + u = p; + goto restart; + } + } + } +#endif + if (is_symbol(fn)) + { +/* + * Special forms and macros are checked for next. Special forms + * take precedence over macros. + */ + Header h = qheader(fn); + if (h & SYM_SPECIAL_FORM) + { Lisp_Object v; +#ifdef DEBUG + if (qfn1(fn) == NULL) + { term_printf("Illegal special form\n"); + my_exit(EXIT_FAILURE); + } +#endif + v = ((Special_Form *)qfn1(fn))(args, env); + return v; + } + else if (h & SYM_MACRO) + { + push2(u, env); +/* + * the environment passed to macroexpand should only be needed to cope + * with macrolet, I think. Since I use just one datastructure for the + * whole environment I also pass along lexical bindings etc, but I hope that + * they will never be accessed. I do not think that macrolet is important + * enough to call for complication and slow-down in the interpreter this + * way - but then I am not exactly what you would call a Common Lisp Fan! + */ + fn = macroexpand(u, env); + pop2(env, u); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + if ((exit_reason & UNWIND_ERROR) != 0) + { err_printf("\nMacroexpanding: "); + loop_print_error(u); + nil = C_nil; + if (exception_pending()) flip_exception(); + } + flip_exception(); + return nil; + } + return eval(fn, env); + } + } +/* + * Otherwise we have a regular function call. I prepare the args and + * call APPLY. + */ +#ifdef COMMON +ordinary_function: +#endif + { int nargs = 0; + Lisp_Object *save_stack = stack; +/* + * Args are built up on the stack here... + */ + while (consp(args)) + { Lisp_Object w; + push3(fn, args, env); + w = qcar(args); + w = eval(w, env); + pop3(env, args, fn); +/* + * nil having its mark bit set indicates that a special sort of exit + * is in progress. Multiple values can be ignored in this case. + */ + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack = save_stack; + if ((exit_reason & UNWIND_ERROR) != 0) + { err_printf("\nEvaluating: "); + loop_print_error(qcar(args)); + nil = C_nil; + if (exception_pending()) flip_exception(); + } + flip_exception(); + return nil; + } + push(w); /* args build up on the Lisp stack */ + nargs++; + args = qcdr(args); + } + +/* + * I pass the environment down to apply() because it will be used if the + * function was a simple lambda expression. If the function is a symbol + * or a closure, env will be irrelevant. The arguments are on the Lisp + * stack, and it is the responsibility of apply() to pop them. + */ + return apply(fn, nargs, env, fn); + } + } +} + +#ifdef COMMON +/* + * Keyword arguments are not supported in CSL mode - but &optional + * and &rest and &aux will be (at least for now). Removal of + * support for keywords will save a little space and an even smaller + * amount of time. + */ + +static bool check_no_unwanted_keys(Lisp_Object restarg, Lisp_Object ok_keys) +/* + * verify that there were no unwanted keys in the actual arg list + */ +{ + Lisp_Object nil = C_nil; + bool odd_key_found = NO; + while (restarg!=nil) + { Lisp_Object k = qcar(restarg); + Lisp_Object w; + for (w=ok_keys; w!=nil; w=qcdr(w)) + if (k == qcar(w)) goto is_ok; + odd_key_found = YES; + is_ok: + restarg = qcdr(restarg); + if (restarg==nil) return YES; /* odd length list */ + if (k == allow_key_key && qcar(restarg) != nil) return NO; /* OK */ + restarg = qcdr(restarg); + } + return odd_key_found; +} + +static bool check_keyargs_even(Lisp_Object restarg) +/* + * check that list is even length with alternate items symbols in + * the keyword package. + */ +{ + Lisp_Object nil = C_nil; + while (restarg!=nil) + { Lisp_Object q = qcar(restarg); + if (!is_symbol(q) || qpackage(q) != qvalue(keyword_package)) return YES; + restarg = qcdr(restarg); + if (restarg==nil) return YES; /* Odd length is wrong */ + restarg = qcdr(restarg); + } + return NO; /* OK */ +} + +static Lisp_Object keywordify(Lisp_Object v) +{ +/* + * arg is a non-nil symbol. Should nil be permitted - I think not + * since there seems too much chance of confusion. + */ + Lisp_Object nil, name = get_pname(v); + errexit(); + return Lintern_2(nil, name, qvalue(keyword_package)); +} + +static Lisp_Object key_lookup(Lisp_Object keyname, Lisp_Object args) +{ + Lisp_Object nil = C_nil; + while (args!=nil) + { Lisp_Object next = qcdr(args); + if (next==nil) return nil; + if (qcar(args) == keyname) return next; + else args = qcdr(next); + } + return nil; +} + +#endif + +Lisp_Object apply_lambda(Lisp_Object def, int nargs, + Lisp_Object env, Lisp_Object name) +/* + * Here def is a lambda expression (sans the initial lambda) that is to + * be applied. Much horrible messing about is needed so that I can cope + * with &optional and &rest args (including initialisers and supplied-p + * variables, also &key, &allow-other-keys and &aux). Note the need to find + * any special declarations at the head of the body of the lambda-form. + * Must pop (nargs) items from the stack at exit. + */ +{ +/* + * lambda-lists are parsed using a finite state engine with the + * following states, plus an exit state. + */ +#define STATE_NULL 0 /* at start and during regular args */ +#define STATE_OPT 1 /* after &optional */ +#define STATE_OPT1 2 /* after &optional + at least one var */ +#define STATE_REST 3 /* immediately after &rest */ +#define STATE_REST1 4 /* after &rest vv */ +#ifdef COMMON +#define STATE_KEY 5 /* &key with no &rest */ +#define STATE_ALLOW 6 /* &allow-other-keys */ +#endif +#define STATE_AUX 7 /* &aux */ + + Lisp_Object nil = C_nil; + int opt_rest_state = STATE_NULL; + Lisp_Object *next_arg; + int args_left = nargs; + Lisp_Object w; + if (!consp(def)) + { popv(nargs); + return onevalue(nil); /* Should never happen */ + } + stackcheck3(0, def, env, name); + w = qcar(def); + next_arg = &stack[1-nargs]; /* Points to arg1 */ + push4(w, /* bvl */ + qcdr(def), /* body */ + env, name); +/* + * Here I need to macroexpand the first few items in body and + * look for declare/special items. I will only bother with SPECIAL decls. + * Note that args have been pushed onto the stack first to avoid corruption + * while the interpreter performs macroexpansion. This is the sort of place + * where I feel that Common Lisp has built in causes of inefficiency. + * Well oh well!!! The Common Lisp standardisation group thought so too, + * and have now indicated that DECLARE forms can not be hidden away as + * the result of macros, so some of this is unnecessary. + */ + push5(nil, nil, /* local_decs, ok_keys */ + nil, nil, nil); /* restarg, specenv, val1 */ + push5(nil, nil, /* arg, v1 */ + nil, nil, nil); /* v, p, w */ +/* + * On computers which have unsigned offsets in indexed memory reference + * instructions the negative indexes off the stack suggested here might + * be more expensive than I would like - maybe on such machines the stack + * pointer should be kept offset by 64 bytes (say). Doing so in general + * would be to the disadvantage of machines with auto-index address modes + * that might be used when pushing/popping single items on the stack. + */ +#define w stack[0] +#define p stack[-1] +#define v stack[-2] +#define v1 stack[-3] +#define arg stack[-4] +#define val1 stack[-5] +#define specenv stack[-6] +#define restarg stack[-7] +#ifdef COMMON +#define ok_keys stack[-8] +#define local_decs stack[-9] +#endif +#define name stack[-10] +#define env stack[-11] +#define body stack[-12] +#define bvl stack[-13] +#define arg1 stack[-14] +#define stack_used ((int)(nargs + 14)) + +#ifdef COMMON + for (;;) + { if (!consp(body)) break; + p = macroexpand(qcar(body), env); + nil = C_nil; + if (exception_pending()) + { Lisp_Object qname = name; + popv(stack_used); + return qname; + } + body = qcdr(body); + if (!consp(p)) + { if (stringp(p) && consp(body)) continue; + body = cons(p, body); + break; + } + if (qcar(p) != declare_symbol) + { body = cons(p, body); + break; + } + for (v = qcdr(v); consp(v); v = qcdr(v)) + { v1 = qcar(v); + if (!consp(v1) || qcar(v1) != special_symbol) continue; + /* here v1 says (special ...) */ + for (v1=qcdr(v1); consp(v1); v1 = qcdr(v1)) + { local_decs = cons(qcar(v1), local_decs); + if (exception_pending()) break; + } + } + } + nil = C_nil; + if (exception_pending()) + { Lisp_Object qname = name; + popv(stack_used); + return qname; + } +#endif +/* + * Parse the BVL + */ + for (p = bvl; consp(p); p=qcdr(p)) + { v = qcar(p); + v1 = nil; + arg = nil; + val1 = nil; +/* + * I can break from this switch statement with v a variable to bind + * and arg the value to bind to it, also v1 (if not nil) is a second + * variable to be bound (a supplied-p value) and val1 the value to bind it to. + * If I see &rest or &key the remaining actual args get collected into + * restarg, which takes the place of arg in some respects. + */ + switch (opt_rest_state) + { + + case STATE_NULL: + if (v == opt_key) + { opt_rest_state = STATE_OPT; + continue; + } + +#define BAD1(msg) { error(0, msg); goto unwind_special_bindings; } +#define BAD2(msg, a) { error(1, msg, a); goto unwind_special_bindings; } + +#define collect_rest_arg() \ + while (args_left-- != 0) \ + { if (!exception_pending()) \ + restarg = cons(next_arg[args_left], restarg); \ + nil = C_nil; \ + } + + if (v == rest_key) + { collect_rest_arg(); + if (exception_pending()) goto unwind_special_bindings; + opt_rest_state = STATE_REST; + continue; + } +#ifdef COMMON + if (v == key_key) + { collect_rest_arg(); + if (exception_pending()) goto unwind_special_bindings; + if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); + opt_rest_state = STATE_KEY; + continue; + } + + if (v == aux_key) + { if (args_left != 0) BAD1(err_excess_args); + opt_rest_state = STATE_AUX; + continue; + } + if (v == allow_other_keys) BAD2(err_bad_bvl, v); +#endif + if (args_left == 0) BAD1(err_insufficient_args); + arg = *next_arg++; + args_left--; + v1 = nil; /* no suppliedp mess here, I'm glad to say */ + break; + + case STATE_OPT: + if (v == opt_key + || v == rest_key +#ifdef COMMON + || v == key_key + || v == allow_other_keys + || v == aux_key +#endif + ) BAD2(err_bad_bvl, v); +/* + * Here v may be a simple variable, or a list (var init suppliedp) + */ + opt_rest_state = STATE_OPT1; +process_optional_parameter: + if (args_left != 0) + { arg = *next_arg++; + args_left--; + val1 = lisp_true; + } + else + { arg = nil; + val1 = nil; + } + v1 = nil; + if (!consp(v)) break; /* Simple case */ + { w = qcdr(v); + v = qcar(v); + if (!consp(w)) break; /* (var) */ + if (val1 == nil) /* use the init form */ + { arg = qcar(w); + arg = eval(arg, env); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + } + w = qcdr(w); + if (consp(w)) v1 = qcar(w); /* suppliedp name */ + break; + } + + case STATE_OPT1: + if (v == rest_key) + { collect_rest_arg(); + if (exception_pending()) goto unwind_special_bindings; + opt_rest_state = STATE_REST; + continue; + } +#ifdef COMMON + if (v == key_key) + { collect_rest_arg(); + if (exception_pending()) goto unwind_special_bindings; + if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); + opt_rest_state = STATE_KEY; + continue; + } + if (v == aux_key) + { if (args_left != 0) BAD1(err_excess_args); + opt_rest_state = STATE_AUX; + continue; + } +#endif + if (v == opt_key +#ifdef COMMON + || v == allow_other_keys +#endif + ) BAD2(err_bad_bvl, v); + goto process_optional_parameter; + + case STATE_REST: + if (v == opt_key + || v == rest_key +#ifdef COMMON + || v == key_key + || v == allow_other_keys + || v == aux_key +#endif + ) BAD2(err_bad_bvl, v); + opt_rest_state = STATE_REST1; + arg = restarg; + break; + + case STATE_REST1: +#ifdef COMMON + if (v == key_key) + { if (check_keyargs_even(restarg)) BAD2(err_bad_keyargs, restarg); + opt_rest_state = STATE_KEY; + continue; + } + if (v == aux_key) + { + opt_rest_state = STATE_AUX; + continue; + } +#endif + BAD2(err_bad_bvl, rest_key); + +#ifdef COMMON + case STATE_KEY: + if (v == allow_other_keys) + { opt_rest_state = STATE_ALLOW; + continue; + } + if (v == aux_key) + { if (check_no_unwanted_keys(restarg, ok_keys)) + BAD2(err_bad_keyargs, restarg); + opt_rest_state = STATE_AUX; + continue; + } + if (v == opt_key || v == rest_key || v == key_key) + BAD2(err_bad_bvl, v); +process_keyword_parameter: +/* + * v needs to expand to ((:kv v) init svar) in effect here. + */ + { Lisp_Object keyname = nil; + w = nil; + if (!consp(v)) + { if (!is_symbol(v)) BAD2(err_bad_bvl, v); + keyname = keywordify(v); + } + else + { w = qcdr(v); + v = qcar(v); + if (!consp(v)) + { if (!is_symbol(v)) BAD2(err_bad_bvl, v); + keyname = keywordify(v); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + } + else + { keyname = qcar(v); + if (!is_symbol(keyname)) BAD2(err_bad_bvl, v); + keyname = keywordify(keyname); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + v = qcdr(v); + if (consp(v)) v = qcar(v); + else BAD2(err_bad_bvl, v); + } + } + ok_keys = cons(keyname, ok_keys); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + arg = key_lookup(qcar(ok_keys), restarg); + if (arg == nil) val1 = nil; + else + { arg = qcar(arg); + val1 = lisp_true; + } + v1 = nil; + if (!consp(w)) break; /* (var) */ + if (val1 == nil) /* use the init form */ + { arg = qcar(w); + arg = eval(arg, env); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + } + w = qcdr(w); + if (consp(w)) v1 = qcar(w); /* suppliedp name */ + break; + } + + case STATE_ALLOW: + if (v == aux_key) + { opt_rest_state = STATE_AUX; + continue; + } + if (v == opt_key || v == rest_key || v == key_key || + v == allow_other_keys) BAD2(err_bad_bvl, v); + goto process_keyword_parameter; + + case STATE_AUX: + if (v == opt_key || v == rest_key || + v == key_key || v == allow_other_keys || + v == aux_key) BAD2(err_bad_bvl, v); + if (consp(v)) + { w = qcdr(v); + v = qcar(v); + if (consp(w)) + { arg = qcar(w); + arg = eval(arg, env); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + } + } + else arg = nil; + v1 = nil; + break; +#endif + } +/* + * This is where I get when I have one or two vars to bind. + */ + +#ifndef COMMON +/* + * CSL mode does not have to mess about looking for local special bindings + * and so is MUCH shorter and neater. I always shallow bind + */ +#define instate_binding(var, val, local_decs1, lab) \ + { if (!is_symbol(var)) BAD2(err_bad_bvl, var); \ + w = acons(var, qvalue(var), specenv); \ + nil = C_nil; \ + if (exception_pending()) goto unwind_special_bindings; \ + specenv = w; \ + qvalue(var) = val; \ + } +#else +#define instate_binding(var, val, local_decs1, lab) \ + { Header h; \ + if (!is_symbol(var)) BAD2(err_bad_bvl, var); \ + h = qheader(var); \ + if ((h & SYM_SPECIAL_VAR) != 0) \ + { w = acons(var, qvalue(var), specenv); \ + nil = C_nil; \ + if (exception_pending()) goto unwind_special_bindings; \ + specenv = w; \ + qvalue(var) = val; \ + } \ + else \ + { for (w = local_decs1; w!=nil; w = qcdr(w)) \ + { if (qcar(w) == var) \ + { qcar(w) = fixnum_of_int(0);/* decl is used up */\ + w = acons(var, work_symbol, env); \ + nil = C_nil; \ + if (exception_pending()) \ + goto unwind_special_bindings; \ + env = w; \ + w = acons(var, qvalue(var), specenv); \ + nil = C_nil; \ + if (exception_pending()) \ + goto unwind_special_bindings; \ + specenv = w; \ + qvalue(var) = val; \ + goto lab; \ + } \ + } \ + w = acons(var, val, env); \ + nil = C_nil; \ + if (exception_pending()) goto unwind_special_bindings; \ + env = w; \ + lab: ; \ + } \ + } +#endif + +#ifdef COMMON +/* + * Must check about local special declarations here... + */ +#endif + instate_binding(v, arg, local_decs, label1); + if (v1 != nil) instate_binding(v1, val1, local_decs, label2); + + } /* End of for loop that scans BVL */ + +#ifdef COMMON +/* + * As well as local special declarations that have applied to bindings here + * there can be some that apply just to variable references within the body. + */ + while (local_decs!=nil) + { Lisp_Object q = qcar(local_decs); + local_decs=qcdr(local_decs); + if (!is_symbol(q)) continue; + w = acons(q, work_symbol, env); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + env = w; + } +#endif + + switch (opt_rest_state) + { +case STATE_NULL: +case STATE_OPT1: /* Ensure there had not been too many args */ + if (args_left != 0) BAD1(err_excess_args); + break; + +case STATE_OPT: /* error if bvl finishes here */ +case STATE_REST: + BAD2(err_bad_bvl, opt_rest_state == STATE_OPT ? opt_key : rest_key); + +#ifdef COMMON +case STATE_KEY: /* ensure only valid keys were given */ + if (check_no_unwanted_keys(restarg, ok_keys)) + BAD2(err_bad_keyargs, restarg); + break; +#endif + +default: +/* in the following cases all is known to be well +case STATE_REST1: +case STATE_ALLOW: +case STATE_AUX: +*/ + break; + } + +/* + * Now all the argument bindings have been performed - it remains to + * process the body of the lambda-expression. + */ + if (specenv == nil) + { Lisp_Object bodyx = body, envx = env; + Lisp_Object qname = name; + popv(stack_used); + push(qname); + bodyx = progn_fn(bodyx, envx); + pop(qname); + nil = C_nil; + if (exception_pending()) return qname; + return bodyx; + } + { body = progn_fn(body, env); + nil = C_nil; + if (exception_pending()) goto unwind_special_bindings; + while (specenv != nil) + { + Lisp_Object bv = qcar(specenv); + qvalue(qcar(bv)) = qcdr(bv); + specenv = qcdr(specenv); + } + { Lisp_Object bodyx = body; + popv(stack_used); +/* + * note that exit_count has not been disturbed since I called progn_fn, + * so the numbert of values that will be returned remains correctly + * established (in Common Lisp mode where it is needed. + */ + return bodyx; + } + } + +unwind_special_bindings: +/* + * I gete here ONLY if nil has its mark bit set, which means that (for + * one reason or another) I am having to unwind the stack, restoring + * special bindings as I go. + */ + nil = C_nil; + flip_exception(); + while (specenv != nil) + { Lisp_Object bv = qcar(specenv); + qvalue(qcar(bv)) = qcdr(bv); + specenv = qcdr(specenv); + } + flip_exception(); + { Lisp_Object qname = name; + popv(stack_used); + return qname; + } +#undef w +#undef p +#undef v +#undef v1 +#undef arg +#undef val1 +#undef specenv +#undef restarg +#undef ok_keys +#undef local_decs +#undef name +#undef env +#undef body +#undef bvl +#undef stack_used +} + +Lisp_Object Leval(Lisp_Object nil, Lisp_Object a) +{ + return eval(a, nil); /* Multiple values may be returned */ +} + +Lisp_Object Levlis(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object r; + stackcheck1(0, a); + r = nil; + while (consp(a)) + { push2(qcdr(a), r); + a = qcar(a); + a = eval(a, nil); + errexitn(2); + pop(r); + r = cons(a, r); + pop(a); + errexit(); + } + return onevalue(nreverse(r)); +} + +Lisp_Object MS_CDECL Lapply_n(Lisp_Object nil, int nargs, ...) +{ + va_list a; + int i; + Lisp_Object *stack_save = stack, last, fn; + if (nargs == 0) return aerror("apply"); + if (nargs > 1) + { va_start(a, nargs); + fn = va_arg(a, Lisp_Object); + push_args_1(a, nargs); + pop(last); + i = nargs-2; + while (consp(last)) + { push(qcar(last)); + last = qcdr(last); + i++; + } + } + else i = 0; + stackcheck1(stack-stack_save, fn); + return apply(fn, i, nil, fn); +} + +Lisp_Object Lapply_1(Lisp_Object nil, Lisp_Object fn) +{ + return Lapply_n(nil, 1, fn); +} + +Lisp_Object Lapply_2(Lisp_Object nil, Lisp_Object fn, Lisp_Object a1) +{ + return Lapply_n(nil, 2, fn, a1); +} + +Lisp_Object Lapply0(Lisp_Object nil, Lisp_Object fn) +{ + if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 0); + stackcheck1(0, fn); + return apply(fn, 0, C_nil, fn); +} + +Lisp_Object Lapply1(Lisp_Object nil, Lisp_Object fn, Lisp_Object a) +{ + if (is_symbol(fn)) return (*qfn1(fn))(qenv(fn), a); + push(a); + stackcheck1(1, fn); + return apply(fn, 1, C_nil, fn); +} + +Lisp_Object MS_CDECL Lapply2(Lisp_Object nil, int nargs, ...) +{ + va_list aa; + Lisp_Object fn, a, b; + argcheck(nargs, 3, "apply2"); + va_start(aa, nargs); + fn = va_arg(aa, Lisp_Object); + a = va_arg(aa, Lisp_Object); + b = va_arg(aa, Lisp_Object); + va_end(aa); + if (is_symbol(fn)) return (*qfn2(fn))(qenv(fn), a, b); + push2(a, b); + stackcheck1(2, fn); + return apply(fn, 2, C_nil, fn); +} + +Lisp_Object MS_CDECL Lapply3(Lisp_Object nil, int nargs, ...) +{ + va_list aa; + Lisp_Object fn, a, b, c; + argcheck(nargs, 4, "apply3"); + va_start(aa, nargs); + fn = va_arg(aa, Lisp_Object); + a = va_arg(aa, Lisp_Object); + b = va_arg(aa, Lisp_Object); + c = va_arg(aa, Lisp_Object); + va_end(aa); + if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 3, a, b, c); + push3(a, b, c); + stackcheck1(3, fn); + return apply(fn, 3, C_nil, fn); +} + +Lisp_Object Lfuncall1(Lisp_Object nil, Lisp_Object fn) +{ + if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 0); + stackcheck1(0, fn); + return apply(fn, 0, nil, fn); +} + +Lisp_Object Lfuncall2(Lisp_Object nil, Lisp_Object fn, Lisp_Object a1) +{ + if (is_symbol(fn)) return (*qfn1(fn))(qenv(fn), a1); + push(a1); + stackcheck1(1, fn); + return apply(fn, 1, nil, fn); +} + +static Lisp_Object MS_CDECL Lfuncalln_sub(Lisp_Object nil, int nargs, va_list a) +{ + Lisp_Object *stack_save = stack, fn; + fn = va_arg(a, Lisp_Object); + push_args_1(a, nargs); + stackcheck1(stack-stack_save, fn); + return apply(fn, nargs-1, nil, fn); +} + +Lisp_Object MS_CDECL Lfuncalln(Lisp_Object nil, int nargs, ...) +{ + va_list a; + Lisp_Object fn, a1, a2, a3, a4; + va_start(a, nargs); + switch (nargs) + { +case 0: return aerror("funcall"); +case 1: /* cases 1 and 2 should go through Lfuncall1,2 not here */ +case 2: return aerror("funcall wrong call"); +case 3: fn = va_arg(a, Lisp_Object); + a1 = va_arg(a, Lisp_Object); + a2 = va_arg(a, Lisp_Object); + if (is_symbol(fn)) return (*qfn2(fn))(qenv(fn), a1, a2); + push2(a1, a2); + return apply(fn, 2, nil, fn); +case 4: fn = va_arg(a, Lisp_Object); + a1 = va_arg(a, Lisp_Object); + a2 = va_arg(a, Lisp_Object); + a3 = va_arg(a, Lisp_Object); + if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 3, a1, a2, a3); + push3(a1, a2, a3); + return apply(fn, 3, nil, fn); +case 5: fn = va_arg(a, Lisp_Object); + a1 = va_arg(a, Lisp_Object); + a2 = va_arg(a, Lisp_Object); + a3 = va_arg(a, Lisp_Object); + a4 = va_arg(a, Lisp_Object); + if (is_symbol(fn)) return (*qfnn(fn))(qenv(fn), 4, a1, a2, a3, a4); + push4(a1, a2, a3, a4); + return apply(fn, 4, nil, fn); +default: + return Lfuncalln_sub(nil, nargs, a); + } +} + +#ifdef COMMON + +Lisp_Object MS_CDECL Lvalues(Lisp_Object nil, int nargs, ...) +{ + va_list a; + Lisp_Object *p = &mv_2, w; + int i; +/* + * Because multiple-values get passed back in static storage there is + * a fixed upper limit to how many I can handle - truncate here to allow + * for that. + */ + if (nargs > 50) nargs = 50; + if (nargs == 0) return nvalues(nil, 0); + va_start(a, nargs); + push_args(a, nargs); + for (i=1; i nil */ + stackcheck2(0, args, env); + push2(args, env); + fn = qcar(args); + fn = eval(fn, env); + pop2(env, args); + errexit(); + args = qcdr(args); + while (consp(args)) + { Lisp_Object r1; + push2(args, env); + r1 = qcar(args); + r1 = eval(r1, env); + nil = C_nil; + if (exception_pending()) + { stack = stack_save; + return nil; + } +/* + * It is critical here that push does not check for stack overflow and + * thus can not call the garbage collector, or otherwise lead to calculation + * that could possibly clobber the multiple results that I am working with + * here. + */ + pop2(env, args); + push(r1); + i++; + for (j = 2; j<=exit_count; j++) + { push((&work_0)[j]); + i++; + } + args = qcdr(args); + } + stackcheck2(stack-stack_save, fn, env); + return apply(fn, i, env, fn); +} + +#endif + +Lisp_Object interpreted1(Lisp_Object def, Lisp_Object a1) +{ + Lisp_Object nil = C_nil; + push(a1); + stackcheck1(1, def); + return apply_lambda(def, 1, nil, def); +} + +Lisp_Object interpreted2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) +{ + Lisp_Object nil = C_nil; + push2(a1, a2); + stackcheck1(2, def); + return apply_lambda(def, 2, nil, def); +} + +Lisp_Object MS_CDECL interpretedn(Lisp_Object def, int nargs, ...) +{ +/* + * The messing about here is to get the (unknown number of) args + * into a nice neat vector so that they can be indexed into. If I knew + * that the args were in consecutive locations on the stack I could + * probably save a copying operation. + */ + Lisp_Object nil = C_nil; + Lisp_Object *stack_save = stack; + va_list a; + if (nargs != 0) + { va_start(a, nargs); + push_args(a, nargs); + } + stackcheck1(stack-stack_save, def); + return apply_lambda(def, nargs, nil, def); +} + +Lisp_Object funarged1(Lisp_Object def, Lisp_Object a1) +{ + Lisp_Object nil = C_nil; + push(a1); + stackcheck1(1, def); + return apply_lambda(qcdr(def), 1, qcar(def), qcdr(def)); +} + +Lisp_Object funarged2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) +{ + Lisp_Object nil = C_nil; + push2(a1, a2); + stackcheck1(2, def); + return apply_lambda(qcdr(def), 2, qcar(def), qcdr(def)); +} + +Lisp_Object MS_CDECL funargedn(Lisp_Object def, int nargs, ...) +{ + Lisp_Object nil = C_nil; + Lisp_Object *stack_save = stack; + va_list a; + if (nargs != 0) + { va_start(a, nargs); + push_args(a, nargs); + } + stackcheck1(stack-stack_save, def); + return apply_lambda(qcdr(def), nargs, qcar(def), qcdr(def)); +} + +/* + * Now some execution-doubling versions... + */ + +Lisp_Object double_interpreted1(Lisp_Object def, Lisp_Object a1) +{ + Lisp_Object nil = C_nil; + push(a1); + stackcheck1(1, def); + return apply_lambda(def, 1, nil, def); +} + +Lisp_Object double_interpreted2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) +{ + Lisp_Object nil = C_nil; + push2(a1, a2); + stackcheck1(2, def); + return apply_lambda(def, 2, nil, def); +} + +Lisp_Object MS_CDECL double_interpretedn(Lisp_Object def, int nargs, ...) +{ +/* + * The messing about here is to get the (unknown number of) args + * into a nice neat vector so that they can be indexed into. If I knew + * that the args were in consecutive locations on the stack I could + * probably save a copying operation. + */ + Lisp_Object nil = C_nil; + Lisp_Object *stack_save = stack; + va_list a; + if (nargs != 0) + { va_start(a, nargs); + push_args(a, nargs); + } + stackcheck1(stack-stack_save, def); + return apply_lambda(def, nargs, nil, def); +} + +Lisp_Object double_funarged1(Lisp_Object def, Lisp_Object a1) +{ + Lisp_Object nil = C_nil; + push(a1); + stackcheck1(1, def); + return apply_lambda(qcdr(def), 1, qcar(def), qcdr(def)); +} + +Lisp_Object double_funarged2(Lisp_Object def, Lisp_Object a1, Lisp_Object a2) +{ + Lisp_Object nil = C_nil; + push2(a1, a2); + stackcheck1(2, def); + return apply_lambda(qcdr(def), 2, qcar(def), qcdr(def)); +} + +Lisp_Object MS_CDECL double_funargedn(Lisp_Object def, int nargs, ...) +{ + Lisp_Object nil = C_nil; + Lisp_Object *stack_save = stack; + va_list a; + if (nargs != 0) + { va_start(a, nargs); + push_args(a, nargs); + } + stackcheck1(stack-stack_save, def); + return apply_lambda(qcdr(def), nargs, qcar(def), qcdr(def)); +} + +int trace_depth = 0; + +static void trace_entering(char *s) +{ + int i; + for (i=0; i0)", env); + return (*qfnn(env))(qenv(env), 0); +} + +Lisp_Object f1_as_0(Lisp_Object env, Lisp_Object a) +{ + return (*qfnn(env))(qenv(env), 0); +} + +Lisp_Object f2_as_0(Lisp_Object env, Lisp_Object a, Lisp_Object b) +{ + return (*qfnn(env))(qenv(env), 0); +} + +Lisp_Object MS_CDECL f3_as_0(Lisp_Object env, int nargs, ...) +{ + if (nargs != 3) return aerror1("wrong number of args (3->0)", env); + return (*qfnn(env))(qenv(env), 0); +} + +Lisp_Object f1_as_1(Lisp_Object env, Lisp_Object a) +{ + return (*qfn1(env))(qenv(env), a); +} + +Lisp_Object f2_as_1(Lisp_Object env, Lisp_Object a, Lisp_Object b) +{ + return (*qfn1(env))(qenv(env), a); +} + +Lisp_Object MS_CDECL f3_as_1(Lisp_Object env, int nargs, ...) +{ + va_list a; + Lisp_Object a1; + if (nargs != 3) return aerror1("wrong number of args (3->1)", env); + va_start(a, nargs); + a1 = va_arg(a, Lisp_Object); + va_end(a); + return (*qfn1(env))(qenv(env), a1); +} + +Lisp_Object f2_as_2(Lisp_Object env, Lisp_Object a, Lisp_Object b) +{ + return (*qfn2(env))(qenv(env), a, b); +} + +Lisp_Object MS_CDECL f3_as_2(Lisp_Object env, int nargs, ...) +{ + va_list a; + Lisp_Object a1, a2; + if (nargs != 3) return aerror1("wrong number of args (3->2)", env); + va_start(a, nargs); + a1 = va_arg(a, Lisp_Object); + a2 = va_arg(a, Lisp_Object); + va_end(a); + return (*qfn2(env))(qenv(env), a1, a2); +} + +Lisp_Object MS_CDECL f3_as_3(Lisp_Object env, int nargs, ...) +{ + va_list a; + Lisp_Object a1, a2, a3; + if (nargs != 3) return aerror1("wrong number of args (3->3)", env); + va_start(a, nargs); + a1 = va_arg(a, Lisp_Object); + a2 = va_arg(a, Lisp_Object); + a3 = va_arg(a, Lisp_Object); + va_end(a); + return (*qfnn(env))(qenv(env), 3, a1, a2, a3); +} + +setup_type const eval1_setup[] = +{ + {"bytecounts", wrong_no_na, wrong_no_nb, bytecounts}, + {"apply", Lapply_1, Lapply_2, Lapply_n}, + {"apply0", Lapply0, too_many_1, wrong_no_1}, + {"apply1", too_few_2, Lapply1, wrong_no_2}, + {"apply2", wrong_no_na, wrong_no_nb, Lapply2}, + {"apply3", wrong_no_na, wrong_no_nb, Lapply3}, + {"evlis", Levlis, too_many_1, wrong_no_1}, + {"funcall", Lfuncall1, Lfuncall2, Lfuncalln}, + {"funcall*", Lfuncall1, Lfuncall2, Lfuncalln}, +#ifdef COMMON + {"values", Lvalues_1, Lvalues_2, Lvalues}, + {"macroexpand", Lmacroexpand, Lmacroexpand_2, wrong_no_1}, + {"macroexpand-1", Lmacroexpand_1, Lmacroexpand_1_2, wrong_no_1}, +#else + {"macroexpand", Lmacroexpand, too_many_1, wrong_no_1}, + {"macroexpand-1", Lmacroexpand_1, too_many_1, wrong_no_1}, +#endif + {NULL, 0, 0, 0} +}; + +/* end of eval1.c */ + Index: r36/cslbase/eval4.c ================================================================== --- r36/cslbase/eval4.c +++ r36/cslbase/eval4.c @@ -1,1767 +1,1767 @@ -/* - * eval4.c Copyright (C) 1991-96, Codemist Ltd - * - * Bytecode interpreter/main interpreter interfaces - */ - -/* Signature: 502ad14c 12-Mar-2000 */ - -#include -#include -#include - -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "arith.h" -#include "entries.h" -#ifdef TIMEOUT -#include "timeout.h" -#endif - -#ifdef DEBUG -int trace_all = 0; -#endif - -#define name_from(def) elt(qcdr(def), 0) - -static void trace_entering(char *s) -{ - int i; - for (i=0; i 3 args not doubled\n"); - r = bytestream_interpret(r-1, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop2(codevec, litvec); - return r; -} - - -/* - * The code that follows is just used to support compiled code that - * has &optional or &rest arguments. - */ - -Lisp_Object byteopt1(Lisp_Object def, Lisp_Object a) -{ - return byteoptn(def, 1, a); -} - -Lisp_Object byteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return byteoptn(def, 2, a, b); -} - -static Lisp_Object vbyteoptn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push2(litvec, codevec); -/* - * Maybe I should raise an exception (continuable error) if too many args - * are provided - for now I just silently ignore the excess. - */ - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs || nargs > wantargs+wantopts) - { popv(nargs); pop2(codevec, litvec) - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - stackcheck1(stack-stack_save, def); - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop2(codevec, litvec); - return r; -} - -Lisp_Object MS_CDECL byteoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vbyteoptn(def, nargs, a, C_nil); -} - -Lisp_Object hardopt1(Lisp_Object def, Lisp_Object a) -{ - return hardoptn(def, 1, a); -} - -Lisp_Object hardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return hardoptn(def, 2, a, b); -} - -Lisp_Object MS_CDECL hardoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vbyteoptn(def, nargs, a, SPID_NOARG); -} - -Lisp_Object byteoptrest1(Lisp_Object def, Lisp_Object a) -{ - return byteoptrestn(def, 1, a); -} - -Lisp_Object byteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return byteoptrestn(def, 2, a, b); -} - -static Lisp_Object vbyterestn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push2(litvec, codevec); - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs) - { popv(nargs+2); - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - { Lisp_Object rest = nil; - while (nargs > wantargs+wantopts) - { Lisp_Object w = stack[0]; - stack[0] = def; - rest = cons(w, rest); - errexitn(nargs+2); - pop(def); - nargs--; - } - push(rest); - nargs++; - } - stackcheck1(stack-stack_save, def); - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop2(codevec, litvec); - return r; -} - -Lisp_Object MS_CDECL byteoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vbyterestn(def, nargs, a, C_nil); -} - -Lisp_Object hardoptrest1(Lisp_Object def, Lisp_Object a) -{ - return hardoptrestn(def, 1, a); -} - -Lisp_Object hardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return hardoptrestn(def, 2, a, b); -} - -Lisp_Object MS_CDECL hardoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vbyterestn(def, nargs, a, SPID_NOARG); -} - -/* - * Next the execution-doubling versions of the &opt/&rest interfaces - */ - -Lisp_Object double_byteopt1(Lisp_Object def, Lisp_Object a) -{ - return double_byteoptn(def, 1, a); -} - -Lisp_Object double_byteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return double_byteoptn(def, 2, a, b); -} - -static Lisp_Object double_vbyteoptn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push2(litvec, codevec); -/* - * Maybe I should raise an exception (continuable error) if too many args - * are provided - for now I just silently ignore th excess. - */ - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs || nargs > wantargs+wantopts) - { popv(nargs); pop2(codevec, litvec) - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - stackcheck1(stack-stack_save, def); - trace_printf("Function with simple &opt arg not doubled\n"); - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop2(codevec, litvec); - return r; -} - -Lisp_Object MS_CDECL double_byteoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return double_vbyteoptn(def, nargs, a, C_nil); -} - -Lisp_Object double_hardopt1(Lisp_Object def, Lisp_Object a) -{ - return double_hardoptn(def, 1, a); -} - -Lisp_Object double_hardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return double_hardoptn(def, 2, a, b); -} - -Lisp_Object MS_CDECL double_hardoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return double_vbyteoptn(def, nargs, a, SPID_NOARG); -} - -Lisp_Object double_byteoptrest1(Lisp_Object def, Lisp_Object a) -{ - return double_byteoptrestn(def, 1, a); -} - -Lisp_Object double_byteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return double_byteoptrestn(def, 2, a, b); -} - -static Lisp_Object double_vbyterestn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push2(litvec, codevec); - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs) - { popv(nargs+2); - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - { Lisp_Object rest = nil; - while (nargs > wantargs+wantopts) - { Lisp_Object w = stack[0]; - stack[0] = def; - rest = cons(w, rest); - errexitn(nargs+2); - pop(def); - nargs--; - } - push(rest); - nargs++; - } - stackcheck1(stack-stack_save, def); - trace_printf("Function with simple &rest arg not doubled\n"); - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop2(codevec, litvec); - return r; -} - -Lisp_Object MS_CDECL double_byteoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return double_vbyterestn(def, nargs, a, C_nil); -} - -Lisp_Object double_hardoptrest1(Lisp_Object def, Lisp_Object a) -{ - return double_hardoptrestn(def, 1, a); -} - -Lisp_Object double_hardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return double_hardoptrestn(def, 2, a, b); -} - -Lisp_Object MS_CDECL double_hardoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return double_vbyterestn(def, nargs, a, SPID_NOARG); -} - -Lisp_Object tracebyteopt1(Lisp_Object def, Lisp_Object a) -{ - return tracebyteoptn(def, 1, a); -} - -Lisp_Object tracebyteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return tracebyteoptn(def, 2, a, b); -} - -static Lisp_Object vtracebyteoptn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push3(litvec, codevec, def); -/* - * Maybe I should raise an exception (continuable error) if too many args - * are provided - for now I just silently ignore th excess. - */ - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs || nargs > wantargs+wantopts) - { popv(nargs+1); pop2(codevec, litvec) - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - stackcheck1(stack-stack_save, def); - freshline_trace(); - loop_print_trace(name_from(def)); - trace_printf(" (%d args)\n", nargs); - for (i=1; i<=nargs; i++) - { trace_printf("Arg%d: ", i); - loop_print_trace(stack[i-nargs]); - trace_printf("\n"); - } - def = stack[-nargs]; - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs+1); pop2(codevec, litvec); - flip_exception(); - return nil; - } -#ifdef COMMON - r = Lmv_list(nil, r); - if (exception_pending()) - { flip_exception(); - popv(1); pop2(codevec, litvec); - flip_exception(); - return nil; - } -#endif - pop(def); - push(r); - freshline_trace(); - loop_print_trace(name_from(def)); - nil = C_nil; - if (!exception_pending()) - { trace_printf(" = "); - loop_print_trace(r); - trace_printf("\n"); - } - if (exception_pending()) - { flip_exception(); - popv(1); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop3(r, codevec, litvec); -#ifdef COMMON - r = unpack_mv(nil, r); -#endif - return r; -} - -Lisp_Object MS_CDECL tracebyteoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vtracebyteoptn(def, nargs, a, C_nil); -} - -Lisp_Object tracehardopt1(Lisp_Object def, Lisp_Object a) -{ - return tracehardoptn(def, 1, a); -} - -Lisp_Object tracehardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return tracehardoptn(def, 2, a, b); -} - -Lisp_Object MS_CDECL tracehardoptn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vtracebyteoptn(def, nargs, a, SPID_NOARG); -} - -Lisp_Object tracebyteoptrest1(Lisp_Object def, Lisp_Object a) -{ - return tracebyteoptrestn(def, 1, a); -} - -Lisp_Object tracebyteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return tracebyteoptrestn(def, 2, a, b); -} - -static Lisp_Object vtracebyterestn(Lisp_Object def, int nargs, - va_list a, Lisp_Object dflt) -{ - Lisp_Object r; - Lisp_Object nil = C_nil; - int i, wantargs, wantopts; - Lisp_Object *stack_save = stack; - push3(litvec, codevec, def); - if (nargs != 0) push_args(a, nargs); - else va_end(a); - stackcheck1(stack-stack_save, def); - r = qcar(def); - wantargs = ((unsigned char *)data_of_bps(r))[0]; - wantopts = ((unsigned char *)data_of_bps(r))[1]; - if (nargs < wantargs) - { popv(nargs+2); - return error(2, err_wrong_no_args, name_from(def), - fixnum_of_int((int32)nargs)); - } - while (nargs < wantargs+wantopts) - { push(dflt); /* Provide value for all optional args */ - nargs++; - } - { Lisp_Object rest = nil; - while (nargs > wantargs+wantopts) - { Lisp_Object w = stack[0]; - stack[0] = def; - rest = cons(w, rest); - errexitn(nargs+2); - pop(def); - nargs--; - } - push(rest); - nargs++; - } - stackcheck1(stack-stack_save, def); - freshline_trace(); - loop_print_trace(name_from(def)); - trace_printf(" (%d args)\n", nargs); - for (i=1; i<=nargs; i++) - { trace_printf("Arg%d: ", i); - loop_print_trace(stack[i-nargs]); - trace_printf("\n"); - } - def = stack[-nargs]; - r = qcar(def); - r = bytestream_interpret(r, qcdr(def), stack-nargs); - nil = C_nil; - if (exception_pending()) - { flip_exception(); - stack += nargs; - if ((exit_reason & UNWIND_ERROR) != 0) - for (i=1; i<=nargs; i++) - { err_printf("Arg%d: ", i); - loop_print_error(stack[i-nargs]); err_printf("\n"); - ignore_exception(); - } - popv(nargs+1); pop2(codevec, litvec); - flip_exception(); - return nil; - } -#ifdef COMMON - r = Lmv_list(nil, r); - if (exception_pending()) - { flip_exception(); - popv(1); pop2(codevec, litvec); - flip_exception(); - return nil; - } -#endif - pop(def); - push(r); - freshline_trace(); - loop_print_trace(name_from(def)); - nil = C_nil; - if (!exception_pending()) - { trace_printf(" = "); - loop_print_trace(r); - trace_printf("\n"); - } - if (exception_pending()) - { flip_exception(); - popv(1); pop2(codevec, litvec); - flip_exception(); - return nil; - } - pop3(r, codevec, litvec); -#ifdef COMMON - r = unpack_mv(nil, r); -#endif - return r; -} - -Lisp_Object MS_CDECL tracebyteoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vtracebyterestn(def, nargs, a, C_nil); -} - -Lisp_Object tracehardoptrest1(Lisp_Object def, Lisp_Object a) -{ - return tracehardoptrestn(def, 1, a); -} - -Lisp_Object tracehardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) -{ - return tracehardoptrestn(def, 2, a, b); -} - -Lisp_Object MS_CDECL tracehardoptrestn(Lisp_Object def, int nargs, ...) -{ - va_list a; - va_start(a, nargs); - return vtracebyterestn(def, nargs, a, SPID_NOARG); -} - -static Lisp_Object Lis_spid(Lisp_Object nil, Lisp_Object a) -{ /* Used in compilation for optional args */ - return onevalue(Lispify_predicate(is_spid(a))); -} - -static Lisp_Object Lspid_to_nil(Lisp_Object nil, Lisp_Object a) -{ /* Used in compilation for optional args */ - if (is_spid(a)) a = nil; - return onevalue(a); -} - -static Lisp_Object MS_CDECL Lload_spid(Lisp_Object nil, int nargs, ...) -{ /* Used in compilation of UNWIND-PROTECT */ - CSL_IGNORE(nil); - CSL_IGNORE(nargs); - return onevalue(SPID_PROTECT); -} - -Lisp_Object Lmv_list(Lisp_Object nil, Lisp_Object a) -/* - * This does a (multiple-value-list A) on just one form. It must be used - * carefully so that the value-count information does not get lost between - * the evaluation of A and calling this code. - */ -{ -#ifdef COMMON - Lisp_Object r, *save_stack = stack; - int i, x = exit_count; - stackcheck1(0, a); - if (x > 0) push(a); - for (i=2; i<=x; i++) push((&work_0)[i]); - r = nil; - for (i=0; i +#include +#include + +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "arith.h" +#include "entries.h" +#ifdef TIMEOUT +#include "timeout.h" +#endif + +#ifdef DEBUG +int trace_all = 0; +#endif + +#define name_from(def) elt(qcdr(def), 0) + +static void trace_entering(char *s) +{ + int i; + for (i=0; i 3 args not doubled\n"); + r = bytestream_interpret(r-1, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop2(codevec, litvec); + return r; +} + + +/* + * The code that follows is just used to support compiled code that + * has &optional or &rest arguments. + */ + +Lisp_Object byteopt1(Lisp_Object def, Lisp_Object a) +{ + return byteoptn(def, 1, a); +} + +Lisp_Object byteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return byteoptn(def, 2, a, b); +} + +static Lisp_Object vbyteoptn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push2(litvec, codevec); +/* + * Maybe I should raise an exception (continuable error) if too many args + * are provided - for now I just silently ignore the excess. + */ + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs || nargs > wantargs+wantopts) + { popv(nargs); pop2(codevec, litvec) + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + stackcheck1(stack-stack_save, def); + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop2(codevec, litvec); + return r; +} + +Lisp_Object MS_CDECL byteoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vbyteoptn(def, nargs, a, C_nil); +} + +Lisp_Object hardopt1(Lisp_Object def, Lisp_Object a) +{ + return hardoptn(def, 1, a); +} + +Lisp_Object hardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return hardoptn(def, 2, a, b); +} + +Lisp_Object MS_CDECL hardoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vbyteoptn(def, nargs, a, SPID_NOARG); +} + +Lisp_Object byteoptrest1(Lisp_Object def, Lisp_Object a) +{ + return byteoptrestn(def, 1, a); +} + +Lisp_Object byteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return byteoptrestn(def, 2, a, b); +} + +static Lisp_Object vbyterestn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push2(litvec, codevec); + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs) + { popv(nargs+2); + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + { Lisp_Object rest = nil; + while (nargs > wantargs+wantopts) + { Lisp_Object w = stack[0]; + stack[0] = def; + rest = cons(w, rest); + errexitn(nargs+2); + pop(def); + nargs--; + } + push(rest); + nargs++; + } + stackcheck1(stack-stack_save, def); + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop2(codevec, litvec); + return r; +} + +Lisp_Object MS_CDECL byteoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vbyterestn(def, nargs, a, C_nil); +} + +Lisp_Object hardoptrest1(Lisp_Object def, Lisp_Object a) +{ + return hardoptrestn(def, 1, a); +} + +Lisp_Object hardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return hardoptrestn(def, 2, a, b); +} + +Lisp_Object MS_CDECL hardoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vbyterestn(def, nargs, a, SPID_NOARG); +} + +/* + * Next the execution-doubling versions of the &opt/&rest interfaces + */ + +Lisp_Object double_byteopt1(Lisp_Object def, Lisp_Object a) +{ + return double_byteoptn(def, 1, a); +} + +Lisp_Object double_byteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return double_byteoptn(def, 2, a, b); +} + +static Lisp_Object double_vbyteoptn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push2(litvec, codevec); +/* + * Maybe I should raise an exception (continuable error) if too many args + * are provided - for now I just silently ignore th excess. + */ + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs || nargs > wantargs+wantopts) + { popv(nargs); pop2(codevec, litvec) + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + stackcheck1(stack-stack_save, def); + trace_printf("Function with simple &opt arg not doubled\n"); + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop2(codevec, litvec); + return r; +} + +Lisp_Object MS_CDECL double_byteoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return double_vbyteoptn(def, nargs, a, C_nil); +} + +Lisp_Object double_hardopt1(Lisp_Object def, Lisp_Object a) +{ + return double_hardoptn(def, 1, a); +} + +Lisp_Object double_hardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return double_hardoptn(def, 2, a, b); +} + +Lisp_Object MS_CDECL double_hardoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return double_vbyteoptn(def, nargs, a, SPID_NOARG); +} + +Lisp_Object double_byteoptrest1(Lisp_Object def, Lisp_Object a) +{ + return double_byteoptrestn(def, 1, a); +} + +Lisp_Object double_byteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return double_byteoptrestn(def, 2, a, b); +} + +static Lisp_Object double_vbyterestn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push2(litvec, codevec); + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs) + { popv(nargs+2); + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + { Lisp_Object rest = nil; + while (nargs > wantargs+wantopts) + { Lisp_Object w = stack[0]; + stack[0] = def; + rest = cons(w, rest); + errexitn(nargs+2); + pop(def); + nargs--; + } + push(rest); + nargs++; + } + stackcheck1(stack-stack_save, def); + trace_printf("Function with simple &rest arg not doubled\n"); + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop2(codevec, litvec); + return r; +} + +Lisp_Object MS_CDECL double_byteoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return double_vbyterestn(def, nargs, a, C_nil); +} + +Lisp_Object double_hardoptrest1(Lisp_Object def, Lisp_Object a) +{ + return double_hardoptrestn(def, 1, a); +} + +Lisp_Object double_hardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return double_hardoptrestn(def, 2, a, b); +} + +Lisp_Object MS_CDECL double_hardoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return double_vbyterestn(def, nargs, a, SPID_NOARG); +} + +Lisp_Object tracebyteopt1(Lisp_Object def, Lisp_Object a) +{ + return tracebyteoptn(def, 1, a); +} + +Lisp_Object tracebyteopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return tracebyteoptn(def, 2, a, b); +} + +static Lisp_Object vtracebyteoptn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push3(litvec, codevec, def); +/* + * Maybe I should raise an exception (continuable error) if too many args + * are provided - for now I just silently ignore th excess. + */ + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs || nargs > wantargs+wantopts) + { popv(nargs+1); pop2(codevec, litvec) + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + stackcheck1(stack-stack_save, def); + freshline_trace(); + loop_print_trace(name_from(def)); + trace_printf(" (%d args)\n", nargs); + for (i=1; i<=nargs; i++) + { trace_printf("Arg%d: ", i); + loop_print_trace(stack[i-nargs]); + trace_printf("\n"); + } + def = stack[-nargs]; + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs+1); pop2(codevec, litvec); + flip_exception(); + return nil; + } +#ifdef COMMON + r = Lmv_list(nil, r); + if (exception_pending()) + { flip_exception(); + popv(1); pop2(codevec, litvec); + flip_exception(); + return nil; + } +#endif + pop(def); + push(r); + freshline_trace(); + loop_print_trace(name_from(def)); + nil = C_nil; + if (!exception_pending()) + { trace_printf(" = "); + loop_print_trace(r); + trace_printf("\n"); + } + if (exception_pending()) + { flip_exception(); + popv(1); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop3(r, codevec, litvec); +#ifdef COMMON + r = unpack_mv(nil, r); +#endif + return r; +} + +Lisp_Object MS_CDECL tracebyteoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vtracebyteoptn(def, nargs, a, C_nil); +} + +Lisp_Object tracehardopt1(Lisp_Object def, Lisp_Object a) +{ + return tracehardoptn(def, 1, a); +} + +Lisp_Object tracehardopt2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return tracehardoptn(def, 2, a, b); +} + +Lisp_Object MS_CDECL tracehardoptn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vtracebyteoptn(def, nargs, a, SPID_NOARG); +} + +Lisp_Object tracebyteoptrest1(Lisp_Object def, Lisp_Object a) +{ + return tracebyteoptrestn(def, 1, a); +} + +Lisp_Object tracebyteoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return tracebyteoptrestn(def, 2, a, b); +} + +static Lisp_Object vtracebyterestn(Lisp_Object def, int nargs, + va_list a, Lisp_Object dflt) +{ + Lisp_Object r; + Lisp_Object nil = C_nil; + int i, wantargs, wantopts; + Lisp_Object *stack_save = stack; + push3(litvec, codevec, def); + if (nargs != 0) push_args(a, nargs); + else va_end(a); + stackcheck1(stack-stack_save, def); + r = qcar(def); + wantargs = ((unsigned char *)data_of_bps(r))[0]; + wantopts = ((unsigned char *)data_of_bps(r))[1]; + if (nargs < wantargs) + { popv(nargs+2); + return error(2, err_wrong_no_args, name_from(def), + fixnum_of_int((int32)nargs)); + } + while (nargs < wantargs+wantopts) + { push(dflt); /* Provide value for all optional args */ + nargs++; + } + { Lisp_Object rest = nil; + while (nargs > wantargs+wantopts) + { Lisp_Object w = stack[0]; + stack[0] = def; + rest = cons(w, rest); + errexitn(nargs+2); + pop(def); + nargs--; + } + push(rest); + nargs++; + } + stackcheck1(stack-stack_save, def); + freshline_trace(); + loop_print_trace(name_from(def)); + trace_printf(" (%d args)\n", nargs); + for (i=1; i<=nargs; i++) + { trace_printf("Arg%d: ", i); + loop_print_trace(stack[i-nargs]); + trace_printf("\n"); + } + def = stack[-nargs]; + r = qcar(def); + r = bytestream_interpret(r, qcdr(def), stack-nargs); + nil = C_nil; + if (exception_pending()) + { flip_exception(); + stack += nargs; + if ((exit_reason & UNWIND_ERROR) != 0) + for (i=1; i<=nargs; i++) + { err_printf("Arg%d: ", i); + loop_print_error(stack[i-nargs]); err_printf("\n"); + ignore_exception(); + } + popv(nargs+1); pop2(codevec, litvec); + flip_exception(); + return nil; + } +#ifdef COMMON + r = Lmv_list(nil, r); + if (exception_pending()) + { flip_exception(); + popv(1); pop2(codevec, litvec); + flip_exception(); + return nil; + } +#endif + pop(def); + push(r); + freshline_trace(); + loop_print_trace(name_from(def)); + nil = C_nil; + if (!exception_pending()) + { trace_printf(" = "); + loop_print_trace(r); + trace_printf("\n"); + } + if (exception_pending()) + { flip_exception(); + popv(1); pop2(codevec, litvec); + flip_exception(); + return nil; + } + pop3(r, codevec, litvec); +#ifdef COMMON + r = unpack_mv(nil, r); +#endif + return r; +} + +Lisp_Object MS_CDECL tracebyteoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vtracebyterestn(def, nargs, a, C_nil); +} + +Lisp_Object tracehardoptrest1(Lisp_Object def, Lisp_Object a) +{ + return tracehardoptrestn(def, 1, a); +} + +Lisp_Object tracehardoptrest2(Lisp_Object def, Lisp_Object a, Lisp_Object b) +{ + return tracehardoptrestn(def, 2, a, b); +} + +Lisp_Object MS_CDECL tracehardoptrestn(Lisp_Object def, int nargs, ...) +{ + va_list a; + va_start(a, nargs); + return vtracebyterestn(def, nargs, a, SPID_NOARG); +} + +static Lisp_Object Lis_spid(Lisp_Object nil, Lisp_Object a) +{ /* Used in compilation for optional args */ + return onevalue(Lispify_predicate(is_spid(a))); +} + +static Lisp_Object Lspid_to_nil(Lisp_Object nil, Lisp_Object a) +{ /* Used in compilation for optional args */ + if (is_spid(a)) a = nil; + return onevalue(a); +} + +static Lisp_Object MS_CDECL Lload_spid(Lisp_Object nil, int nargs, ...) +{ /* Used in compilation of UNWIND-PROTECT */ + CSL_IGNORE(nil); + CSL_IGNORE(nargs); + return onevalue(SPID_PROTECT); +} + +Lisp_Object Lmv_list(Lisp_Object nil, Lisp_Object a) +/* + * This does a (multiple-value-list A) on just one form. It must be used + * carefully so that the value-count information does not get lost between + * the evaluation of A and calling this code. + */ +{ +#ifdef COMMON + Lisp_Object r, *save_stack = stack; + int i, x = exit_count; + stackcheck1(0, a); + if (x > 0) push(a); + for (i=2; i<=x; i++) push((&work_0)[i]); + r = nil; + for (i=0; i= stacklimit) \ - { reclaim(nil, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck1(k, a1) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { a1 = reclaim(a1, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck2(k, a1, a2) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push(a2); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck3(k, a1, a2, a3) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push2(a2, a3); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop2(a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck4(k, a1, a2, a3, a4) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push3(a2, a3, a4); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop3(a4, a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#else /* SOFTWARE_TICKS */ - -#define stackcheck0(k) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if (stack >= stacklimit) \ - { reclaim(nil, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck1(k, a1) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if (stack >= stacklimit) \ - { a1 = reclaim(a1, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck2(k, a1, a2) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if (stack >= stacklimit) \ - { push(a2); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck3(k, a1, a2, a3) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if (stack >= stacklimit) \ - { push2(a2, a3); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop2(a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck4(k, a1, a2, a3, a4) \ - if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ - if (stack >= stacklimit) \ - { push3(a2, a3, a4); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop3(a4, a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#endif /* SOFTWARE_TICKS */ - -#else /* CHECK_STACK */ - -#ifdef SOFTWARE_TICKS - -extern DLLexport int32 countdown; -#ifdef INITIAL_SOFTWARE_TICKS -extern DLLexport int32 software_ticks; -#endif -extern DLLexport int deal_with_tick(void); - -#define stackcheck0(k) \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { reclaim(nil, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck1(k, a1) \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { a1 = reclaim(a1, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck2(k, a1, a2) \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push(a2); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck3(k, a1, a2, a3) \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push2(a2, a3); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop2(a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck4(k, a1, a2, a3, a4) \ - if ((--countdown < 0 && deal_with_tick()) || \ - stack >= stacklimit) \ - { push3(a2, a3, a4); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop3(a4, a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#else /* SOFTWARE_TICKS */ - -#define stackcheck0(k) \ - if (stack >= stacklimit) \ - { reclaim(nil, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck1(k, a1) \ - if (stack >= stacklimit) \ - { a1 = reclaim(a1, "stack", GC_STACK, 0); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck2(k, a1, a2) \ - if (stack >= stacklimit) \ - { push(a2); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck3(k, a1, a2, a3) \ - if (stack >= stacklimit) \ - { push2(a2, a3); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop2(a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#define stackcheck4(k, a1, a2, a3, a4) \ - if (stack >= stacklimit) \ - { push3(a2, a3, a4); \ - a1 = reclaim(a1, "stack", GC_STACK, 0); \ - pop3(a4, a3, a2); \ - nil = C_nil; \ - if (exception_pending()) { popv(k); return nil; } \ - } - -#endif /* SOFTWARE_TICKS */ -#endif /* CHECK_STACK */ - -/* - * As well as being used to point directly to the major Lisp item NIL, - * this register is used as a base for a table of other critically - * important other Lisp values. Offsets for at least some of these are - * defined here. - * I also need a proper C external variable holding the value of NIL since - * when called from the C library (e.g. in a signal handler) the global - * register variable will not be available! - */ - -extern DLLexport Lisp_Object C_nil; - -/* - * In COMMON mode the symbol-head for NIL uses the first few offsets - * from NIL here, so I start storing system variables at offset 12 so - * that even if at some stage I expand the size of all identifiers from the - * present state I will be safe. - */ - -#define first_nil_offset 50 /* GC collector marks from here up */ - -/* - * A vector of 50 words is used by the interpreter when preparing args - * for functions and when handling multiple values. - */ - -#define work_0_offset 200 - -/* Garbage collector marks up to but not including last_nil_offset */ -#define last_nil_offset 251 - -/* - * NIL_SEGMENT_SIZE must be over-large by enough to allow for - * space lost while rounding nil up to be a multiple of 8. Also in the - * Common Lisp case I need to give myself a spare word BEFORE the place - * where C_nil points. - */ -#define NIL_SEGMENT_SIZE (last_nil_offset*sizeof(Lisp_Object) + 32) - -/* - * I give myself a margin of SPARE bytes at the end of a page so that I can - * always CONS that amount (even without a garbage collection check) and not - * corrupt anything. The main use for this is that sometimes I need to - * convert a set of multiple values or of arguments from values on the - * (C-) stack or wherever va_arg() can find them into a list structure, and - * to avoid horrible potential problems with a garbage collection spotting] - * an exception (notably a ^C interrupt), running arbitrary code in an - * exception ghandler and then continuing, I need to cons those things up - * without any possible GC. The function cons_no_gc does that, and - * I should then call cons_gc_test() afterwards to regularise the situation. - * 512 bytes here leaves room for 64 conses, and I support at most 50 - * (multiple-) values so I hope this is safe. - */ - -#define SPARE 512 - -#ifdef NILSEG_EXTERNS -/* - * One some computers (ones with plenty of registers, and where the - * main addressing mode is register-indexed, and where optimising - * an compiler can keep variables in registers all the time, it will - * be most efficient to put major system variables addressed as offsets - * from NIL, where I expect to keep nil in a register variable pretty - * well always. On other machines (notable the Intel 80286) that policy - * gives pretty disasterous code, and the use of direct simple external - * variables will win. In PRESERVE and RESTORE I will have to copy - * all the separate external variables into a compact block for - * transfer to and from files. Actually on many (most?) machines the - * choice of whether this option should be enabled or not will be pretty - * marginal and should really be sorted out by building once with - * NILSEG_EXTERNS and once without, and comparing the performance of the - * two resulting systems. - */ - -#define nil_as_base - -extern unsigned32 byteflip; - -extern Lisp_Object codefringe; -extern Lisp_Object volatile codelimit; - -extern Lisp_Object * volatile stacklimit; - -extern Lisp_Object fringe; -extern Lisp_Object volatile heaplimit; - -extern Lisp_Object volatile vheaplimit; -extern Lisp_Object vfringe; - -extern int32 nwork; - -extern int32 exit_reason; -extern DLLexport int32 exit_count; -extern unsigned32 gensym_ser, print_precision, miscflags; -extern int32 current_modulus, fastget_size, package_bits; - -extern DLLexport Lisp_Object lisp_true, lambda, funarg, unset_var, opt_key, rest_key; -extern DLLexport Lisp_Object quote_symbol, function_symbol, comma_symbol; -extern DLLexport Lisp_Object comma_at_symbol, cons_symbol, eval_symbol; -extern DLLexport Lisp_Object work_symbol, evalhook, applyhook, macroexpand_hook; -extern DLLexport Lisp_Object append_symbol, exit_tag, exit_value, catch_tags; -extern DLLexport Lisp_Object current_package, startfn; -extern DLLexport Lisp_Object gensym_base, string_char_sym, boffo; -extern DLLexport Lisp_Object err_table; -extern DLLexport Lisp_Object progn_symbol; -extern DLLexport Lisp_Object lisp_work_stream, charvec, raise_symbol, lower_symbol; -extern DLLexport Lisp_Object echo_symbol, codevec, litvec, supervisor, B_reg; -extern DLLexport Lisp_Object savedef, comp_symbol, compiler_symbol, faslvec; -extern DLLexport Lisp_Object tracedfn, lisp_terminal_io; -extern DLLexport Lisp_Object lisp_standard_output, lisp_standard_input, lisp_error_output; -extern DLLexport Lisp_Object lisp_trace_output, lisp_debug_io, lisp_query_io; -extern DLLexport Lisp_Object prompt_thing, faslgensyms; -extern DLLexport Lisp_Object prinl_symbol, emsg_star, redef_msg; -extern DLLexport Lisp_Object expr_symbol, fexpr_symbol, macro_symbol; -extern DLLexport Lisp_Object cl_symbols, active_stream, current_module; -extern DLLexport Lisp_Object features_symbol, lisp_package; -extern DLLexport Lisp_Object sys_hash_table, help_index, cfunarg, lex_words; -extern DLLexport Lisp_Object get_counts, fastget_names, input_libraries; -extern DLLexport Lisp_Object output_library, current_file, break_function; -extern DLLexport Lisp_Object standard_output, standard_input, debug_io; -extern DLLexport Lisp_Object error_output, query_io, terminal_io; -extern DLLexport Lisp_Object trace_output, fasl_stream; - -#ifdef COMMON -extern DLLexport Lisp_Object keyword_package; -extern DLLexport Lisp_Object all_packages, package_symbol, internal_symbol; -extern DLLexport Lisp_Object external_symbol, inherited_symbol; -extern DLLexport Lisp_Object key_key, allow_other_keys, aux_key; -extern DLLexport Lisp_Object format_symbol; -extern DLLexport Lisp_Object expand_def_symbol, allow_key_key, declare_symbol; -extern DLLexport Lisp_Object special_symbol; -#endif -extern DLLexport Lisp_Object native_code, native_symbol, traceprint_symbol; -extern DLLexport Lisp_Object loadsource_symbol; -extern DLLexport Lisp_Object hankaku_symbol; - -extern Lisp_Object workbase[51]; - -extern DLLexport Lisp_Object user_base_0, user_base_1, user_base_2; -extern DLLexport Lisp_Object user_base_3, user_base_4, user_base_5; -extern DLLexport Lisp_Object user_base_6, user_base_7, user_base_8; -extern DLLexport Lisp_Object user_base_9; - -#define work_0 workbase[0] -#define work_1 workbase[1] -#define mv_1 workbase[1] -#define mv_2 workbase[2] -#define mv_3 workbase[3] -#define work_50 workbase[50] - -#else /* NILSEG_EXTERNS */ - -#define nil_as_base Lisp_Object nil = C_nil; - -#define byteflip (*(unsigned32 *)&((Lisp_Object *)nil)[12]) -#define codefringe ((Lisp_Object *)nil)[13] -#define codelimit ((Lisp_Object volatile *)nil)[14] -/* - * On a machine where sizeof(void *)=8 and alignment matters I need to arrange for - * stacklimit to be properly aligned. Also I MUST do the address calculation - * in a way that does not get muddled by the "sizeof(void *)" issue. I - * reserve nilseg offsets 15, 16 and 17 for this. - */ -#ifdef COMMON -#define stacklimit (*(Lisp_Object * volatile *) \ - &((Lisp_Object *)nil)[16]) -#else -#define stacklimit (*(Lisp_Object * volatile *) \ - &((Lisp_Object *)nil)[15]) -#endif -#define fringe ((Lisp_Object *)nil)[18] -#define heaplimit ((Lisp_Object volatile *)nil)[19] -#define vheaplimit ((Lisp_Object volatile *)nil)[20] -#define vfringe ((Lisp_Object *)nil)[21] -#define miscflags (*(unsigned32 *)&((Lisp_Object *)nil)[22]) - -#define nwork (*(int32 *)&((Lisp_Object *)nil)[24]) -#define exit_reason (*(int32 *)&((Lisp_Object *)nil)[25]) -#define exit_count (*(int32 *)&((Lisp_Object *)nil)[26]) -#define gensym_ser (*(unsigned32 *)&((Lisp_Object *)nil)[27]) -#define print_precision (*(unsigned32 *)&((Lisp_Object *)nil)[28]) -#define current_modulus (*(int32 *)&((Lisp_Object *)nil)[29]) -#define fastget_size (*(int32 *)&((Lisp_Object *)nil)[30]) -#define package_bits (*(int32 *)&((Lisp_Object *)nil)[31]) -/* offsets 32-49 spare at present */ - -/* Offset 50 used for EQ hash table list */ -/* Offset 51 used for EQUAL hash table list */ -#define current_package ((Lisp_Object *)nil)[52] -/* current_package is treated specially by the garbage collector */ - -#define B_reg ((Lisp_Object *)nil)[53] -#define codevec ((Lisp_Object *)nil)[54] -#define litvec ((Lisp_Object *)nil)[55] -#define exit_tag ((Lisp_Object *)nil)[56] -#define exit_value ((Lisp_Object *)nil)[57] -#define catch_tags ((Lisp_Object *)nil)[58] -#define lisp_package ((Lisp_Object *)nil)[59] -#define boffo ((Lisp_Object *)nil)[60] -#define charvec ((Lisp_Object *)nil)[61] -#define sys_hash_table ((Lisp_Object *)nil)[62] -#define help_index ((Lisp_Object *)nil)[63] -#define gensym_base ((Lisp_Object *)nil)[64] -#define err_table ((Lisp_Object *)nil)[65] -#define supervisor ((Lisp_Object *)nil)[66] -#define startfn ((Lisp_Object *)nil)[67] -#define faslvec ((Lisp_Object *)nil)[68] -#define tracedfn ((Lisp_Object *)nil)[69] -#define prompt_thing ((Lisp_Object *)nil)[70] -#define faslgensyms ((Lisp_Object *)nil)[71] -#define cl_symbols ((Lisp_Object *)nil)[72] -#define active_stream ((Lisp_Object *)nil)[73] -#define current_module ((Lisp_Object *)nil)[74] -/* - * 75-89 spare for workspace-style locations - */ -#define append_symbol ((Lisp_Object *)nil)[90] -#define applyhook ((Lisp_Object *)nil)[91] -#define cfunarg ((Lisp_Object *)nil)[92] -#define comma_at_symbol ((Lisp_Object *)nil)[93] -#define comma_symbol ((Lisp_Object *)nil)[94] -#define compiler_symbol ((Lisp_Object *)nil)[95] -#define comp_symbol ((Lisp_Object *)nil)[96] -#define cons_symbol ((Lisp_Object *)nil)[97] -#define echo_symbol ((Lisp_Object *)nil)[98] -#define emsg_star ((Lisp_Object *)nil)[99] -#define evalhook ((Lisp_Object *)nil)[100] -#define eval_symbol ((Lisp_Object *)nil)[101] -#define expr_symbol ((Lisp_Object *)nil)[102] -#define features_symbol ((Lisp_Object *)nil)[103] -#define fexpr_symbol ((Lisp_Object *)nil)[104] -#define funarg ((Lisp_Object *)nil)[105] -#define function_symbol ((Lisp_Object *)nil)[106] -#define lambda ((Lisp_Object *)nil)[107] -#define lisp_true ((Lisp_Object *)nil)[108] -#define lower_symbol ((Lisp_Object *)nil)[109] -#define macroexpand_hook ((Lisp_Object *)nil)[110] -#define macro_symbol ((Lisp_Object *)nil)[111] -#define opt_key ((Lisp_Object *)nil)[112] -#define prinl_symbol ((Lisp_Object *)nil)[113] -#define progn_symbol ((Lisp_Object *)nil)[114] -#define quote_symbol ((Lisp_Object *)nil)[115] -#define raise_symbol ((Lisp_Object *)nil)[116] -#define redef_msg ((Lisp_Object *)nil)[117] -#define rest_key ((Lisp_Object *)nil)[118] -#define savedef ((Lisp_Object *)nil)[119] -#define string_char_sym ((Lisp_Object *)nil)[120] -#define unset_var ((Lisp_Object *)nil)[121] -#define work_symbol ((Lisp_Object *)nil)[122] -#define lex_words ((Lisp_Object *)nil)[123] -#define get_counts ((Lisp_Object *)nil)[124] -#define fastget_names ((Lisp_Object *)nil)[125] -#define input_libraries ((Lisp_Object *)nil)[126] -#define output_library ((Lisp_Object *)nil)[127] -#define current_file ((Lisp_Object *)nil)[128] -#define break_function ((Lisp_Object *)nil)[129] - -#define lisp_work_stream ((Lisp_Object *)nil)[130] -#define lisp_standard_output ((Lisp_Object *)nil)[131] -#define lisp_standard_input ((Lisp_Object *)nil)[132] -#define lisp_debug_io ((Lisp_Object *)nil)[133] -#define lisp_error_output ((Lisp_Object *)nil)[134] -#define lisp_query_io ((Lisp_Object *)nil)[135] -#define lisp_terminal_io ((Lisp_Object *)nil)[136] -#define lisp_trace_output ((Lisp_Object *)nil)[137] -#define standard_output ((Lisp_Object *)nil)[138] -#define standard_input ((Lisp_Object *)nil)[139] -#define debug_io ((Lisp_Object *)nil)[140] -#define error_output ((Lisp_Object *)nil)[141] -#define query_io ((Lisp_Object *)nil)[142] -#define terminal_io ((Lisp_Object *)nil)[143] -#define trace_output ((Lisp_Object *)nil)[144] -#define fasl_stream ((Lisp_Object *)nil)[145] -#define native_code ((Lisp_Object *)nil)[146] -#define native_symbol ((Lisp_Object *)nil)[147] -#define traceprint_symbol ((Lisp_Object *)nil)[148] -#define loadsource_symbol ((Lisp_Object *)nil)[149] -#define hankaku_symbol ((Lisp_Object *)nil)[150] - -#ifdef COMMON -#define keyword_package ((Lisp_Object *)nil)[170] -#define all_packages ((Lisp_Object *)nil)[171] -#define package_symbol ((Lisp_Object *)nil)[172] -#define internal_symbol ((Lisp_Object *)nil)[173] -#define external_symbol ((Lisp_Object *)nil)[174] -#define inherited_symbol ((Lisp_Object *)nil)[175] -#define key_key ((Lisp_Object *)nil)[176] -#define allow_other_keys ((Lisp_Object *)nil)[177] -#define aux_key ((Lisp_Object *)nil)[178] -#define format_symbol ((Lisp_Object *)nil)[179] -#define expand_def_symbol ((Lisp_Object *)nil)[180] -#define allow_key_key ((Lisp_Object *)nil)[181] -#define declare_symbol ((Lisp_Object *)nil)[182] -#define special_symbol ((Lisp_Object *)nil)[183] -#endif - - - -/* - * The next are intended for use by people building custom versions - * of CSL. They are always handled as if NILSEG_EXTERNS had been set, - * even if it had not, since that gives the user direct access to them as - * simple C variables. Note that they must ALWAYS be kept with proper - * valid Lisp objects in them. - */ -/* #define user_base_0 ((Lisp_Object *)nil)[190] */ -/* #define user_base_1 ((Lisp_Object *)nil)[191] */ -/* #define user_base_2 ((Lisp_Object *)nil)[192] */ -/* #define user_base_3 ((Lisp_Object *)nil)[193] */ -/* #define user_base_4 ((Lisp_Object *)nil)[194] */ -/* #define user_base_5 ((Lisp_Object *)nil)[195] */ -/* #define user_base_6 ((Lisp_Object *)nil)[196] */ -/* #define user_base_7 ((Lisp_Object *)nil)[197] */ -/* #define user_base_8 ((Lisp_Object *)nil)[198] */ -/* #define user_base_9 ((Lisp_Object *)nil)[199] */ - -extern DLLexport Lisp_Object user_base_0, user_base_1, user_base_2; -extern DLLexport Lisp_Object user_base_3, user_base_4, user_base_5; -extern DLLexport Lisp_Object user_base_6, user_base_7, user_base_8; -extern DLLexport Lisp_Object user_base_9; - -#define work_0 ((Lisp_Object *)nil)[200] -#define work_1 ((Lisp_Object *)nil)[201] -#define mv_1 work_1 -#define mv_2 ((Lisp_Object *)nil)[202] -#define mv_3 ((Lisp_Object *)nil)[203] -#define work_50 ((Lisp_Object *)nil)[250] - -#endif /*NILSEG_EXTERNS */ - -/* dummy_function_call is only used to patch around C compiler bugs! */ -extern void MS_CDECL dummy_function_call(char *why, ...); - -extern void copy_into_nilseg(int fg); -extern void copy_out_of_nilseg(int fg); - -#define eq_hash_table_list ((Lisp_Object *)nil)[50] /* In heap image */ -#define equal_hash_table_list ((Lisp_Object *)nil)[51] /* In heap image */ -#define current_package_offset 52 - -extern void rehash_this_table(Lisp_Object v); -extern Lisp_Object eq_hash_tables, equal_hash_tables; - -/* - * The following are used to help processing. - */ -extern Lisp_Object volatile savecodelimit; -extern Lisp_Object * volatile savestacklimit; -extern Lisp_Object volatile saveheaplimit; -extern Lisp_Object volatile savevheaplimit; -extern char *exit_charvec; - -#ifdef DEBUG -extern int trace_all; -#endif - -extern int trace_depth; - -#define MAX_INPUT_FILES 40 /* limit on command-line length */ -#define MAX_SYMBOLS_TO_DEFINE 40 -#define MAX_FASL_PATHS 20 - -extern char *files_to_read[MAX_INPUT_FILES], - *symbols_to_define[MAX_SYMBOLS_TO_DEFINE], - *fasl_paths[MAX_FASL_PATHS]; -extern int fasl_output_file, output_directory; -extern FILE *binary_read_file; - -#ifndef COMMON -#ifdef CWIN -extern char **loadable_packages; -extern char **switches; -#endif -#endif - -#ifdef SOCKETS -extern int sockets_ready; -extern void flush_socket(); -#endif - -extern CSLbool undefine_this_one[MAX_SYMBOLS_TO_DEFINE]; - -extern int number_of_input_files, - number_of_symbols_to_define, - number_of_fasl_paths, - init_flags; - -extern int native_code_tag; - -extern char *standard_directory; - -extern CSLbool gc_method; -extern int32 gc_number; - -#define INIT_QUIET 1 -#define INIT_VERBOSE 2 -#define INIT_EXPANDABLE 4 - -#define Lispify_predicate(p) ((p) ? lisp_true : nil) - -/* - * variables used by the IO system. - */ - -extern int tty_count; -extern FILE *spool_file; -extern char spool_file_name[32]; - -typedef struct Ihandle -{ - FILE *f; /* File within which this sub-file lives */ - long int o; /* Offset (as returned by ftell) */ - long int n; /* Number of bytes remaining unread here */ - unsigned32 chk; /* Checksum */ - int status; /* Reading or Writing */ -} Ihandle; - -/* - * If there is no more than 100 bytes of data then I will deem - * file compression frivolous. The compression code assumes that - * it has at least 2 bytes to work on, so do NOT cut this limit down to zero. - * Indeed more than that the limit must be greater than the length of - * the initial header record (112 bytes). - */ - -extern int32 compression_worth_while; -#define CODESIZE 0x1000 - -typedef struct entry_point -{ - void *p; - char *s; -} entry_point; - -#ifdef CJAVA -#define entry_table_size 132 -#else -#define entry_table_size 127 -#endif -extern entry_point entries_table[]; - -extern int doubled_execution; - -#ifdef MEMORY_TRACE -extern int32 memory_base, memory_size; -extern unsigned char *memory_map; -extern FILE *memory_file; -extern void memory_comment(int n); -#endif - -#define ARG_CUT_OFF 25 -extern void push_args(va_list a, int nargs); -extern void push_args_1(va_list a, int nargs); - -extern void Iinit(void); -extern void IreInit(void); -extern void Icontext(Ihandle *); -extern void Irestore_context(Ihandle); -extern void Ilist(void); -extern CSLbool Iopen(char *name, int len, CSLbool dirn, char *expanded_name); -extern CSLbool Iopen_from_stdin(); -extern CSLbool IopenRoot(char *expanded_name, int hard); -extern CSLbool Iwriterootp(char *expanded); -extern CSLbool Iopen_help(int32 offset); -extern CSLbool Iopen_banner(int code); -extern CSLbool Imodulep(char *name, int len, char *datestamp, int32 *size, - char *expanded_name); -extern CSLbool Icopy(char *name, int len); -extern CSLbool Idelete(char *name, int len); -extern CSLbool IcloseInput(int check_checksum); -extern CSLbool IcloseOutput(); -extern CSLbool Ifinished(void); -extern int Igetc(void); -extern int32 Iread(void *buff, int32 size); -extern CSLbool Iputc(int ch); -extern CSLbool Iwrite(void *buff, int32 size); -extern long int Ioutsize(void); - -/* - * I will allow myself 192 bytes to store registration information. - * In my initial implementation I will only use a fraction of that - * but it seems safer to design the structure with extra room for potential - * enhancements. I will keep a version code in the data so that I can update - * my methods but still preserve upwards compatibility when I do that. - */ -#define REGISTRATION_SIZE 192 -#define REGISTRATION_VERSION "r1.0" -extern unsigned char registration_data[REGISTRATION_SIZE]; -extern void MD5_Init(); -extern void MD5_Update(unsigned char *data, int len); -extern void MD5_Final(unsigned char *md); -extern CSLbool MD5_busy; -extern unsigned char *MD5(unsigned char *data, int n, unsigned char *md); -extern void checksum(Lisp_Object a); -extern unsigned char unpredictable[256]; -extern void inject_randomness(int n); -/* - * crypt_init() seeds the encryption engine that I used, and then - * crypt_get_block() gets a chunk of the sequence, which I can XOR with - * text to mess it up. - */ -extern void crypt_init(char *key); -#define CRYPT_BLOCK 128 -extern void crypt_get_block(unsigned char result[CRYPT_BLOCK]); -/* - * crypt_active is -ve if none is in use, otherwise it is a key identifier - * (to allow for possibly multiple keys). crypt_buffer & crypt_count are - * things filled in by crypt_get_block(). The encryption stuff here is just - * for protection of the software, and the code that does somewhat more - * serious encryption to create the keys used with this stream cipher live - * elsewhere. The crypto technology in CSL is only used on image files, ie - * chunks of compiled code etc, and no provision has been made to use it - * on user data-files. I can store up to CRYPT_KEYS different keys with - * a CSL system and have different modules protected by different ones of - * them. - */ -#define CRYPT_KEYS 10 -extern char *crypt_keys[CRYPT_KEYS]; -extern int crypt_active; -extern unsigned char *crypt_buffer; -extern int crypt_count; - -extern void ensure_screen(void); -extern int window_heading; -#ifndef WINDOW_SYSTEM -#ifdef BUFFERED_STDOUT -extern clock_t last_flush; -#endif -#define start_up_window_manager(a) {} -#endif -extern void my_exit(int n); -extern void *my_malloc(size_t n); - -extern clock_t base_time; -extern double *clock_stack; -extern void push_clock(void); -extern double pop_clock(void); -extern double consolidated_time[10], gc_time; -extern CSLbool volatile already_in_gc, tick_on_gc_exit; -extern CSLbool volatile interrupt_pending, tick_pending, polltick_pending; -extern int current_fp_rep; -#ifndef __cplusplus -extern jmp_buf *errorset_buffer; -#endif -extern char *errorset_msg; -extern int errorset_code; -extern void unwind_stack(Lisp_Object *, CSLbool findcatch); -extern CSLbool segvtrap; -extern CSLbool batch_flag; -extern int escaped_printing; -#ifdef __WATCOMC__ -extern void low_level_signal_handler(int code); -#else -extern void MS_CDECL low_level_signal_handler(int code); -#endif -extern void MS_CDECL sigint_handler(int code); -#ifdef CHECK_STACK -extern int check_stack(char *file, int line); -#endif - -#ifdef RECORD_GET -extern void record_get(Lisp_Object tag, CSLbool found); -#endif - -/* - * Functions used internally - not to be installed in Lisp function - * cells, but some of these may end up getting called using special - * non-standard conventions when the Lisp compiler has been at work. - */ - -extern void adjust_all(); -extern void set_up_functions(CSLbool restartp); -extern void get_user_files_checksum(unsigned char *); -extern DLLexport Lisp_Object acons(Lisp_Object a, Lisp_Object b, Lisp_Object c); -extern DLLexport Lisp_Object ash(Lisp_Object a, Lisp_Object b); -extern Lisp_Object bytestream_interpret(Lisp_Object code, Lisp_Object lit, - Lisp_Object *entry_stack); -extern CSLbool complex_stringp(Lisp_Object a); -extern void freshline_trace(); -extern void freshline_debug(); -extern DLLexport Lisp_Object cons(Lisp_Object a, Lisp_Object b); -extern Lisp_Object cons_no_gc(Lisp_Object a, Lisp_Object b); -extern Lisp_Object cons_gc_test(Lisp_Object a); -extern void convert_fp_rep(void *p, int old_rep, int new_rep, int type); -extern DLLexport Lisp_Object Ceval(Lisp_Object u, Lisp_Object env); -extern unsigned32 Crand(void); -extern DLLexport Lisp_Object Cremainder(Lisp_Object a, Lisp_Object b); -extern void Csrand(unsigned32 a, unsigned32 b); -extern void discard(Lisp_Object a); -extern DLLexport CSLbool eql_fn(Lisp_Object a, Lisp_Object b); -extern DLLexport CSLbool cl_equal_fn(Lisp_Object a, Lisp_Object b); -extern DLLexport CSLbool equal_fn(Lisp_Object a, Lisp_Object b); -#ifdef TRACED_EQUAL -extern DLLexport CSLbool traced_equal_fn(Lisp_Object a, Lisp_Object b, - char *, int, int); -#define equal_fn(a, b) traced_equal_fn(a, b, __FILE__, __LINE__, 0) -extern void dump_equals(); -#endif -extern DLLexport CSLbool equalp(Lisp_Object a, Lisp_Object b); -extern DLLexport Lisp_Object apply(Lisp_Object fn, int nargs, - Lisp_Object env, Lisp_Object fname); -extern DLLexport Lisp_Object apply_lambda(Lisp_Object def, int nargs, - Lisp_Object env, Lisp_Object name); -extern void deallocate_pages(void); -extern void drop_heap_segments(void); -extern DLLexport Lisp_Object gcd(Lisp_Object a, Lisp_Object b); -extern Lisp_Object get_pname(Lisp_Object a); -#ifdef COMMON -extern DLLexport Lisp_Object get(Lisp_Object a, Lisp_Object b, Lisp_Object c); -#else -extern DLLexport Lisp_Object get(Lisp_Object a, Lisp_Object b); -#endif -extern Lisp_Object getvector(int tag, int32 type, int32 length); -extern Lisp_Object getvector_init(int32 n, Lisp_Object v); -extern Lisp_Object getcodevector(int32 type, int32 size); -extern unsigned32 hash_lisp_string(Lisp_Object s); -extern void lose_C_def(Lisp_Object a); -extern DLLexport CSLbool geq2(Lisp_Object a, Lisp_Object b); -extern DLLexport CSLbool greaterp2(Lisp_Object a, Lisp_Object b); -extern DLLexport CSLbool lesseq2(Lisp_Object a, Lisp_Object b); -extern DLLexport CSLbool lessp2(Lisp_Object a, Lisp_Object b); -extern DLLexport Lisp_Object list2(Lisp_Object a, Lisp_Object b); -extern DLLexport Lisp_Object list2star(Lisp_Object a, Lisp_Object b, Lisp_Object c); -extern DLLexport Lisp_Object list3(Lisp_Object a, Lisp_Object b, Lisp_Object c); -extern DLLexport Lisp_Object lognot(Lisp_Object a); -extern DLLexport Lisp_Object macroexpand(Lisp_Object form, Lisp_Object env); -extern Lisp_Object make_one_word_bignum(int32 n); -extern Lisp_Object make_package(Lisp_Object name); -extern Lisp_Object make_string(char *b); -extern Lisp_Object make_nstring(char *b, int32 n); -extern Lisp_Object make_undefined_symbol(char const *s); -extern Lisp_Object make_symbol(char const *s, int restartp, - one_args *f1, two_args *f2, n_args *fn); -extern DLLexport void MS_CDECL stdout_printf(char *fmt, ...); -extern DLLexport void MS_CDECL term_printf(char *fmt, ...); -extern DLLexport void MS_CDECL err_printf(char *fmt, ...); -extern DLLexport void MS_CDECL debug_printf(char *fmt, ...); -extern DLLexport void MS_CDECL trace_printf(char *fmt, ...); -extern char *my_getenv(char *name); -extern DLLexport Lisp_Object ncons(Lisp_Object a); -extern DLLexport Lisp_Object ndelete(Lisp_Object a, Lisp_Object b); -extern DLLexport Lisp_Object negate(Lisp_Object a); -extern DLLexport Lisp_Object nreverse(Lisp_Object a); -extern FILE *open_file(char *filename, char *original_name, - size_t n, char *dirn, FILE *old_file); -extern DLLexport Lisp_Object plus2(Lisp_Object a, Lisp_Object b); -extern void preserve(char *msg); -extern void preserve_native_code(); -extern void relocate_native_function(unsigned char *bps); -extern Lisp_Object prin(Lisp_Object u); -extern char *get_string_data(Lisp_Object a, char *why, int32 *len); -extern DLLexport void prin_to_stdout(Lisp_Object u); -extern DLLexport void prin_to_terminal(Lisp_Object u); -extern DLLexport void prin_to_debug(Lisp_Object u); -extern DLLexport void prin_to_query(Lisp_Object u); -extern DLLexport void prin_to_trace(Lisp_Object u); -extern DLLexport void prin_to_error(Lisp_Object u); -extern DLLexport void loop_print_stdout(Lisp_Object o); -extern DLLexport void loop_print_terminal(Lisp_Object o); -extern DLLexport void loop_print_debug(Lisp_Object o); -extern DLLexport void loop_print_query(Lisp_Object o); -extern DLLexport void loop_print_trace(Lisp_Object o); -extern DLLexport void loop_print_error(Lisp_Object o); -extern void internal_prin(Lisp_Object u, int prefix); -extern DLLexport Lisp_Object princ(Lisp_Object u); -extern DLLexport Lisp_Object print(Lisp_Object u); -extern DLLexport Lisp_Object printc(Lisp_Object u); -extern void print_bignum(Lisp_Object u, CSLbool blankp, int nobreak); -extern void print_bighexoctbin(Lisp_Object u, - int radix, int width, CSLbool blankp, int nobreak); -extern DLLexport Lisp_Object putprop(Lisp_Object a, Lisp_Object b, - Lisp_Object c); -extern DLLexport Lisp_Object quot2(Lisp_Object a, Lisp_Object b); -extern DLLexport Lisp_Object rational(Lisp_Object a); -extern void read_eval_print(int noisy); -extern DLLexport Lisp_Object reclaim(Lisp_Object value_to_return, char *why, - int stg_class, int32 size); -extern CSLbool do_not_kill_native_code; -extern void set_fns(Lisp_Object sym, one_args *f1, - two_args *f2, n_args *fn); -extern void setup(int restartp, double storesize); -extern Lisp_Object simplify_string(Lisp_Object s); -extern CSLbool stringp(Lisp_Object a); -extern DLLexport Lisp_Object times2(Lisp_Object a, Lisp_Object b); -extern int32 thirty_two_bits(Lisp_Object a); - -#ifdef DEMO_MODE -extern void give_up(); -#endif -#ifdef DEMO_BUILD -extern int32 demo_key1, demo_key2; -#endif - -/* - * The next few provide support for multiple values. - */ -#ifdef COMMON -#define onevalue(r) (exit_count=1, (r)) -#define nvalues(r, n) (exit_count=(n), (r)) -#else -#define onevalue(r) (r) -#define nvalues(r, n) (r) -#endif - -#ifdef COMMON -#define eval(a, b) Ceval(a, b) -#define voideval(a, b) Ceval(a, b) -#else -/* - * I lift the top test from eval out to be in-line so that I can - * (rather often) avoid the overhead of a procedure call when return from - * it will be almost immediate. The effect is that in CSL mode Ceval is - * only ever called on a list. NB the first arg to eval gets evaluated - * several times here - maybe I will just hope that CSE optimisation picks - * up this sort of repetition... - */ -#define eval(a, b) \ - (is_cons(a) ? Ceval(a, b) : \ - is_symbol(a) ? (qvalue(a) == unset_var ? error(1, err_unset_var, a) : \ - onevalue(qvalue(a))) : \ - onevalue(a)) -/* voideval(a, b) is like (void)eval(a, b) */ -#define voideval(a, b) \ - if (is_cons(a)) Ceval(a, b) /* Beware "else" after this */ -#endif - -/* - * The function "equal" seems to be pretty critical (certainly for Standard - * Lisp mode and Reduce). So I write out the top-level part of it in-line - * and only call the (messy) function in cases where it might be worth-while. - * For Common Lisp I will presumably look at eql and cl_equal as well. - * The test here says: - * If a and b are EQ then they are EQUAL, - * else if a and b have different types they are not EQUAL - * else if a has type 1, 2, 3 or 4 (ie fixnum, odds, sfloat, symbol) - * then they are not EQUAL (those types need to be EQ to be EQUAL) - * otherwise call equal_fn(a, b) to decide the issue. - */ -#define equal(a, b) \ - ((a) == (b) || \ - (((((a) ^ (b)) & TAG_BITS) == 0) && \ - ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ - equal_fn(a, b))) - -#define cl_equal(a, b) \ - ((a) == (b) || \ - (((((a) ^ (b)) & TAG_BITS) == 0) && \ - ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ - cl_equal_fn(a, b))) - -#define eql(a, b) \ - ((a) == (b) || \ - (((((a) ^ (b)) & TAG_BITS) == 0) && \ - ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ - eql_fn(a, b))) - -/* - * Helpers for the bignum arithmetic code... - */ - -#ifndef IMULTIPLY -extern unsigned32 Imultiply(unsigned32 *rlow, unsigned32 a, - unsigned32 b, unsigned32 c); -#endif -#ifndef IDIVIDE -extern unsigned32 Idivide(unsigned32 *qp, unsigned32 a, - unsigned32 b, unsigned32 c); -extern unsigned32 Idiv10_9(unsigned32 *qp, unsigned32 a, unsigned32 b); -#endif - -/* - * UNSAFE removes some checks - but it does noy seem to make much difference - * so I rather strongly suggest that you do not enable it! - */ -#ifdef UNSAFE -# define argcheck(var, n, msg) (var) = (var); -#else -# define argcheck(var, n, msg) if ((var)!=(n)) return aerror(msg); -#endif - -extern n_args *zero_arg_functions[]; -extern one_args *one_arg_functions[]; -extern two_args *two_arg_functions[]; -extern n_args *three_arg_functions[]; -extern void *useful_functions[]; -extern char *address_of_var(int n); - -typedef struct setup_type -{ - char *name; - one_args *one; - two_args *two; - n_args *n; -} setup_type; - -extern setup_type const - arith06_setup[], arith08_setup[], arith10_setup[], arith12_setup[], - char_setup[], eval1_setup[], eval2_setup[], eval3_setup[], - funcs1_setup[], funcs2_setup[], funcs3_setup[], print_setup[], - read_setup[], mpi_setup[]; -extern setup_type const - u01_setup[], u02_setup[], u03_setup[], u04_setup[], - u05_setup[], u06_setup[], u07_setup[], u08_setup[], - u09_setup[], u10_setup[], u11_setup[], u12_setup[]; -#ifdef NAG -extern setup_type const nag_setup[], asp_setup[]; -extern setup_type const socket_setup[], xdr_setup[], grep_setup[]; -extern setup_type const gr_setup[], axfns_setup[]; -#endif - -extern char *find_image_directory(int argc, char *argv[]); -extern char program_name[64]; -extern Lisp_Object declare_fn(Lisp_Object args, Lisp_Object env); -extern Lisp_Object function_fn(Lisp_Object args, Lisp_Object env); -extern Lisp_Object let_fn_1(Lisp_Object bvl, Lisp_Object body, - Lisp_Object env, int compilerp); -extern Lisp_Object mv_call_fn(Lisp_Object args, Lisp_Object env); -extern Lisp_Object progn_fn(Lisp_Object args, Lisp_Object env); -extern Lisp_Object quote_fn(Lisp_Object args, Lisp_Object env); -extern Lisp_Object tagbody_fn(Lisp_Object args, Lisp_Object env); - -#ifdef __cplusplus -} -#endif - -/* - * Now declare entrypoints to machine-dependent code fragments... - */ - -#include "sys.h" - -#endif /* header_externs_h */ - -/* end of externs.h */ +/* externs.h Copyright (C) Codemist 1989-99 */ + +/* + * Main batch of extern declarations. Must have tags.h loaded first. + * + */ + +/* Signature: 7754c8eb 07-Mar-2000 */ + +#ifndef header_externs_h +#define header_externs_h 1 + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef USE_MPI +#include "mpi.h" +extern int32 mpi_rank,mpi_size; + +#ifdef MEMORY_TRACE +#define my_pop() (memory_reference((int32)stack), (*stack--)) +#else +#define my_pop() (*stack--) +#endif + +#endif /* USE_MPI */ + + +extern void **pages, + **heap_pages, **vheap_pages, + **bps_pages, **native_pages; +#ifndef NO_COPYING_GC +extern void **new_heap_pages, **new_vheap_pages, + **new_bps_pages, **new_native_pages; +#endif +extern int32 pages_count, + heap_pages_count, vheap_pages_count, + bps_pages_count, native_pages_count; +#ifndef NO_COPYING_GC +extern int32 new_heap_pages_count, new_vheap_pages_count, + new_bps_pages_count, new_native_pages_count; +#endif + +extern int native_pages_changed; +extern int32 native_fringe; + +extern Lisp_Object *nilsegment, *stacksegment; +extern Lisp_Object *stackbase; +extern int32 stack_segsize; /* measured in units of one CSL page */ +extern DLLexport Lisp_Object *C_stack; +#define stack C_stack + +#ifdef MEMORY_TRACE + +#define push(a) { *++stack = (a); memory_reference((int32)stack); } +/* push2 etc are just like push, but grouped together */ +#define push2(a,b) { *++stack = (a); memory_reference((int32)stack); *++stack = (b); memory_reference((int32)stack); } +#define push3(a,b,c) { *++stack = (a); memory_reference((int32)stack); *++stack = (b); memory_reference((int32)stack); *++stack = (c); memory_reference((int32)stack); } +#define push4(a,b,c,d) { *++stack = (a); memory_reference((int32)stack); *++stack = (b); memory_reference((int32)stack); *++stack = (c); memory_reference((int32)stack); \ + *++stack = (d); memory_reference((int32)stack); } +#define push5(a,b,c,d,e){ *++stack = (a); memory_reference((int32)stack); *++stack = (b); memory_reference((int32)stack); *++stack = (c); memory_reference((int32)stack); \ + *++stack = (d); memory_reference((int32)stack); *++stack = (e); memory_reference((int32)stack); } +#define push6(a,b,c,d,e,f) {push3(a,b,c); push3(d,e,f)} + +#define pop(a) { memory_reference((int32)stack); (a) = *stack--; } +#define pop2(a,b) { memory_reference((int32)stack); (a) = *stack--; memory_reference((int32)stack); (b) = *stack--; } +#define pop3(a,b,c) { memory_reference((int32)stack); (a) = *stack--; memory_reference((int32)stack); (b) = *stack--; memory_reference((int32)stack); (c) = *stack--; } +#define pop4(a,b,c,d) { memory_reference((int32)stack); (a) = *stack--; memory_reference((int32)stack); (b) = *stack--; memory_reference((int32)stack); (c) = *stack--; \ + memory_reference((int32)stack); (d) = *stack--; } +#define pop5(a,b,c,d,e) { memory_reference((int32)stack); (a) = *stack--; memory_reference((int32)stack); (b) = *stack--; memory_reference((int32)stack); (c) = *stack--; \ + memory_reference((int32)stack); (d) = *stack--; memory_reference((int32)stack); (e) = *stack--; } +#define pop6(a,b,c,d,e,f) {pop3(a,b,c); pop3(d,e,f)} +#define popv(n) stack -= (n); + +#else /* MEMORY_TRACE */ + +#define push(a) { *++stack = (a); } +/* push2 etc are just like push, but grouped together */ +#ifdef USE_AUTOINDEX +/* + * Having inspected the code generated by one of the C compilers that + * is frequently used with this Lisp it emerges that the multiple + * push operations might sometimes be much better treated with + * the increment parts explicitly consolidated into one. To leave + * scope for fine-tuning to cmpiler and machine architecture the + * USE_AUTOINDEX macro could be pre-defined and I suspect that on + * VAX and ARM computers it may make good sense. + */ +#define push2(a,b) { *++stack = (a); *++stack = (b); } +#define push3(a,b,c) { *++stack = (a); *++stack = (b); *++stack = (c); } +#define push4(a,b,c,d) { *++stack = (a); *++stack = (b); *++stack = (c); \ + *++stack = (d); } +#define push5(a,b,c,d,e){ *++stack = (a); *++stack = (b); *++stack = (c); \ + *++stack = (d); *++stack = (e); } +#define push6(a,b,c,d,e,f) {push3(a,b,c); push3(d,e,f)} + +#define pop(a) { (a) = *stack--; } +#define pop2(a,b) { (a) = *stack--; (b) = *stack--; } +#define pop3(a,b,c) { (a) = *stack--; (b) = *stack--; (c) = *stack--; } +#define pop4(a,b,c,d) { (a) = *stack--; (b) = *stack--; (c) = *stack--; \ + (d) = *stack--; } +#define pop5(a,b,c,d,e) { (a) = *stack--; (b) = *stack--; (c) = *stack--; \ + (d) = *stack--; (e) = *stack--; } +#define pop6(a,b,c,d,e,f) {pop3(a,b,c); pop3(d,e,f)} +#define popv(n) stack -= (n); +#else /* USE_AUTOINDEX */ +#define push2(a,b) { stack[1] = (a); stack[2] = (b); stack += 2; } +#define push3(a,b,c) { stack[1] = (a); stack[2] = (b); stack[3] = (c); \ + stack += 3; } +#define push4(a,b,c,d) { stack[1] = (a); stack[2] = (b); stack[3] = (c); \ + stack[4] = (d); stack += 4; } +#define push5(a,b,c,d,e){ stack[1] = (a); stack[2] = (b); stack[3] = (c); \ + stack[4] = (d); stack[5] = (e); stack += 5; } +#define push6(a,b,c,d,e,f) { \ + stack[1] = (a); stack[2] = (b); stack[3] = (c); \ + stack[4] = (d); stack[5] = (e); stack[6] = (f); \ + stack += 6; } + +#define pop(a) { (a) = *stack--; } +#define pop2(a,b) { stack -= 2; (a) = stack[2]; (b) = stack[1]; } +#define pop3(a,b,c) { stack -= 3; (a) = stack[3]; (b) = stack[2]; \ + (c) = stack[1]; } +#define pop4(a,b,c,d) { stack -= 4; (a) = stack[4]; (b) = stack[3]; \ + (c) = stack[2]; (d) = stack[1]; } +#define pop5(a,b,c,d,e) { stack -= 5; (a) = stack[5]; (b) = stack[4]; \ + (c) = stack[3]; (d) = stack[2]; (e) = stack[1]; } +#define pop6(a,b,c,d,e, f) { stack -= 6; \ + (a) = stack[6]; (b) = stack[5]; (c) = stack[4]; \ + (d) = stack[3]; (e) = stack[2]; (f) = stack[1]; } +#define popv(n) stack -= (n); +#endif /* USE_AUTOINDEX */ +#endif /* MEMORY_TRACE*/ + +#define errexit() { nil = C_nil; if (exception_pending()) return nil; } +#define errexitn(n) { nil = C_nil; \ + if (exception_pending()) { popv(n); return nil; } } +#define errexitv() { nil = C_nil; if (exception_pending()) return; } +#define errexitvn(n) { nil = C_nil; \ + if (exception_pending()) { popv(n); return; } } + +#define GC_USER_SOFT 0 +#define GC_USER_HARD 1 +#define GC_STACK 2 +#define GC_CONS 3 +#define GC_VEC 4 +#define GC_BPS 5 +#define GC_PRESERVE 6 +#define GC_NATIVE 7 + + +#ifdef CHECK_STACK + +#ifdef SOFTWARE_TICKS + +extern DLLexport int32 countdown; +#ifdef INITIAL_SOFTWARE_TICKS +extern DLLexport int32 software_ticks; +#endif +extern DLLexport int deal_with_tick(void); + +#define stackcheck0(k) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { reclaim(nil, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck1(k, a1) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { a1 = reclaim(a1, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck2(k, a1, a2) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push(a2); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck3(k, a1, a2, a3) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push2(a2, a3); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop2(a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck4(k, a1, a2, a3, a4) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push3(a2, a3, a4); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop3(a4, a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#else /* SOFTWARE_TICKS */ + +#define stackcheck0(k) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if (stack >= stacklimit) \ + { reclaim(nil, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck1(k, a1) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if (stack >= stacklimit) \ + { a1 = reclaim(a1, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck2(k, a1, a2) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if (stack >= stacklimit) \ + { push(a2); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck3(k, a1, a2, a3) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if (stack >= stacklimit) \ + { push2(a2, a3); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop2(a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck4(k, a1, a2, a3, a4) \ + if (check_stack(__FILE__,__LINE__)) return aerror("stack overflow"); \ + if (stack >= stacklimit) \ + { push3(a2, a3, a4); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop3(a4, a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#endif /* SOFTWARE_TICKS */ + +#else /* CHECK_STACK */ + +#ifdef SOFTWARE_TICKS + +extern DLLexport int32 countdown; +#ifdef INITIAL_SOFTWARE_TICKS +extern DLLexport int32 software_ticks; +#endif +extern DLLexport int deal_with_tick(void); + +#define stackcheck0(k) \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { reclaim(nil, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck1(k, a1) \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { a1 = reclaim(a1, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck2(k, a1, a2) \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push(a2); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck3(k, a1, a2, a3) \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push2(a2, a3); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop2(a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck4(k, a1, a2, a3, a4) \ + if ((--countdown < 0 && deal_with_tick()) || \ + stack >= stacklimit) \ + { push3(a2, a3, a4); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop3(a4, a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#else /* SOFTWARE_TICKS */ + +#define stackcheck0(k) \ + if (stack >= stacklimit) \ + { reclaim(nil, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck1(k, a1) \ + if (stack >= stacklimit) \ + { a1 = reclaim(a1, "stack", GC_STACK, 0); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck2(k, a1, a2) \ + if (stack >= stacklimit) \ + { push(a2); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); pop(a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck3(k, a1, a2, a3) \ + if (stack >= stacklimit) \ + { push2(a2, a3); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop2(a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#define stackcheck4(k, a1, a2, a3, a4) \ + if (stack >= stacklimit) \ + { push3(a2, a3, a4); \ + a1 = reclaim(a1, "stack", GC_STACK, 0); \ + pop3(a4, a3, a2); \ + nil = C_nil; \ + if (exception_pending()) { popv(k); return nil; } \ + } + +#endif /* SOFTWARE_TICKS */ +#endif /* CHECK_STACK */ + +/* + * As well as being used to point directly to the major Lisp item NIL, + * this register is used as a base for a table of other critically + * important other Lisp values. Offsets for at least some of these are + * defined here. + * I also need a proper C external variable holding the value of NIL since + * when called from the C library (e.g. in a signal handler) the global + * register variable will not be available! + */ + +extern DLLexport Lisp_Object C_nil; + +/* + * In COMMON mode the symbol-head for NIL uses the first few offsets + * from NIL here, so I start storing system variables at offset 12 so + * that even if at some stage I expand the size of all identifiers from the + * present state I will be safe. + */ + +#define first_nil_offset 50 /* GC collector marks from here up */ + +/* + * A vector of 50 words is used by the interpreter when preparing args + * for functions and when handling multiple values. + */ + +#define work_0_offset 200 + +/* Garbage collector marks up to but not including last_nil_offset */ +#define last_nil_offset 251 + +/* + * NIL_SEGMENT_SIZE must be over-large by enough to allow for + * space lost while rounding nil up to be a multiple of 8. Also in the + * Common Lisp case I need to give myself a spare word BEFORE the place + * where C_nil points. + */ +#define NIL_SEGMENT_SIZE (last_nil_offset*sizeof(Lisp_Object) + 32) + +/* + * I give myself a margin of SPARE bytes at the end of a page so that I can + * always CONS that amount (even without a garbage collection check) and not + * corrupt anything. The main use for this is that sometimes I need to + * convert a set of multiple values or of arguments from values on the + * (C-) stack or wherever va_arg() can find them into a list structure, and + * to avoid horrible potential problems with a garbage collection spotting] + * an exception (notably a ^C interrupt), running arbitrary code in an + * exception ghandler and then continuing, I need to cons those things up + * without any possible GC. The function cons_no_gc does that, and + * I should then call cons_gc_test() afterwards to regularise the situation. + * 512 bytes here leaves room for 64 conses, and I support at most 50 + * (multiple-) values so I hope this is safe. + */ + +#define SPARE 512 + +#ifdef NILSEG_EXTERNS +/* + * One some computers (ones with plenty of registers, and where the + * main addressing mode is register-indexed, and where optimising + * an compiler can keep variables in registers all the time, it will + * be most efficient to put major system variables addressed as offsets + * from NIL, where I expect to keep nil in a register variable pretty + * well always. On other machines (notable the Intel 80286) that policy + * gives pretty disasterous code, and the use of direct simple external + * variables will win. In PRESERVE and RESTORE I will have to copy + * all the separate external variables into a compact block for + * transfer to and from files. Actually on many (most?) machines the + * choice of whether this option should be enabled or not will be pretty + * marginal and should really be sorted out by building once with + * NILSEG_EXTERNS and once without, and comparing the performance of the + * two resulting systems. + */ + +#define nil_as_base + +extern unsigned32 byteflip; + +extern Lisp_Object codefringe; +extern Lisp_Object volatile codelimit; + +extern Lisp_Object * volatile stacklimit; + +extern Lisp_Object fringe; +extern Lisp_Object volatile heaplimit; + +extern Lisp_Object volatile vheaplimit; +extern Lisp_Object vfringe; + +extern int32 nwork; + +extern int32 exit_reason; +extern DLLexport int32 exit_count; +extern unsigned32 gensym_ser, print_precision, miscflags; +extern int32 current_modulus, fastget_size, package_bits; + +extern DLLexport Lisp_Object lisp_true, lambda, funarg, unset_var, opt_key, rest_key; +extern DLLexport Lisp_Object quote_symbol, function_symbol, comma_symbol; +extern DLLexport Lisp_Object comma_at_symbol, cons_symbol, eval_symbol; +extern DLLexport Lisp_Object work_symbol, evalhook, applyhook, macroexpand_hook; +extern DLLexport Lisp_Object append_symbol, exit_tag, exit_value, catch_tags; +extern DLLexport Lisp_Object current_package, startfn; +extern DLLexport Lisp_Object gensym_base, string_char_sym, boffo; +extern DLLexport Lisp_Object err_table; +extern DLLexport Lisp_Object progn_symbol; +extern DLLexport Lisp_Object lisp_work_stream, charvec, raise_symbol, lower_symbol; +extern DLLexport Lisp_Object echo_symbol, codevec, litvec, supervisor, B_reg; +extern DLLexport Lisp_Object savedef, comp_symbol, compiler_symbol, faslvec; +extern DLLexport Lisp_Object tracedfn, lisp_terminal_io; +extern DLLexport Lisp_Object lisp_standard_output, lisp_standard_input, lisp_error_output; +extern DLLexport Lisp_Object lisp_trace_output, lisp_debug_io, lisp_query_io; +extern DLLexport Lisp_Object prompt_thing, faslgensyms; +extern DLLexport Lisp_Object prinl_symbol, emsg_star, redef_msg; +extern DLLexport Lisp_Object expr_symbol, fexpr_symbol, macro_symbol; +extern DLLexport Lisp_Object cl_symbols, active_stream, current_module; +extern DLLexport Lisp_Object features_symbol, lisp_package; +extern DLLexport Lisp_Object sys_hash_table, help_index, cfunarg, lex_words; +extern DLLexport Lisp_Object get_counts, fastget_names, input_libraries; +extern DLLexport Lisp_Object output_library, current_file, break_function; +extern DLLexport Lisp_Object standard_output, standard_input, debug_io; +extern DLLexport Lisp_Object error_output, query_io, terminal_io; +extern DLLexport Lisp_Object trace_output, fasl_stream; + +#ifdef COMMON +extern DLLexport Lisp_Object keyword_package; +extern DLLexport Lisp_Object all_packages, package_symbol, internal_symbol; +extern DLLexport Lisp_Object external_symbol, inherited_symbol; +extern DLLexport Lisp_Object key_key, allow_other_keys, aux_key; +extern DLLexport Lisp_Object format_symbol; +extern DLLexport Lisp_Object expand_def_symbol, allow_key_key, declare_symbol; +extern DLLexport Lisp_Object special_symbol; +#endif +extern DLLexport Lisp_Object native_code, native_symbol, traceprint_symbol; +extern DLLexport Lisp_Object loadsource_symbol; +extern DLLexport Lisp_Object hankaku_symbol; + +extern Lisp_Object workbase[51]; + +extern DLLexport Lisp_Object user_base_0, user_base_1, user_base_2; +extern DLLexport Lisp_Object user_base_3, user_base_4, user_base_5; +extern DLLexport Lisp_Object user_base_6, user_base_7, user_base_8; +extern DLLexport Lisp_Object user_base_9; + +#define work_0 workbase[0] +#define work_1 workbase[1] +#define mv_1 workbase[1] +#define mv_2 workbase[2] +#define mv_3 workbase[3] +#define work_50 workbase[50] + +#else /* NILSEG_EXTERNS */ + +#define nil_as_base Lisp_Object nil = C_nil; + +#define byteflip (*(unsigned32 *)&((Lisp_Object *)nil)[12]) +#define codefringe ((Lisp_Object *)nil)[13] +#define codelimit ((Lisp_Object volatile *)nil)[14] +/* + * On a machine where sizeof(void *)=8 and alignment matters I need to arrange for + * stacklimit to be properly aligned. Also I MUST do the address calculation + * in a way that does not get muddled by the "sizeof(void *)" issue. I + * reserve nilseg offsets 15, 16 and 17 for this. + */ +#ifdef COMMON +#define stacklimit (*(Lisp_Object * volatile *) \ + &((Lisp_Object *)nil)[16]) +#else +#define stacklimit (*(Lisp_Object * volatile *) \ + &((Lisp_Object *)nil)[15]) +#endif +#define fringe ((Lisp_Object *)nil)[18] +#define heaplimit ((Lisp_Object volatile *)nil)[19] +#define vheaplimit ((Lisp_Object volatile *)nil)[20] +#define vfringe ((Lisp_Object *)nil)[21] +#define miscflags (*(unsigned32 *)&((Lisp_Object *)nil)[22]) + +#define nwork (*(int32 *)&((Lisp_Object *)nil)[24]) +#define exit_reason (*(int32 *)&((Lisp_Object *)nil)[25]) +#define exit_count (*(int32 *)&((Lisp_Object *)nil)[26]) +#define gensym_ser (*(unsigned32 *)&((Lisp_Object *)nil)[27]) +#define print_precision (*(unsigned32 *)&((Lisp_Object *)nil)[28]) +#define current_modulus (*(int32 *)&((Lisp_Object *)nil)[29]) +#define fastget_size (*(int32 *)&((Lisp_Object *)nil)[30]) +#define package_bits (*(int32 *)&((Lisp_Object *)nil)[31]) +/* offsets 32-49 spare at present */ + +/* Offset 50 used for EQ hash table list */ +/* Offset 51 used for EQUAL hash table list */ +#define current_package ((Lisp_Object *)nil)[52] +/* current_package is treated specially by the garbage collector */ + +#define B_reg ((Lisp_Object *)nil)[53] +#define codevec ((Lisp_Object *)nil)[54] +#define litvec ((Lisp_Object *)nil)[55] +#define exit_tag ((Lisp_Object *)nil)[56] +#define exit_value ((Lisp_Object *)nil)[57] +#define catch_tags ((Lisp_Object *)nil)[58] +#define lisp_package ((Lisp_Object *)nil)[59] +#define boffo ((Lisp_Object *)nil)[60] +#define charvec ((Lisp_Object *)nil)[61] +#define sys_hash_table ((Lisp_Object *)nil)[62] +#define help_index ((Lisp_Object *)nil)[63] +#define gensym_base ((Lisp_Object *)nil)[64] +#define err_table ((Lisp_Object *)nil)[65] +#define supervisor ((Lisp_Object *)nil)[66] +#define startfn ((Lisp_Object *)nil)[67] +#define faslvec ((Lisp_Object *)nil)[68] +#define tracedfn ((Lisp_Object *)nil)[69] +#define prompt_thing ((Lisp_Object *)nil)[70] +#define faslgensyms ((Lisp_Object *)nil)[71] +#define cl_symbols ((Lisp_Object *)nil)[72] +#define active_stream ((Lisp_Object *)nil)[73] +#define current_module ((Lisp_Object *)nil)[74] +/* + * 75-89 spare for workspace-style locations + */ +#define append_symbol ((Lisp_Object *)nil)[90] +#define applyhook ((Lisp_Object *)nil)[91] +#define cfunarg ((Lisp_Object *)nil)[92] +#define comma_at_symbol ((Lisp_Object *)nil)[93] +#define comma_symbol ((Lisp_Object *)nil)[94] +#define compiler_symbol ((Lisp_Object *)nil)[95] +#define comp_symbol ((Lisp_Object *)nil)[96] +#define cons_symbol ((Lisp_Object *)nil)[97] +#define echo_symbol ((Lisp_Object *)nil)[98] +#define emsg_star ((Lisp_Object *)nil)[99] +#define evalhook ((Lisp_Object *)nil)[100] +#define eval_symbol ((Lisp_Object *)nil)[101] +#define expr_symbol ((Lisp_Object *)nil)[102] +#define features_symbol ((Lisp_Object *)nil)[103] +#define fexpr_symbol ((Lisp_Object *)nil)[104] +#define funarg ((Lisp_Object *)nil)[105] +#define function_symbol ((Lisp_Object *)nil)[106] +#define lambda ((Lisp_Object *)nil)[107] +#define lisp_true ((Lisp_Object *)nil)[108] +#define lower_symbol ((Lisp_Object *)nil)[109] +#define macroexpand_hook ((Lisp_Object *)nil)[110] +#define macro_symbol ((Lisp_Object *)nil)[111] +#define opt_key ((Lisp_Object *)nil)[112] +#define prinl_symbol ((Lisp_Object *)nil)[113] +#define progn_symbol ((Lisp_Object *)nil)[114] +#define quote_symbol ((Lisp_Object *)nil)[115] +#define raise_symbol ((Lisp_Object *)nil)[116] +#define redef_msg ((Lisp_Object *)nil)[117] +#define rest_key ((Lisp_Object *)nil)[118] +#define savedef ((Lisp_Object *)nil)[119] +#define string_char_sym ((Lisp_Object *)nil)[120] +#define unset_var ((Lisp_Object *)nil)[121] +#define work_symbol ((Lisp_Object *)nil)[122] +#define lex_words ((Lisp_Object *)nil)[123] +#define get_counts ((Lisp_Object *)nil)[124] +#define fastget_names ((Lisp_Object *)nil)[125] +#define input_libraries ((Lisp_Object *)nil)[126] +#define output_library ((Lisp_Object *)nil)[127] +#define current_file ((Lisp_Object *)nil)[128] +#define break_function ((Lisp_Object *)nil)[129] + +#define lisp_work_stream ((Lisp_Object *)nil)[130] +#define lisp_standard_output ((Lisp_Object *)nil)[131] +#define lisp_standard_input ((Lisp_Object *)nil)[132] +#define lisp_debug_io ((Lisp_Object *)nil)[133] +#define lisp_error_output ((Lisp_Object *)nil)[134] +#define lisp_query_io ((Lisp_Object *)nil)[135] +#define lisp_terminal_io ((Lisp_Object *)nil)[136] +#define lisp_trace_output ((Lisp_Object *)nil)[137] +#define standard_output ((Lisp_Object *)nil)[138] +#define standard_input ((Lisp_Object *)nil)[139] +#define debug_io ((Lisp_Object *)nil)[140] +#define error_output ((Lisp_Object *)nil)[141] +#define query_io ((Lisp_Object *)nil)[142] +#define terminal_io ((Lisp_Object *)nil)[143] +#define trace_output ((Lisp_Object *)nil)[144] +#define fasl_stream ((Lisp_Object *)nil)[145] +#define native_code ((Lisp_Object *)nil)[146] +#define native_symbol ((Lisp_Object *)nil)[147] +#define traceprint_symbol ((Lisp_Object *)nil)[148] +#define loadsource_symbol ((Lisp_Object *)nil)[149] +#define hankaku_symbol ((Lisp_Object *)nil)[150] + +#ifdef COMMON +#define keyword_package ((Lisp_Object *)nil)[170] +#define all_packages ((Lisp_Object *)nil)[171] +#define package_symbol ((Lisp_Object *)nil)[172] +#define internal_symbol ((Lisp_Object *)nil)[173] +#define external_symbol ((Lisp_Object *)nil)[174] +#define inherited_symbol ((Lisp_Object *)nil)[175] +#define key_key ((Lisp_Object *)nil)[176] +#define allow_other_keys ((Lisp_Object *)nil)[177] +#define aux_key ((Lisp_Object *)nil)[178] +#define format_symbol ((Lisp_Object *)nil)[179] +#define expand_def_symbol ((Lisp_Object *)nil)[180] +#define allow_key_key ((Lisp_Object *)nil)[181] +#define declare_symbol ((Lisp_Object *)nil)[182] +#define special_symbol ((Lisp_Object *)nil)[183] +#endif + + + +/* + * The next are intended for use by people building custom versions + * of CSL. They are always handled as if NILSEG_EXTERNS had been set, + * even if it had not, since that gives the user direct access to them as + * simple C variables. Note that they must ALWAYS be kept with proper + * valid Lisp objects in them. + */ +/* #define user_base_0 ((Lisp_Object *)nil)[190] */ +/* #define user_base_1 ((Lisp_Object *)nil)[191] */ +/* #define user_base_2 ((Lisp_Object *)nil)[192] */ +/* #define user_base_3 ((Lisp_Object *)nil)[193] */ +/* #define user_base_4 ((Lisp_Object *)nil)[194] */ +/* #define user_base_5 ((Lisp_Object *)nil)[195] */ +/* #define user_base_6 ((Lisp_Object *)nil)[196] */ +/* #define user_base_7 ((Lisp_Object *)nil)[197] */ +/* #define user_base_8 ((Lisp_Object *)nil)[198] */ +/* #define user_base_9 ((Lisp_Object *)nil)[199] */ + +extern DLLexport Lisp_Object user_base_0, user_base_1, user_base_2; +extern DLLexport Lisp_Object user_base_3, user_base_4, user_base_5; +extern DLLexport Lisp_Object user_base_6, user_base_7, user_base_8; +extern DLLexport Lisp_Object user_base_9; + +#define work_0 ((Lisp_Object *)nil)[200] +#define work_1 ((Lisp_Object *)nil)[201] +#define mv_1 work_1 +#define mv_2 ((Lisp_Object *)nil)[202] +#define mv_3 ((Lisp_Object *)nil)[203] +#define work_50 ((Lisp_Object *)nil)[250] + +#endif /*NILSEG_EXTERNS */ + +/* dummy_function_call is only used to patch around C compiler bugs! */ +extern void MS_CDECL dummy_function_call(char *why, ...); + +extern void copy_into_nilseg(int fg); +extern void copy_out_of_nilseg(int fg); + +#define eq_hash_table_list ((Lisp_Object *)nil)[50] /* In heap image */ +#define equal_hash_table_list ((Lisp_Object *)nil)[51] /* In heap image */ +#define current_package_offset 52 + +extern void rehash_this_table(Lisp_Object v); +extern Lisp_Object eq_hash_tables, equal_hash_tables; + +/* + * The following are used to help processing. + */ +extern Lisp_Object volatile savecodelimit; +extern Lisp_Object * volatile savestacklimit; +extern Lisp_Object volatile saveheaplimit; +extern Lisp_Object volatile savevheaplimit; +extern char *exit_charvec; + +#ifdef DEBUG +extern int trace_all; +#endif + +extern int trace_depth; + +#define MAX_INPUT_FILES 40 /* limit on command-line length */ +#define MAX_SYMBOLS_TO_DEFINE 40 +#define MAX_FASL_PATHS 20 + +extern char *files_to_read[MAX_INPUT_FILES], + *symbols_to_define[MAX_SYMBOLS_TO_DEFINE], + *fasl_paths[MAX_FASL_PATHS]; +extern int fasl_output_file, output_directory; +extern FILE *binary_read_file; + +#ifndef COMMON +#ifdef CWIN +extern char **loadable_packages; +extern char **switches; +#endif +#endif + +#ifdef SOCKETS +extern int sockets_ready; +extern void flush_socket(); +#endif + +extern CSLbool undefine_this_one[MAX_SYMBOLS_TO_DEFINE]; + +extern int number_of_input_files, + number_of_symbols_to_define, + number_of_fasl_paths, + init_flags; + +extern int native_code_tag; + +extern char *standard_directory; + +extern CSLbool gc_method; +extern int32 gc_number; + +#define INIT_QUIET 1 +#define INIT_VERBOSE 2 +#define INIT_EXPANDABLE 4 + +#define Lispify_predicate(p) ((p) ? lisp_true : nil) + +/* + * variables used by the IO system. + */ + +extern int tty_count; +extern FILE *spool_file; +extern char spool_file_name[32]; + +typedef struct Ihandle +{ + FILE *f; /* File within which this sub-file lives */ + long int o; /* Offset (as returned by ftell) */ + long int n; /* Number of bytes remaining unread here */ + unsigned32 chk; /* Checksum */ + int status; /* Reading or Writing */ +} Ihandle; + +/* + * If there is no more than 100 bytes of data then I will deem + * file compression frivolous. The compression code assumes that + * it has at least 2 bytes to work on, so do NOT cut this limit down to zero. + * Indeed more than that the limit must be greater than the length of + * the initial header record (112 bytes). + */ + +extern int32 compression_worth_while; +#define CODESIZE 0x1000 + +typedef struct entry_point +{ + void *p; + char *s; +} entry_point; + +#ifdef CJAVA +#define entry_table_size 132 +#else +#define entry_table_size 127 +#endif +extern entry_point entries_table[]; + +extern int doubled_execution; + +#ifdef MEMORY_TRACE +extern int32 memory_base, memory_size; +extern unsigned char *memory_map; +extern FILE *memory_file; +extern void memory_comment(int n); +#endif + +#define ARG_CUT_OFF 25 +extern void push_args(va_list a, int nargs); +extern void push_args_1(va_list a, int nargs); + +extern void Iinit(void); +extern void IreInit(void); +extern void Icontext(Ihandle *); +extern void Irestore_context(Ihandle); +extern void Ilist(void); +extern CSLbool Iopen(char *name, int len, CSLbool dirn, char *expanded_name); +extern CSLbool Iopen_from_stdin(); +extern CSLbool IopenRoot(char *expanded_name, int hard); +extern CSLbool Iwriterootp(char *expanded); +extern CSLbool Iopen_help(int32 offset); +extern CSLbool Iopen_banner(int code); +extern CSLbool Imodulep(char *name, int len, char *datestamp, int32 *size, + char *expanded_name); +extern CSLbool Icopy(char *name, int len); +extern CSLbool Idelete(char *name, int len); +extern CSLbool IcloseInput(int check_checksum); +extern CSLbool IcloseOutput(); +extern CSLbool Ifinished(void); +extern int Igetc(void); +extern int32 Iread(void *buff, int32 size); +extern CSLbool Iputc(int ch); +extern CSLbool Iwrite(void *buff, int32 size); +extern long int Ioutsize(void); + +/* + * I will allow myself 192 bytes to store registration information. + * In my initial implementation I will only use a fraction of that + * but it seems safer to design the structure with extra room for potential + * enhancements. I will keep a version code in the data so that I can update + * my methods but still preserve upwards compatibility when I do that. + */ +#define REGISTRATION_SIZE 192 +#define REGISTRATION_VERSION "r1.0" +extern unsigned char registration_data[REGISTRATION_SIZE]; +extern void MD5_Init(); +extern void MD5_Update(unsigned char *data, int len); +extern void MD5_Final(unsigned char *md); +extern CSLbool MD5_busy; +extern unsigned char *MD5(unsigned char *data, int n, unsigned char *md); +extern void checksum(Lisp_Object a); +extern unsigned char unpredictable[256]; +extern void inject_randomness(int n); +/* + * crypt_init() seeds the encryption engine that I used, and then + * crypt_get_block() gets a chunk of the sequence, which I can XOR with + * text to mess it up. + */ +extern void crypt_init(char *key); +#define CRYPT_BLOCK 128 +extern void crypt_get_block(unsigned char result[CRYPT_BLOCK]); +/* + * crypt_active is -ve if none is in use, otherwise it is a key identifier + * (to allow for possibly multiple keys). crypt_buffer & crypt_count are + * things filled in by crypt_get_block(). The encryption stuff here is just + * for protection of the software, and the code that does somewhat more + * serious encryption to create the keys used with this stream cipher live + * elsewhere. The crypto technology in CSL is only used on image files, ie + * chunks of compiled code etc, and no provision has been made to use it + * on user data-files. I can store up to CRYPT_KEYS different keys with + * a CSL system and have different modules protected by different ones of + * them. + */ +#define CRYPT_KEYS 10 +extern char *crypt_keys[CRYPT_KEYS]; +extern int crypt_active; +extern unsigned char *crypt_buffer; +extern int crypt_count; + +extern void ensure_screen(void); +extern int window_heading; +#ifndef WINDOW_SYSTEM +#ifdef BUFFERED_STDOUT +extern clock_t last_flush; +#endif +#define start_up_window_manager(a) {} +#endif +extern void my_exit(int n); +extern void *my_malloc(size_t n); + +extern clock_t base_time; +extern double *clock_stack; +extern void push_clock(void); +extern double pop_clock(void); +extern double consolidated_time[10], gc_time; +extern CSLbool volatile already_in_gc, tick_on_gc_exit; +extern CSLbool volatile interrupt_pending, tick_pending, polltick_pending; +extern int current_fp_rep; +#ifndef __cplusplus +extern jmp_buf *errorset_buffer; +#endif +extern char *errorset_msg; +extern int errorset_code; +extern void unwind_stack(Lisp_Object *, CSLbool findcatch); +extern CSLbool segvtrap; +extern CSLbool batch_flag; +extern int escaped_printing; +#ifdef __WATCOMC__ +extern void low_level_signal_handler(int code); +#else +extern void MS_CDECL low_level_signal_handler(int code); +#endif +extern void MS_CDECL sigint_handler(int code); +#ifdef CHECK_STACK +extern int check_stack(char *file, int line); +#endif + +#ifdef RECORD_GET +extern void record_get(Lisp_Object tag, CSLbool found); +#endif + +/* + * Functions used internally - not to be installed in Lisp function + * cells, but some of these may end up getting called using special + * non-standard conventions when the Lisp compiler has been at work. + */ + +extern void adjust_all(); +extern void set_up_functions(CSLbool restartp); +extern void get_user_files_checksum(unsigned char *); +extern DLLexport Lisp_Object acons(Lisp_Object a, Lisp_Object b, Lisp_Object c); +extern DLLexport Lisp_Object ash(Lisp_Object a, Lisp_Object b); +extern Lisp_Object bytestream_interpret(Lisp_Object code, Lisp_Object lit, + Lisp_Object *entry_stack); +extern CSLbool complex_stringp(Lisp_Object a); +extern void freshline_trace(); +extern void freshline_debug(); +extern DLLexport Lisp_Object cons(Lisp_Object a, Lisp_Object b); +extern Lisp_Object cons_no_gc(Lisp_Object a, Lisp_Object b); +extern Lisp_Object cons_gc_test(Lisp_Object a); +extern void convert_fp_rep(void *p, int old_rep, int new_rep, int type); +extern DLLexport Lisp_Object Ceval(Lisp_Object u, Lisp_Object env); +extern unsigned32 Crand(void); +extern DLLexport Lisp_Object Cremainder(Lisp_Object a, Lisp_Object b); +extern void Csrand(unsigned32 a, unsigned32 b); +extern void discard(Lisp_Object a); +extern DLLexport CSLbool eql_fn(Lisp_Object a, Lisp_Object b); +extern DLLexport CSLbool cl_equal_fn(Lisp_Object a, Lisp_Object b); +extern DLLexport CSLbool equal_fn(Lisp_Object a, Lisp_Object b); +#ifdef TRACED_EQUAL +extern DLLexport CSLbool traced_equal_fn(Lisp_Object a, Lisp_Object b, + char *, int, int); +#define equal_fn(a, b) traced_equal_fn(a, b, __FILE__, __LINE__, 0) +extern void dump_equals(); +#endif +extern DLLexport CSLbool equalp(Lisp_Object a, Lisp_Object b); +extern DLLexport Lisp_Object apply(Lisp_Object fn, int nargs, + Lisp_Object env, Lisp_Object fname); +extern DLLexport Lisp_Object apply_lambda(Lisp_Object def, int nargs, + Lisp_Object env, Lisp_Object name); +extern void deallocate_pages(void); +extern void drop_heap_segments(void); +extern DLLexport Lisp_Object gcd(Lisp_Object a, Lisp_Object b); +extern Lisp_Object get_pname(Lisp_Object a); +#ifdef COMMON +extern DLLexport Lisp_Object get(Lisp_Object a, Lisp_Object b, Lisp_Object c); +#else +extern DLLexport Lisp_Object get(Lisp_Object a, Lisp_Object b); +#endif +extern Lisp_Object getvector(int tag, int32 type, int32 length); +extern Lisp_Object getvector_init(int32 n, Lisp_Object v); +extern Lisp_Object getcodevector(int32 type, int32 size); +extern unsigned32 hash_lisp_string(Lisp_Object s); +extern void lose_C_def(Lisp_Object a); +extern DLLexport CSLbool geq2(Lisp_Object a, Lisp_Object b); +extern DLLexport CSLbool greaterp2(Lisp_Object a, Lisp_Object b); +extern DLLexport CSLbool lesseq2(Lisp_Object a, Lisp_Object b); +extern DLLexport CSLbool lessp2(Lisp_Object a, Lisp_Object b); +extern DLLexport Lisp_Object list2(Lisp_Object a, Lisp_Object b); +extern DLLexport Lisp_Object list2star(Lisp_Object a, Lisp_Object b, Lisp_Object c); +extern DLLexport Lisp_Object list3(Lisp_Object a, Lisp_Object b, Lisp_Object c); +extern DLLexport Lisp_Object lognot(Lisp_Object a); +extern DLLexport Lisp_Object macroexpand(Lisp_Object form, Lisp_Object env); +extern Lisp_Object make_one_word_bignum(int32 n); +extern Lisp_Object make_package(Lisp_Object name); +extern Lisp_Object make_string(char *b); +extern Lisp_Object make_nstring(char *b, int32 n); +extern Lisp_Object make_undefined_symbol(char const *s); +extern Lisp_Object make_symbol(char const *s, int restartp, + one_args *f1, two_args *f2, n_args *fn); +extern DLLexport void MS_CDECL stdout_printf(char *fmt, ...); +extern DLLexport void MS_CDECL term_printf(char *fmt, ...); +extern DLLexport void MS_CDECL err_printf(char *fmt, ...); +extern DLLexport void MS_CDECL debug_printf(char *fmt, ...); +extern DLLexport void MS_CDECL trace_printf(char *fmt, ...); +extern char *my_getenv(char *name); +extern DLLexport Lisp_Object ncons(Lisp_Object a); +extern DLLexport Lisp_Object ndelete(Lisp_Object a, Lisp_Object b); +extern DLLexport Lisp_Object negate(Lisp_Object a); +extern DLLexport Lisp_Object nreverse(Lisp_Object a); +extern FILE *open_file(char *filename, char *original_name, + size_t n, char *dirn, FILE *old_file); +extern DLLexport Lisp_Object plus2(Lisp_Object a, Lisp_Object b); +extern void preserve(char *msg); +extern void preserve_native_code(); +extern void relocate_native_function(unsigned char *bps); +extern Lisp_Object prin(Lisp_Object u); +extern char *get_string_data(Lisp_Object a, char *why, int32 *len); +extern DLLexport void prin_to_stdout(Lisp_Object u); +extern DLLexport void prin_to_terminal(Lisp_Object u); +extern DLLexport void prin_to_debug(Lisp_Object u); +extern DLLexport void prin_to_query(Lisp_Object u); +extern DLLexport void prin_to_trace(Lisp_Object u); +extern DLLexport void prin_to_error(Lisp_Object u); +extern DLLexport void loop_print_stdout(Lisp_Object o); +extern DLLexport void loop_print_terminal(Lisp_Object o); +extern DLLexport void loop_print_debug(Lisp_Object o); +extern DLLexport void loop_print_query(Lisp_Object o); +extern DLLexport void loop_print_trace(Lisp_Object o); +extern DLLexport void loop_print_error(Lisp_Object o); +extern void internal_prin(Lisp_Object u, int prefix); +extern DLLexport Lisp_Object princ(Lisp_Object u); +extern DLLexport Lisp_Object print(Lisp_Object u); +extern DLLexport Lisp_Object printc(Lisp_Object u); +extern void print_bignum(Lisp_Object u, CSLbool blankp, int nobreak); +extern void print_bighexoctbin(Lisp_Object u, + int radix, int width, CSLbool blankp, int nobreak); +extern DLLexport Lisp_Object putprop(Lisp_Object a, Lisp_Object b, + Lisp_Object c); +extern DLLexport Lisp_Object quot2(Lisp_Object a, Lisp_Object b); +extern DLLexport Lisp_Object rational(Lisp_Object a); +extern void read_eval_print(int noisy); +extern DLLexport Lisp_Object reclaim(Lisp_Object value_to_return, char *why, + int stg_class, int32 size); +extern CSLbool do_not_kill_native_code; +extern void set_fns(Lisp_Object sym, one_args *f1, + two_args *f2, n_args *fn); +extern void setup(int restartp, double storesize); +extern Lisp_Object simplify_string(Lisp_Object s); +extern CSLbool stringp(Lisp_Object a); +extern DLLexport Lisp_Object times2(Lisp_Object a, Lisp_Object b); +extern int32 thirty_two_bits(Lisp_Object a); + +#ifdef DEMO_MODE +extern void give_up(); +#endif +#ifdef DEMO_BUILD +extern int32 demo_key1, demo_key2; +#endif + +/* + * The next few provide support for multiple values. + */ +#ifdef COMMON +#define onevalue(r) (exit_count=1, (r)) +#define nvalues(r, n) (exit_count=(n), (r)) +#else +#define onevalue(r) (r) +#define nvalues(r, n) (r) +#endif + +#ifdef COMMON +#define eval(a, b) Ceval(a, b) +#define voideval(a, b) Ceval(a, b) +#else +/* + * I lift the top test from eval out to be in-line so that I can + * (rather often) avoid the overhead of a procedure call when return from + * it will be almost immediate. The effect is that in CSL mode Ceval is + * only ever called on a list. NB the first arg to eval gets evaluated + * several times here - maybe I will just hope that CSE optimisation picks + * up this sort of repetition... + */ +#define eval(a, b) \ + (is_cons(a) ? Ceval(a, b) : \ + is_symbol(a) ? (qvalue(a) == unset_var ? error(1, err_unset_var, a) : \ + onevalue(qvalue(a))) : \ + onevalue(a)) +/* voideval(a, b) is like (void)eval(a, b) */ +#define voideval(a, b) \ + if (is_cons(a)) Ceval(a, b) /* Beware "else" after this */ +#endif + +/* + * The function "equal" seems to be pretty critical (certainly for Standard + * Lisp mode and Reduce). So I write out the top-level part of it in-line + * and only call the (messy) function in cases where it might be worth-while. + * For Common Lisp I will presumably look at eql and cl_equal as well. + * The test here says: + * If a and b are EQ then they are EQUAL, + * else if a and b have different types they are not EQUAL + * else if a has type 1, 2, 3 or 4 (ie fixnum, odds, sfloat, symbol) + * then they are not EQUAL (those types need to be EQ to be EQUAL) + * otherwise call equal_fn(a, b) to decide the issue. + */ +#define equal(a, b) \ + ((a) == (b) || \ + (((((a) ^ (b)) & TAG_BITS) == 0) && \ + ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ + equal_fn(a, b))) + +#define cl_equal(a, b) \ + ((a) == (b) || \ + (((((a) ^ (b)) & TAG_BITS) == 0) && \ + ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ + cl_equal_fn(a, b))) + +#define eql(a, b) \ + ((a) == (b) || \ + (((((a) ^ (b)) & TAG_BITS) == 0) && \ + ((unsigned)(((a) & TAG_BITS) - 1) > 3) && \ + eql_fn(a, b))) + +/* + * Helpers for the bignum arithmetic code... + */ + +#ifndef IMULTIPLY +extern unsigned32 Imultiply(unsigned32 *rlow, unsigned32 a, + unsigned32 b, unsigned32 c); +#endif +#ifndef IDIVIDE +extern unsigned32 Idivide(unsigned32 *qp, unsigned32 a, + unsigned32 b, unsigned32 c); +extern unsigned32 Idiv10_9(unsigned32 *qp, unsigned32 a, unsigned32 b); +#endif + +/* + * UNSAFE removes some checks - but it does noy seem to make much difference + * so I rather strongly suggest that you do not enable it! + */ +#ifdef UNSAFE +# define argcheck(var, n, msg) (var) = (var); +#else +# define argcheck(var, n, msg) if ((var)!=(n)) return aerror(msg); +#endif + +extern n_args *zero_arg_functions[]; +extern one_args *one_arg_functions[]; +extern two_args *two_arg_functions[]; +extern n_args *three_arg_functions[]; +extern void *useful_functions[]; +extern char *address_of_var(int n); + +typedef struct setup_type +{ + char *name; + one_args *one; + two_args *two; + n_args *n; +} setup_type; + +extern setup_type const + arith06_setup[], arith08_setup[], arith10_setup[], arith12_setup[], + char_setup[], eval1_setup[], eval2_setup[], eval3_setup[], + funcs1_setup[], funcs2_setup[], funcs3_setup[], print_setup[], + read_setup[], mpi_setup[]; +extern setup_type const + u01_setup[], u02_setup[], u03_setup[], u04_setup[], + u05_setup[], u06_setup[], u07_setup[], u08_setup[], + u09_setup[], u10_setup[], u11_setup[], u12_setup[]; +#ifdef NAG +extern setup_type const nag_setup[], asp_setup[]; +extern setup_type const socket_setup[], xdr_setup[], grep_setup[]; +extern setup_type const gr_setup[], axfns_setup[]; +#endif + +extern char *find_image_directory(int argc, char *argv[]); +extern char program_name[64]; +extern Lisp_Object declare_fn(Lisp_Object args, Lisp_Object env); +extern Lisp_Object function_fn(Lisp_Object args, Lisp_Object env); +extern Lisp_Object let_fn_1(Lisp_Object bvl, Lisp_Object body, + Lisp_Object env, int compilerp); +extern Lisp_Object mv_call_fn(Lisp_Object args, Lisp_Object env); +extern Lisp_Object progn_fn(Lisp_Object args, Lisp_Object env); +extern Lisp_Object quote_fn(Lisp_Object args, Lisp_Object env); +extern Lisp_Object tagbody_fn(Lisp_Object args, Lisp_Object env); + +#ifdef __cplusplus +} +#endif + +/* + * Now declare entrypoints to machine-dependent code fragments... + */ + +#include "sys.h" + +#endif /* header_externs_h */ + +/* end of externs.h */ Index: r36/cslbase/fns2.c ================================================================== --- r36/cslbase/fns2.c +++ r36/cslbase/fns2.c @@ -1,3499 +1,3499 @@ -/* fns2.c Copyright (C) 1989-96 Codemist Ltd */ - -/* - * Basic functions part 2. - */ - -/* Signature: 31f63691 12-Mar-2000 */ - -#include -#include -#include - -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "entries.h" -#include "arith.h" -#ifdef COMMON -#include "clsyms.h" -#endif -#ifdef TIMEOUT -#include "timeout.h" -#endif - -#ifdef SOCKETS -#include "sockhdr.h" -#endif - -Lisp_Object getcodevector(int32 type, int32 size) -{ -/* - * type is the code (e.g. TYPE_BPS) that gets packed, together with - * the size, into a header word. - * size is measured in bytes and must allow space for the header word. - * This obtains space in the BPS area - */ - Lisp_Object nil = C_nil; -#ifdef CHECK_FOR_CORRUPT_HEAP - validate_all(); -#endif - for (;;) - { int32 alloc_size = (int32)doubleword_align_up(size); - char *cf = (char *)codefringe, *cl = (char *)codelimit; - unsigned int free = cf - cl; - char *r; - if (alloc_size > (int32)free) - { char msg[40]; - sprintf(msg, "codevector %ld", (long)size); - reclaim(nil, msg, GC_BPS, alloc_size); - errexit(); - continue; - } - r = cf - alloc_size; - codefringe = (Lisp_Object)r; - *((Header *)r) = type + (size << 10) + TAG_ODDS; - return TAG_BPS + - (((int32)(r - cl + 12) & (PAGE_POWER_OF_TWO-4)) << 6) + - (((int32)(bps_pages_count-1))<<(PAGE_BITS+6)); /* Wow! Obscure!! */ - } -} - -Lisp_Object Lget_bps(Lisp_Object nil, Lisp_Object n) -{ - int32 n1; - if (!is_fixnum(n) || (int32)n<0) return aerror1("get-bps", n); - n1 = int_of_fixnum(n); - n = getcodevector(TYPE_BPS, n1+4); - errexit(); - return onevalue(n); -} - -Lisp_Object get_native_code_vector(int32 size) -{ -/* - * Create some space for native code and return a handle that identifies - * its start point. size is measured in bytes. - */ - Lisp_Object nil = C_nil; - if (size <= 0) size = 8; - for (;;) - { int32 alloc_size = (int32)doubleword_align_up(size); - int32 cf = native_fringe; - int32 free = CSL_PAGE_SIZE - cf - 0x100; /* 256 bytes to be safe */ -/* - * When I start up a cold CSL I will have native_fringe set to zero and - * native_pages_count also zero, indicating that there is none of this stuff - * active. - */ - if (native_fringe == 0 || alloc_size > free) - { char msg[40]; - sprintf(msg, "native code %ld", (long)size); - reclaim(nil, msg, GC_NATIVE, alloc_size); - errexit(); - continue; - } - free = (int32)native_pages[native_pages_count-1]; - free = doubleword_align_up(free); -/* - * I put the number of bytes in this block as the first word of the chunk - * of memory, and arrange that there is a zero in what would be the first - * word of unused space. Provided the user does not clobber bytes 0 to 4 - * or the block this is enough to allow restart code to scan through all - * native code segments. - */ - *(int32 *)(free+native_fringe) = alloc_size; - *(int32 *)(free+native_fringe+alloc_size) = 0; - native_fringe += alloc_size; - native_pages_changed = 1; - return Lcons(nil, - fixnum_of_int(native_pages_count-1), - fixnum_of_int(cf)); - } -} - -Lisp_Object Lget_native(Lisp_Object nil, Lisp_Object n) -{ - int32 n1; - if (!is_fixnum(n) || (int32)n<0) return aerror1("get-native", n); - n1 = int_of_fixnum(n); - n = get_native_code_vector(n1); - errexit(); - return onevalue(n); -} - -int do_not_kill_native_code = 0; - -void set_fns(Lisp_Object a, one_args *f1, two_args *f2, n_args *fn) -{ - Lisp_Object nil = C_nil; - Lisp_Object w1, w2, w3 = nil; -/* - * If I redefine a function for any reason (except to set trace options - * on a bytecoded definition) I will discard any native-coded definitions - * by splicing them out of the record. I provide a global variable to - * defeat this behaviour (ugh). - */ - if (!do_not_kill_native_code) - { for (w1 = native_code; w1!=nil; w1=qcdr(w1)) - { w2 = qcar(w1); - if (qcar(w2) == a) break; - w3 = w1; - } - if (w1 != nil) - { w1 = qcdr(w1); - if (w3 == nil) native_code = w1; - else qcdr(w3) = w1; - } - } - if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == - (SYM_C_DEF | SYM_CODEPTR)) - { -#ifdef NOISY_RE_PROTECTED_FNS - trace_printf("+++ protected function "); - prin_to_trace(a); - trace_printf(" not redefined\n"); -#endif - return; - } - ifn1(a) = (int32)f1; - ifn2(a) = (int32)f2; - ifnn(a) = (int32)fn; -} - -#ifdef HIDE_USELESS_SYMBOL_ENVIRONMENTS - -static CSLbool interpreter_entry(Lisp_Object a) -/* - * If a function will be handled by the interpreter, including the case - * of it being undefined, then the fn1() cell will tell me so. - */ -{ - return ( - qfn1(a) == interpreted1 || - qfn1(a) == traceinterpreted1 || - qfn1(a) == double_interpreted1 || - qfn1(a) == funarged1 || - qfn1(a) == tracefunarged1 || - qfn1(a) == double_funarged1 || - qfn1(a) == undefined1); -} - -#endif - -static char *show_fn(void *p) -{ - int i; - for (i=0; i MAX_FASTGET_SIZE)) return aerror1("symbol-make-fastget", a); - term_printf("+++ Fastget size was %d, now %d\n", n1, n); - fastget_size = n; - return onevalue(fixnum_of_int(n1)); -} - -Lisp_Object Lsymbol_make_fastget(Lisp_Object nil, Lisp_Object a, Lisp_Object n) -{ - int32 n1, p, q; - Header h; - if (!symbolp(a)) return onevalue(nil); - h = qheader(a); - p = header_fastget(h); - if (is_fixnum(n)) - { n1 = int_of_fixnum(n); - if (n1 < -1 || n1 >= fastget_size) - return aerror1("symbol-make-fastget", n); - trace_printf("+++ Use fastget slot %d for ", n1); - loop_print_trace(a); - errexit(); - trace_printf("\n"); - if (p != 0) elt(fastget_names, p-1) = SPID_NOPROP; - q = (n1 + 1) & 0x3f; - h = (h & ~SYM_FASTGET_MASK) | (q << SYM_FASTGET_SHIFT); - qheader(a) = h; - if (q != 0) elt(fastget_names, q-1) = a; - } - if (p == 0) return onevalue(nil); - else return onevalue(fixnum_of_int(p - 1)); -} - -static Lisp_Object deleqip(Lisp_Object a, Lisp_Object l) -/* - * This deletes the item a (tested for using EQ) from the list l, - * assuming that the list is nil-terminated and that the item a - * occurs at most once. It overwrites the list l in the process. - */ -{ - Lisp_Object nil = C_nil, w, r; - if (l == nil) return nil; - if (qcar(l) == a) return qcdr(l); - r = l; - while (w = l, (l = qcdr(l)) != nil) - { if (qcar(l) == a) - { qcdr(w) = qcdr(l); - return r; - } - } - return r; -} - -void lose_C_def(Lisp_Object a) -{ -/* - * None of the code here can cause garbage collection. - */ -#ifdef COMMON - Lisp_Object nil = C_nil; - Lisp_Object b = get(a, unset_var, nil), c; -#else - nil_as_base - Lisp_Object b = get(a, unset_var), c; -#endif - Lremprop(C_nil, a, unset_var); - qheader(a) &= ~SYM_C_DEF; -#ifdef COMMON - c = get(b, work_symbol, nil); -#else - c = get(b, work_symbol); -#endif - c = deleqip(a, c); - if (c == C_nil) Lremprop(C_nil, b, work_symbol); - else putprop(b, work_symbol, c); -} - -/* - * (symbol-set-native fn args bpsbase offset env) - * where bpsbase is as handed back by (make-native nnn) and offset is - * the offset in this block to enter at. - * If args has the actual arg count in its bottom byte. Usually the - * rest of it will be zero, and then one function cell is set to point to the - * given entrypoint and the other two are set to point at error handlers. - * If any bits in args beyond that are set then this call only changes the - * directly specified function cell, and the others are left in whatever state - * they were. If several of the fuction cells are to be filled in (eg to cope - * with &optional or &rest arguments) then a simple call with args<256 must - * be made first, followed by the calls (args>=256) that fill in the other - * two cells. - * The first time that symbol-set-native is called on a function that - * function MUST have a byte coded definition, and this definition is - * picked up and stored away, so that if (preserve) is called the bytecoded - * definition will be available for use on systems with different - * architectures. To make things tolerably consistent with that any operation - * that installs a new bytecoded (or for that matter other) definition - * will clear away any native-compiled versions of the function. - * - * The native code that is installed will be expected to have relocation - * records starting at the start of bpsbase, and these will be activated, - * filling in references from the bps to other executable parts of Lisp. - * Passing bad arguments to this function provide a quick and easy way to - * cayse UTTER havoc. Therefore I disable its use in server applications. - */ - -Lisp_Object MS_CDECL Lsymbol_set_native(Lisp_Object nil, int nargs, ...) -{ - va_list a; - Lisp_Object fn, args, bpsbase, offset, env, w1, w2, w3; - int32 pagenumber, page, bps, address, t_p, arginfo; -#ifdef SOCKETS -/* - * Security measure - deny symbol-set-native to remote users - */ - if (socket_server != 0) return aerror("symbol-set-native"); -#endif - argcheck(nargs, 5, "symbol-set-native"); - va_start(a, nargs); - fn = va_arg(a, Lisp_Object); - args = va_arg(a, Lisp_Object); - bpsbase = va_arg(a, Lisp_Object); - offset = va_arg(a, Lisp_Object); - env = va_arg(a, Lisp_Object); - va_end(a); - if (!is_symbol(fn) || - (qheader(fn) & (SYM_SPECIAL_FORM | SYM_CODEPTR)) != 0) - return aerror1("symbol-set-native", fn); - if (!is_fixnum(args)) return aerror1("symbol-set-native", args); - if (!consp(bpsbase) || - !is_fixnum(qcar(bpsbase)) || - !is_fixnum(qcdr(bpsbase))) - return aerror1("symbol-set-native", bpsbase); - if (!is_fixnum(offset)) return aerror1("symbol-set-native", offset); - nargs = int_of_fixnum(args); - pagenumber = int_of_fixnum(qcar(bpsbase)); - if (pagenumber<0 || pagenumber>=native_pages_count) - return aerror1("symbol-set-native", bpsbase); - bps = int_of_fixnum(qcdr(bpsbase)); - address = bps+int_of_fixnum(offset); - if (address<8 || address>=CSL_PAGE_SIZE) - return aerror1("symbol-set-native", offset); - page = (int32)native_pages[pagenumber]; - page = doubleword_align_up(page); - bps = page + bps; - relocate_native_function((unsigned char *)bps); -/* - * Here I need to push the info I have just collected onto - * the native_code list since otherwise things will not be re-loaded in - * from a checkpoint image. Also if the function is at present byte-coded - * I need to record that info about it in native_code. - */ - w1 = native_code; - while (w1!=nil) - { w2 = qcar(w1); - if (qcar(w2) == fn) break; - w1 = qcdr(w1); - } - if (w1 == nil) - { -/* - * Here the function has not been seen as native code ever before, so it has - * not been entered into the list. Do something about that... - */ - push2(env, fn); - args = Lsymbol_argcount(nil, fn); - errexitn(2); - if (args == nil) - return aerror1("No bytecode definition found for", fn); -/* - * Now I have to reverse the information that symbol_argcount gave me - * to get the single numeric code as wanted by symbol_set_definition. - * Oh what a mess. - */ - if (is_fixnum(args)) arginfo = int_of_fixnum(args); - else - { arginfo = int_of_fixnum(qcar(args)); - args = qcdr(args); - arginfo |= ((int_of_fixnum(qcar(args)) - arginfo) << 8); - args = qcdr(args); - arginfo |= int_of_fixnum(qcar(args)) << 16; - } - fn = stack[0]; - w2 = list2(fn, fixnum_of_int(arginfo)); - errexitn(2); - w2 = cons(w2, native_code); - errexitn(2); - native_code = w2; - w2 = qcar(w2); - pop2(fn, env); - } - w2 = qcdr(w2); /* {nargs,(type . offset . env),...} */ -/* - * If I was defining this function in the simple way I should clear any - * previous version (for this machine architecture) from the record. - * Just at present this does not release the memory, but at some stage - * in the future I may arrange to compact away old code when I do a - * preserve operation (say). - */ - if (nargs <= 0xff) - { w1 = w3 = w2; - for (w1=qcdr(w2); w1!=nil; w1=qcdr(w1)) - { w3 = qcar(w1); - if (qcar(w3) == fixnum_of_int(native_code_tag)) break; - w3 = w1; - } - if (w1 != nil) qcdr(w3) = qcdr(w1); - } -/* - * w2 is still the entry for this function in the native code list. It - * needs to have an entry of type 0 (ie for bytecoded) and so the next - * thing to do is to check that such an entry exists and if not to create - * it. - */ - w1 = w2; - while ((w1 = qcdr(w1)) != nil) - { w3 = qcar(w1); - if (qcar(w3) == fixnum_of_int(0)) break; - w1 = qcdr(w1); - } - if (w1 == nil) - { -/* - * This is where there was no bytecode entry on the native code list - * for this function, so I had better create one for it. Note that only - * one such entry will ever be stored so it does not matter much where on - * the list it goes. I suspect that the list ought always to be empty - * in this case anyway. - */ - push3(fn, env, w2); - w1 = list2star(fixnum_of_int(0), fixnum_of_int(0), qenv(fn)); - errexitn(3); - w2 = stack[0]; - w1 = cons(w1, qcdr(w2)); - errexitn(3); - pop3(w2, env, fn); - qcdr(w2) = w1; - } -/* - * Now the list of native code associated with this function certainly holds - * a byte-coded definition (and for sanity that had better be consistent - * with the native code I am installing now, but that is not something - * that can be checked at this level). Put in an entry referring to the - * current gubbins. - */ - push3(w2, fn, env); -/* - * now I pack the code type, arg category and offset into the - * single fixnum that that information has to end up in. - */ - t_p = (native_code_tag << 20); - if ((nargs & 0xffffff00) != 0) - { - switch (nargs & 0xff) - { - case 1: t_p |= (1<<18); break; - case 2: t_p |= (2<<18); break; - default:t_p |= (3<<18); break; - } - } - t_p |= (pagenumber & 0x3ffff); - w1 = list2star(fixnum_of_int(t_p), fixnum_of_int(address), env); - errexitn(3); - w1 = ncons(w1); - pop3(env, fn, w2); - errexit(); - while ((w3 = qcdr(w2)) != nil) w2 = w3; /* Tag onto the END */ - qcdr(w2) = w1; - qheader(fn) &= ~SYM_TRACED; - address = page + address; -/* - * The code here must do just about the equivalent to that in restart.c - */ - switch (nargs & 0xff) - { -case 0: ifnn(fn) = address; - if (nargs<=0xff) - ifn1(fn) = (int32)wrong_no_0a, ifn2(fn) = (int32)wrong_no_0b; - break; -case 1: ifn1(fn) = address; - if (nargs<=0xff) - ifn2(fn) = (int32)too_many_1, ifnn(fn) = (int32)wrong_no_1; - break; -case 2: ifn2(fn) = address; - if (nargs<=0xff) - ifn1(fn) = (int32)too_few_2, ifnn(fn) = (int32)wrong_no_2; - break; -case 3: ifnn(fn) = address; - if (nargs<=0xff) - ifn1(fn) = (int32)wrong_no_3a, ifn2(fn) = (int32)wrong_no_3b; - break; -default: ifnn(fn) = address; - if (nargs<=0xff) - ifn1(fn) = (int32)wrong_no_na, ifn2(fn) = (int32)wrong_no_nb; - break; - } - qenv(fn) = env; - return onevalue(fn); -} - -static CSLbool restore_fn_cell(Lisp_Object a, char *name, - int32 len, setup_type const s[]) -{ - int i; - for (i=0; s[i].name != NULL; i++) - { if (strlen(s[i].name) == len && - memcmp(name, s[i].name, len) == 0) break; - } - if (s[i].name == NULL) return NO; - set_fns(a, s[i].one, s[i].two, s[i].n); - return YES; -} - -static Lisp_Object Lrestore_c_code(Lisp_Object nil, Lisp_Object a) -{ - char *name; - int32 len; - Lisp_Object pn; - if (!symbolp(a)) return aerror1("restore-c-code", a); - push(a); - pn = get_pname(a); - pop(a); - errexit(); - name = (char *)&celt(pn, 0); - len = length_of_header(vechdr(pn)) - 4; - if (restore_fn_cell(a, name, len, u01_setup) || - restore_fn_cell(a, name, len, u02_setup) || - restore_fn_cell(a, name, len, u03_setup) || - restore_fn_cell(a, name, len, u04_setup) || - restore_fn_cell(a, name, len, u05_setup) || - restore_fn_cell(a, name, len, u06_setup) || - restore_fn_cell(a, name, len, u07_setup) || - restore_fn_cell(a, name, len, u08_setup) || - restore_fn_cell(a, name, len, u09_setup) || - restore_fn_cell(a, name, len, u10_setup) || - restore_fn_cell(a, name, len, u11_setup) || - restore_fn_cell(a, name, len, u12_setup)) - { Lisp_Object env; - push(a); -#ifdef COMMON - env = get(a, funarg, nil); -#else - env = get(a, funarg); -#endif - pop(a); - errexit(); - qenv(a) = env; - return onevalue(a); - } - else return onevalue(nil); -} - -Lisp_Object Lsymbol_set_definition(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -/* - * The odd case here is where the second argument represents a freshly - * created bit of compiled code. In which case the structure is - * (nargs . codevec . envvec) - * where nargs is an integer indicating the number of arguments, codevec - * is a vector of bytecodes, and envvec is something to go in the - * environment cell of the symbol. - * Here the low 8 bits of nargs indicate the number of required arguments. - * The next 8 bits give the number of optional arguments, and the next - * two bits are flags. Of these, the first is set if any of the optional - * arguments has an initform or supplied-p associate, and the other - * indicates that a "&rest" argument is required. - * Bits beyond that (if non-zero) indicate that the function definition - * is of the form (defun f1 (a b c) (f2 a b)) and the number coded is the - * length of the function body. - * Standard Lisp does not need &optional or &rest arguments, but it turned - * out to be pretty easy to make the bytecode compiler support them. - */ -{ - if (!is_symbol(a) || -/* - * Something flagged with the CODEPTR bit is a gensym manufactured to - * stand for a compiled-code object. It should NOT be reset! - */ - (qheader(a) & (SYM_SPECIAL_FORM | SYM_CODEPTR)) != 0) - { if (qheader(a) & SYM_C_DEF) return onevalue(nil); - return aerror1("symbol-set-definition", a); - } - qheader(a) &= ~SYM_TRACED; - set_fns(a, undefined1, undefined2, undefinedn); /* Tidy up first */ - qenv(a) = a; - if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); - if (b == nil) return onevalue(b); /* set defn to nil to undefine */ - else if (symbolp(b)) - { -/* - * One could imagine a view that the second arg to symbol-set-definition - * had to be a codepointer object. I will be kind (?) and permit the NAME - * of a function too. However for the second arg to be a macro or a - * special form would still be a calamity. - * if ((qheader(b) & SYM_CODEPTR) == 0) - * return aerror1("symbol-set-definition", b); - */ - if ((qheader(b) & (SYM_SPECIAL_FORM | SYM_MACRO)) != 0) - return aerror1("symbol-set-definition", b); - qheader(a) = qheader(a) & ~SYM_MACRO; - { set_fns(a, qfn1(b), qfn2(b), qfnn(b)); - qenv(a) = qenv(b); -/* - * In order that checkpoint files can be made there is some very - * ugly fooling around here for functions that are defined in the C coded - * kernel. Sorry. - */ - if ((qheader(b) & SYM_C_DEF) != 0) - { -#ifdef COMMON - Lisp_Object c = get(b, unset_var, nil); -#else - Lisp_Object c = get(b, unset_var); -#endif - if (c == nil) c = b; - push2(c, a); - putprop(a, unset_var, c); - errexitn(2); - pop(a); -#ifdef COMMON - a = cons(a, get(stack[0], work_symbol, nil)); -#else - a = cons(a, get(stack[0], work_symbol)); -#endif - errexitn(1); - putprop(stack[0], work_symbol, a); - pop(b); - errexit(); - } - } - } - else if (!consp(b)) return aerror1("symbol-set-definition", b); - else if (is_fixnum(qcar(b))) - { int32 nargs = (int)int_of_fixnum(qcar(b)), nopts, flagbits, ntail; - nopts = nargs >> 8; - flagbits = nopts >> 8; - ntail = flagbits >> 2; - nargs &= 0xff; - nopts &= 0xff; - flagbits &= 3; - if (ntail != 0) - { switch (100*nargs + ntail-1) - { - case 300: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_0); break; - case 301: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_1); break; - case 302: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_2); break; - case 303: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_3); break; - case 200: set_fns(a, too_few_2, f2_as_0, wrong_no_2); break; - case 201: set_fns(a, too_few_2, f2_as_1, wrong_no_2); break; - case 202: set_fns(a, too_few_2, f2_as_2, wrong_no_2); break; - case 100: set_fns(a, f1_as_0, too_many_1, wrong_no_1); break; - case 101: set_fns(a, f1_as_1, too_many_1, wrong_no_1); break; - case 000: set_fns(a, wrong_no_na, wrong_no_nb, f0_as_0); break; - } - b = qcdr(b); - } - else if (flagbits != 0 || nopts != 0) - { if ((qheader(a) & SYM_TRACED) == 0) switch(flagbits) - { - default: - case 0: /* easy case optional arguments */ - set_fns(a, byteopt1, byteopt2, byteoptn); break; - case 1: /* optional args, but non-nil default, or supplied-p extra */ - set_fns(a, hardopt1, hardopt2, hardoptn); break; - case 2: /* easy opt args, but also a &rest arg */ - set_fns(a, byteoptrest1, byteoptrest2, byteoptrestn); break; - case 3: /* complicated &options and &rest */ - set_fns(a, hardoptrest1, hardoptrest2, hardoptrestn); break; - } - else switch (flagbits) - { - default: - case 0: /* easy case optional arguments */ - set_fns(a, tracebyteopt1, tracebyteopt2, tracebyteoptn); break; - case 1: /* optional args, but non-nil default, or supplied-p extra */ - set_fns(a, tracehardopt1, tracehardopt2, tracehardoptn); break; - case 2: /* easy opt args, but also a &rest arg */ - set_fns(a, tracebyteoptrest1, tracebyteoptrest2, tracebyteoptrestn); break; - case 3: /* complicated &options and &rest */ - set_fns(a, tracehardoptrest1, tracehardoptrest2, tracehardoptrestn); break; - } - } - else - { if (nargs > 4) nargs = 4; - if ((qheader(a) & SYM_TRACED) != 0) nargs += 5; - qheader(a) = qheader(a) & ~SYM_MACRO; - switch (nargs) - { - case 0: set_fns(a, wrong_no_0a, wrong_no_0b, bytecoded0); - break; - case 1: set_fns(a, bytecoded1, too_many_1, wrong_no_1); - break; - case 2: set_fns(a, too_few_2, bytecoded2, wrong_no_2); - break; - case 3: set_fns(a, wrong_no_3a, wrong_no_3b, bytecoded3); - break; - default: - case 4: set_fns(a, wrong_no_na, wrong_no_nb, bytecodedn); - break; - - case 5+0: set_fns(a, wrong_no_0a, wrong_no_0b, tracebytecoded0); - break; - case 5+1: set_fns(a, tracebytecoded1, too_many_1, wrong_no_1); - break; - case 5+2: set_fns(a, too_few_2, tracebytecoded2, wrong_no_2); - break; - case 5+3: set_fns(a, wrong_no_3a, wrong_no_3b, tracebytecoded3); - break; - case 5+4: set_fns(a, wrong_no_na, wrong_no_nb, tracebytecodedn); - break; - } - } - qenv(a) = qcdr(b); - } - else if (qcar(b) == lambda) - { Lisp_Object bvl = qcar(qcdr(b)); - int nargs = 0; - while (consp(bvl)) nargs++, bvl = qcdr(bvl); - qheader(a) = qheader(a) & ~SYM_MACRO; - if ((qheader(a) & SYM_TRACED) != 0) - set_fns(a, traceinterpreted1, traceinterpreted2, traceinterpretedn); - else set_fns(a, interpreted1, interpreted2, interpretedn); - qenv(a) = qcdr(b); - if (qvalue(comp_symbol) != nil && - qfn1(compiler_symbol) != undefined1) - { push(a); - a = ncons(a); - errexitn(1); - (qfn1(compiler_symbol))(qenv(compiler_symbol), a); - pop(a); - errexit(); - } - } - else if (qcar(b) == funarg) - { Lisp_Object bvl = qcar(qcdr(b)); - int nargs = 0; - while (consp(bvl)) nargs++, bvl = qcdr(bvl); - qheader(a) = qheader(a) & ~SYM_MACRO; - if ((qheader(a) & SYM_TRACED) != 0) - set_fns(a, tracefunarged1, tracefunarged2, tracefunargedn); - else set_fns(a, funarged1, funarged2, funargedn); - qenv(a) = qcdr(b); - } - else return aerror1("symbol-set-definition", b); - return onevalue(b); -} - -Lisp_Object Lgetd(Lisp_Object nil, Lisp_Object a) -{ - Header h; - Lisp_Object type; - CSL_IGNORE(nil); - if (a == nil) return onevalue(nil); - else if (!is_symbol(a)) return onevalue(nil); - h = qheader(a); - if ((h & SYM_SPECIAL_FORM) != 0) type = fexpr_symbol; - else if ((h & SYM_MACRO) != 0) - { a = cons(lambda, qenv(a)); - errexit(); - type = macro_symbol; - } - else - { a = Lsymbol_function(nil, a); - errexit(); - if (a == nil) return onevalue(nil); - type = expr_symbol; - } - a = cons(type, a); - errexit(); - return onevalue(a); -} - -Lisp_Object Lremd(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object res; - CSL_IGNORE(nil); - if (!is_symbol(a) || - (qheader(a) & SYM_SPECIAL_FORM) != 0) - return aerror1("remd", a); - if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == - (SYM_C_DEF | SYM_CODEPTR)) return onevalue(nil); - res = Lgetd(nil, a); - errexit(); - if (res == nil) return onevalue(nil); /* no definition to remove */ -/* - * I treat an explicit use of remd as a redefinition, and ensure that - * restarting a preserved image will not put the definition back. - */ - qheader(a) = qheader(a) & ~SYM_MACRO; - if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); - set_fns(a, undefined1, undefined2, undefinedn); - qenv(a) = a; - return onevalue(res); -} - -/* - * For set-autoload the first argument must be a symbol that will name - * a function, the second arg is either an atom or a list of atoms, each - * of which specified a module to be loaded if the names function is - * called. Loading the modules is expected to instate a definition for the - * function involved. This function is arranged so it does NOT do anything - * if the function being set for autoloading is already defined. This is - * on the supposition that the existing definition is in fact the desired - * one, say because the relevant module happens to have been loaded already. - * An explicit use of remd first can be used to ensure that no previous - * definition is present and thus that a real autoload stub will be instated, - * if that is what you really want. - */ - -Lisp_Object Lset_autoload(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - Lisp_Object res; - CSL_IGNORE(nil); - if (!is_symbol(a) || - (qheader(a) & SYM_SPECIAL_FORM) != 0) - return aerror1("set-autoload", a); - if (!(qfn1(a) == undefined1 && qfn2(a) == undefined2 && - qfnn(a) == undefinedn)) return onevalue(nil); - if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == - (SYM_C_DEF | SYM_CODEPTR)) return onevalue(nil); - push2(a, b); - if (consp(b)) res = cons(a, b); - else res = list2(a, b); - pop2(b, a); - errexit(); -/* - * I treat an explicit use of set-autoload as a redefinition, and ensure that - * restarting a preserved image will not put the definition back. Note that - * I will not allow autoloadable macros... - */ - qheader(a) = qheader(a) & ~SYM_MACRO; - if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); - set_fns(a, autoload1, autoload2, autoloadn); - qenv(a) = res; - return onevalue(res); -} - -#define pack_funtable(a, n) ((((int32)(a)) << 16) | (n)) -#define funtable_nargs(u) ((u) >> 16) -#define funtable_index(u) ((u) & 0xffffU) - -static one_args *displaced1 = NULL; -static two_args *displaced2; -static n_args *displacedn; -static unsigned32 table_entry; - -static void trace_entering(char *s) -{ - int i; - for (i=0; i 15 args: not supported"); - } - popv(nargs); - pop(name); - errexit(); - push(r); - freshline_trace(); - loop_print_trace(name); - trace_printf(" = "); - loop_print_trace(r); - trace_exiting("\n"); - pop(r); - return onevalue(r); -} - -#define NOT_FOUND 100 - -static unsigned32 find_built_in_function(one_args *f1, - two_args *f2, - n_args *fn) -/* - * This take the entrypoint of a function and tries to identify it - * by scanning the tables used by the bytecode interpreter. If the - * function is found a record is returned indicating how many args - * it takes, and what its index is in the relevant table. The code - * is returned to indicate failure if the function - * is not found. - */ -{ - int32 index; - for (index=0; zero_arg_functions[index]!=NULL; index++) - if (fn == zero_arg_functions[index]) return pack_funtable(0, index); - for (index=0; one_arg_functions[index]!=NULL; index++) - if (f1 == one_arg_functions[index]) return pack_funtable(1, index); - for (index=0; two_arg_functions[index]!=NULL; index++) - if (f2 == two_arg_functions[index]) return pack_funtable(2, index); - for (index=0; three_arg_functions[index]!=NULL; index++) - if (fn == three_arg_functions[index]) return pack_funtable(3, index); - return pack_funtable(NOT_FOUND, NOT_FOUND); -} - -Lisp_Object Ltrace_all(Lisp_Object nil, Lisp_Object a) -{ -#ifdef DEBUG - if (a == nil) trace_all = 0; - else trace_all = 1; - return onevalue(nil); -#else - return aerror("trace-all only supported in DEBUG version"); -#endif -} - -Lisp_Object Ltrace(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object w = a; - if (symbolp(a)) - { a = ncons(a); - errexit(); - w = a; - } - while (consp(w)) - { Lisp_Object s = qcar(w); - w = qcdr(w); - if (symbolp(s)) - { one_args *f1 = qfn1(s); - two_args *f2 = qfn2(s); - n_args *fn = qfnn(s); - int fixenv = 0, done = 0; - if (f1 == undefined1) - { freshline_debug(); - debug_printf("+++ "); - loop_print_debug(s); - debug_printf(" not yet defined\n"); - continue; - } - qheader(s) |= SYM_TRACED; - if (f1 == interpreted1) - { set_fns(s, traceinterpreted1, traceinterpreted2, traceinterpretedn); - fixenv = done = 1; - } - if (f1 == funarged1) - { set_fns(s, tracefunarged1, tracefunarged2, tracefunargedn); - fixenv = done = 1; - } - if (fn == bytecoded0) ifnn(s) = (int32)tracebytecoded0, done = 1; - if (f1 == bytecoded1) ifn1(s) = (int32)tracebytecoded1, done = 1; - if (f2 == bytecoded2) ifn2(s) = (int32)tracebytecoded2, done = 1; - if (fn == bytecoded3) ifnn(s) = (int32)tracebytecoded3, done = 1; - if (fn == bytecodedn) ifnn(s) = (int32)tracebytecodedn, done = 1; - if (f1 == byteopt1) ifn1(s) = (int32)tracebyteopt1, done = 1; - if (f2 == byteopt2) ifn2(s) = (int32)tracebyteopt2, done = 1; - if (fn == byteoptn) ifnn(s) = (int32)tracebyteoptn, done = 1; - if (f1 == hardopt1) ifn1(s) = (int32)tracehardopt1, done = 1; - if (f2 == hardopt2) ifn2(s) = (int32)tracehardopt2, done = 1; - if (fn == hardoptn) ifnn(s) = (int32)tracehardoptn, done = 1; - if (f1 == byteoptrest1) ifn1(s) = (int32)tracebyteoptrest1, done = 1; - if (f2 == byteoptrest2) ifn2(s) = (int32)tracebyteoptrest2, done = 1; - if (fn == byteoptrestn) ifnn(s) = (int32)tracebyteoptrestn, done = 1; - if (f1 == hardoptrest1) ifn1(s) = (int32)tracehardoptrest1, done = 1; - if (f2 == hardoptrest2) ifn2(s) = (int32)tracehardoptrest2, done = 1; - if (fn == hardoptrestn) ifnn(s) = (int32)tracehardoptrestn, done = 1; - if (fixenv) - { push2(a, s); - a = cons(s, qenv(s)); - errexitn(2); - pop(s); - qenv(s) = a; - pop(a); - } - if (done) continue; -/* - * I permit the tracing of just one function from the kernel, and achieve - * this by installing a wrapper function in place of the real definition. - * Indeed this is just like Lisp-level embedding, except that I can get at the - * entrypoint table used by the bytecode interpreter and so trap calls made - * via there, and I can use that table to tell me how many arguments the - * traced function needed. - */ - if (displaced1 == NULL) - { int nargs = funtable_nargs(table_entry); -/* - * Remember what function was being traced, so that it can eventually be - * invoked, and its name printed. - */ - displaced1 = f1; - displaced2 = f2; - displacedn = fn; - tracedfn = s; -/* - * This makes calls via the regular interpreter see the traced version... - */ - set_fns(s, traced1_function, traced2_function, - tracedn_function); - table_entry = find_built_in_function(f1, f2, fn); - nargs = funtable_nargs(table_entry); - table_entry = funtable_index(table_entry); - if (nargs != NOT_FOUND) - { -/* - * .. and now I make calls via short-form bytecodes do likewise. - */ - switch (nargs) - { - default: - case 0: zero_arg_functions[funtable_index(table_entry)] = - tracedn_function; - break; - case 1: one_arg_functions[funtable_index(table_entry)] = - traced1_function; - break; - case 2: two_arg_functions[funtable_index(table_entry)] = - traced2_function; - break; - case 3: three_arg_functions[funtable_index(table_entry)] = - tracedn_function; - break; - } - } - } - continue; - } - } - return onevalue(a); -} - -Lisp_Object Luntrace(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object w = a; - CSL_IGNORE(nil); - if (symbolp(a)) - { a = ncons(a); - errexit(); - w = a; - } - while (consp(w)) - { Lisp_Object s = qcar(w); - w = qcdr(w); - if (symbolp(s)) - { one_args *f1 = qfn1(s); - two_args *f2 = qfn2(s); - n_args *fn = qfnn(s); - if (f1 == traceinterpreted1) - { set_fns(a, interpreted1, interpreted2, interpretedn); - qenv(s) = qcdr(qenv(s)); - } - else if (f1 == tracefunarged1) - { set_fns(s, funarged1, funarged2, funargedn); - qenv(s) = qcdr(qenv(s)); - } - if (f1 == tracebytecoded1) ifn1(s) = (int32)bytecoded1; - if (f2 == tracebytecoded2) ifn2(s) = (int32)bytecoded2; - if (fn == tracebytecoded0) ifnn(s) = (int32)bytecoded0; - if (fn == tracebytecoded3) ifnn(s) = (int32)bytecoded3; - if (fn == tracebytecodedn) ifnn(s) = (int32)bytecodedn; - if (f1 == tracebyteopt1) ifn1(s) = (int32)byteopt1; - if (f2 == tracebyteopt2) ifn2(s) = (int32)byteopt2; - if (fn == tracebyteoptn) ifnn(s) = (int32)byteoptn; - if (f1 == tracebyteoptrest1) ifn1(s) = (int32)byteoptrest1; - if (f2 == tracebyteoptrest2) ifn2(s) = (int32)byteoptrest2; - if (fn == tracebyteoptrestn) ifnn(s) = (int32)byteoptrestn; - if (f1 == tracehardopt1) ifn1(s) = (int32)hardopt1; - if (f2 == tracehardopt2) ifn2(s) = (int32)hardopt2; - if (fn == tracehardoptn) ifnn(s) = (int32)hardoptn; - if (f1 == tracehardoptrest1) ifn1(s) = (int32)hardoptrest1; - if (f2 == tracehardoptrest2) ifn2(s) = (int32)hardoptrest2; - if (fn == tracehardoptrestn) ifnn(s) = (int32)hardoptrestn; - if (f1 == traced1_function) - { int nargs = funtable_nargs(table_entry); - set_fns(s, displaced1, displaced2, displacedn); - if (nargs != NOT_FOUND) - switch (nargs) - { - default: - case 0: zero_arg_functions[funtable_index(table_entry)] = - displacedn; - break; - case 1: one_arg_functions[funtable_index(table_entry)] = - displaced1; - break; - case 2: two_arg_functions[funtable_index(table_entry)] = - displaced2; - break; - case 3: three_arg_functions[funtable_index(table_entry)] = - displacedn; - break; - } - displaced1 = NULL; - displaced2 = NULL; - displacedn = NULL; - } - qheader(s) &= ~SYM_TRACED; - } - } - return onevalue(a); -} - -Lisp_Object Ldouble(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object w = a; - if (symbolp(a)) - { a = ncons(a); - errexit(); - w = a; - } - while (consp(w)) - { Lisp_Object s = qcar(w); - w = qcdr(w); - if (symbolp(s)) - { one_args *f1 = qfn1(s); - two_args *f2 = qfn2(s); - n_args *fn = qfnn(s); - int fixenv = 0, done = 0; - if (f1 == undefined1) continue; - if (f1 == interpreted1) - { set_fns(s, double_interpreted1, double_interpreted2, double_interpretedn); - fixenv = done = 1; - } - if (f1 == funarged1) - { set_fns(s, double_funarged1, double_funarged2, double_funargedn); - fixenv = done = 1; - } - if (fn == bytecoded0) ifnn(s) = (int32)double_bytecoded0, done = 1; - if (f1 == bytecoded1) ifn1(s) = (int32)double_bytecoded1, done = 1; - if (f2 == bytecoded2) ifn2(s) = (int32)double_bytecoded2, done = 1; - if (fn == bytecoded3) ifnn(s) = (int32)double_bytecoded3, done = 1; - if (fn == bytecodedn) ifnn(s) = (int32)double_bytecodedn, done = 1; - if (f1 == byteopt1) ifn1(s) = (int32)double_byteopt1, done = 1; - if (f2 == byteopt2) ifn2(s) = (int32)double_byteopt2, done = 1; - if (fn == byteoptn) ifnn(s) = (int32)double_byteoptn, done = 1; - if (f1 == hardopt1) ifn1(s) = (int32)double_hardopt1, done = 1; - if (f2 == hardopt2) ifn2(s) = (int32)double_hardopt2, done = 1; - if (fn == hardoptn) ifnn(s) = (int32)double_hardoptn, done = 1; - if (f1 == byteoptrest1) ifn1(s) = (int32)double_byteoptrest1, done = 1; - if (f2 == byteoptrest2) ifn2(s) = (int32)double_byteoptrest2, done = 1; - if (fn == byteoptrestn) ifnn(s) = (int32)double_byteoptrestn, done = 1; - if (f1 == hardoptrest1) ifn1(s) = (int32)double_hardoptrest1, done = 1; - if (f2 == hardoptrest2) ifn2(s) = (int32)double_hardoptrest2, done = 1; - if (fn == hardoptrestn) ifnn(s) = (int32)double_hardoptrestn, done = 1; - if (fixenv) - { push2(a, s); - a = cons(s, qenv(s)); - errexitn(2); - pop(s); - qenv(s) = a; - pop(a); - } - if (done) continue; - debug_printf("Unable to execution-double: "); loop_print_debug(s); - trace_printf("\n"); - continue; - } - } - return onevalue(a); -} - -Lisp_Object Lundouble(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object w = a; - CSL_IGNORE(nil); - if (symbolp(a)) - { a = ncons(a); - errexit(); - w = a; - } - while (consp(w)) - { Lisp_Object s = qcar(w); - w = qcdr(w); - if (symbolp(s)) - { one_args *f1 = qfn1(s); - two_args *f2 = qfn2(s); - n_args *fn = qfnn(s); - if (f1 == double_interpreted1) - { set_fns(a, interpreted1, interpreted2, interpretedn); - qenv(s) = qcdr(qenv(s)); - } - else if (f1 == double_funarged1) - { set_fns(s, funarged1, funarged2, funargedn); - qenv(s) = qcdr(qenv(s)); - } - else if (f1 == double_bytecoded1) ifn1(s) = (int32)bytecoded1; - else if (f2 == double_bytecoded2) ifn2(s) = (int32)bytecoded2; - else if (fn == double_bytecoded0) ifnn(s) = (int32)bytecoded0; - else if (fn == double_bytecoded3) ifnn(s) = (int32)bytecoded3; - else if (fn == double_bytecodedn) ifnn(s) = (int32)bytecodedn; - else if (f1 == double_byteopt1) ifn1(s) = (int32)byteopt1; - else if (f2 == double_byteopt2) ifn2(s) = (int32)byteopt2; - else if (fn == double_byteoptn) ifnn(s) = (int32)byteoptn; - else if (f1 == double_byteoptrest1) ifn1(s) = (int32)byteoptrest1; - else if (f2 == double_byteoptrest2) ifn2(s) = (int32)byteoptrest2; - else if (fn == double_byteoptrestn) ifnn(s) = (int32)byteoptrestn; - else if (f1 == double_hardopt1) ifn1(s) = (int32)hardopt1; - else if (f2 == double_hardopt2) ifn2(s) = (int32)hardopt2; - else if (fn == double_hardoptn) ifnn(s) = (int32)hardoptn; - else if (f1 == double_hardoptrest1) ifn1(s) = (int32)hardoptrest1; - else if (f2 == double_hardoptrest2) ifn2(s) = (int32)hardoptrest2; - else if (fn == double_hardoptrestn) ifnn(s) = (int32)hardoptrestn; - } - } - return onevalue(a); -} - -Lisp_Object Lmacro_function(Lisp_Object nil, Lisp_Object a) -{ - if (!symbolp(a)) return onevalue(nil); - else if ((qheader(a) & SYM_MACRO) == 0) return onevalue(nil); -/* If the MACRO bit is set in the header I know there is a definition */ - else return onevalue(cons(lambda, qenv(a))); -} - - -Lisp_Object get_pname(Lisp_Object a) -{ - Lisp_Object name = qpname(a); -#ifndef COMMON -/* - * When a gensym is first created its pname field points at a string that - * will form the base of its name, and a magic bit is set in its header. - * If at some stage it is necessary to inspect the print name (mainly in - * order to print the symbol) it becomes necessary to create a new string - * and insert a serial number. Doing things this way means that the serial - * numbers that users see will tend to be smaller, and space for per-gensym - * strings does not get allocated unless really needed. The down side is - * that every time I want to grab the pname of anything I have to check for - * this case and admit the possibility of garbage collection or even - * failure. - */ - if (qheader(a) & SYM_UNPRINTED_GENSYM) - { unsigned32 len; - Lisp_Object nil = C_nil; - char genname[64]; - len = length_of_header(vechdr(name)) - 4; - if (len > 60) len = 60; /* Unpublished truncation of the string */ - sprintf(genname, "%.*s%lu", (int)len, - (char *)name + (4 - TAG_VECTOR), (long)gensym_ser++); - push(a); - name = make_string(genname); - pop(a); - errexit(); - qpname(a) = name; - qheader(a) &= ~SYM_UNPRINTED_GENSYM; - } -#endif - return name; -} - -Lisp_Object Lsymbol_name(Lisp_Object nil, Lisp_Object a) -{ - if (!symbolp(a)) return aerror1("symbol-name", a); - a = get_pname(a); - errexit(); - return onevalue(a); -} - -#ifdef COMMON - -Lisp_Object Lsymbol_package(Lisp_Object nil, Lisp_Object a) -{ - if (!symbolp(a)) return aerror1("symbol-package", a); - a = qpackage(a); - return onevalue(a); -} - -#endif - -static Lisp_Object Lrestart_csl2(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -/* - * If the argument is given as nil then this is a cold-start, and when - * I begin again it would be a VERY good idea to do a (load!-module 'compat) - * rather promptly (otherwise some Lisp functions will not work at all). - * I do not automate that because this function is intended for use in - * delicate system rebuilding contexts and I want the user to have ultimate - * control. (restart!-csl t) reloads a heap-image in the normal way. - * (restart!-csl 'xx) where xx is neither nil nor t starts by reloading a - * heap image, but then it looks for a function with the same name as xx - * (since a heap image is reloaded it is NOT easy (possible?) to keep the - * symbol) and calls it as a function. Finally the case - * (restart!-csl '(module fn)) restart the system, then calls load-module - * on the named module and finally calls the given restart function. - * This last option can be useful since otherwise the function to be called - * in (restart!-csl 'xx) would need to be in the base image as re-loaded. - */ -{ - int n; - char *v; -#ifdef SOCKETS -/* - * Security measure - deny restart-csl to remote users - */ - if (socket_server != 0) return aerror("restart-csl"); -#endif - n = 0; - v = NULL; -/* - * A comment seems in order here. The case b==SPID_NOARG should only - * arise if I came from Lrestart_csl: it indicates that there was - * no second argument provided. - */ - if (b != SPID_NOARG) - { Lisp_Object b1 = b = Lexploden(nil, b); - errexit(); - while (b1 != nil) - { n++; /* number of chars of arg */ - b1 = qcdr(b1); - } - v = (char *)malloc(n+1); - if (v == NULL) return aerror("space exhausted in restart-csl"); - n = 0; - while (b != nil) - { v[n++] = int_of_fixnum(qcar(b)); - b = qcdr(b); - } - v[n] = 0; - } - term_printf("\nThe system is about to do a restart...\n"); -/* Almost all unpicking of the argument is done back in csl.c */ - exit_value = a; - exit_tag = fixnum_of_int(2); /* Flag to say "restart" */ - exit_reason = UNWIND_RESTART; - exit_charvec = v; - flip_exception(); - return nil; -} - -static Lisp_Object Lrestart_csl(Lisp_Object nil, Lisp_Object a) -{ - return Lrestart_csl2(nil, a, SPID_NOARG); -} - -static Lisp_Object Lpreserve(Lisp_Object nil, - Lisp_Object startup, Lisp_Object banner) -/* - * (preserve ) saves a Lisp image in a standard place - * and arranges that when restarted the saved image will call the specified - * startup function. In the process of doing all this it unwinds down to - * the top level of Lisp. If a startup function is not given then the - * previously active one is used. If nil is specified then the previously - * active startup function is retained. If banner is non-nil (well really - * I want a string) is is a message of up to 40 characters to display - * when the system restart. - */ -{ - char filename[LONGEST_LEGAL_FILENAME]; - CSLbool failed; -#ifdef SOCKETS -/* - * Security measure - deny preserve to remote users - */ - if (socket_server != 0) return aerror("preserve"); -#endif - if (startup != nil) supervisor = startup; - failed = Iwriterootp(filename); /* Can I open image file for writing? */ - term_printf("\nThe system will be preserved on file \"%s\"\n", filename); - if (failed) return aerror("preserve"); - exit_count = 0; - nil = C_nil; - exit_value = banner; - exit_tag = fixnum_of_int(1); /* Flag to say "preserve" */ - exit_reason = UNWIND_RESTART; - flip_exception(); - return nil; -} - -static Lisp_Object MS_CDECL Lpreserve_0(Lisp_Object nil, int nargs, ...) -{ - argcheck(nargs, 0, "preserve"); - return Lpreserve(nil, nil, nil); -} - -static Lisp_Object Lpreserve_1(Lisp_Object nil, Lisp_Object startup) -{ - return Lpreserve(nil, startup, nil); -} - - -/* - * This is an experimental addition - a version of PRESERVE that allows - * CSL to continue executing after it has written out an image file. - */ - -static Lisp_Object Lcheckpoint(Lisp_Object nil, - Lisp_Object startup, Lisp_Object banner) -{ - char filename[LONGEST_LEGAL_FILENAME]; - CSLbool failed = 0; - char *msg = ""; -#ifdef SOCKETS -/* - * Security measure - deny checkpoint to remote users - */ - if (socket_server != 0) return aerror("checkpoint"); -#endif - if (startup != nil) supervisor = startup; - failed = Iwriterootp(filename); /* Can I open image file for writing? */ - term_printf("\nThe system will be preserved on file \"%s\"\n", filename); - if (failed) return aerror("checkpoint"); - if (is_vector(banner) && - type_of_header(vechdr(banner)) == TYPE_STRING) - msg = &celt(banner, 0); -/* - * Note, with some degree of nervousness, that things on the C stack will - * be updated by the garbage collection that happens during the processing - * of the call to preserve(), but they will be neither adjusted into - * relative addresses nor unadjusted (and hence restored) by in the - * image-writing. But the image writing will not actually move any data - * around so all is still OK, I hope! - */ - push5(codevec, litvec, catch_tags, faslvec, faslgensyms); - preserve(msg); - nil = C_nil; - if (exception_pending()) failed = 1, flip_exception(); - adjust_all(); - pop5(faslgensyms, faslvec, catch_tags, litvec, codevec); - eq_hash_tables = eq_hash_table_list; - equal_hash_tables = equal_hash_table_list; - eq_hash_table_list = equal_hash_table_list = nil; - { Lisp_Object qq; - for (qq = eq_hash_tables; qq!=nil; qq=qcdr(qq)) - rehash_this_table(qcar(qq)); - for (qq = equal_hash_tables; qq!=nil; qq=qcdr(qq)) - rehash_this_table(qcar(qq)); - } - set_up_functions(YES); - if (failed) return aerror("checkpoint"); - return onevalue(nil); -} - -static Lisp_Object MS_CDECL Lcheckpoint_0(Lisp_Object nil, int nargs, ...) -{ - argcheck(nargs, 0, "checkpoint"); - return Lcheckpoint(nil, nil, nil); -} - -static Lisp_Object Lcheckpoint_1(Lisp_Object nil, Lisp_Object startup) -{ - return Lcheckpoint(nil, startup, nil); -} - - -#ifdef COMMON -static CSLbool eql_numbers(Lisp_Object a, Lisp_Object b) -/* - * This is only called from eql, and then only when a and b are both tagged - * as ratios or complex numbers. - */ -{ - Lisp_Object p, q; - p = *(Lisp_Object *)(a + (4 - TAG_NUMBERS)); - q = *(Lisp_Object *)(b + (4 - TAG_NUMBERS)); - if (!eql(p, q)) return NO; - p = *(Lisp_Object *)(a + (8 - TAG_NUMBERS)); - q = *(Lisp_Object *)(b + (8 - TAG_NUMBERS)); - return eql(p, q); -} -#endif - -CSLbool eql_fn(Lisp_Object a, Lisp_Object b) -/* - * This seems incredible - all the messing about that is needed to - * check that numeric values compare properly. Ugh. - */ -{ -/* - * (these tests done before eql_fn is called). - * if (a == b) return YES; - * if ((((int32)a ^ (int32)b) & TAG_BITS) != 0) return NO; - * - * Actually in Common Lisp mode where I have short floats as immediate data - * I have further pain here with (eql 0.0 -0.0). - */ -#ifdef COMMON - if ((a == TAG_SFLOAT && b == (TAG_SFLOAT|0x80000000)) || - (a == (TAG_SFLOAT|0x80000000) && b == TAG_SFLOAT) return YES; -#endif - if (!is_number(a) || is_immed_or_cons(a)) return NO; - if (is_bfloat(a)) - { Header h = flthdr(a); - if (h != flthdr(b)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != - *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; - else return YES; -#else - return (single_float_val(a) == single_float_val(b)); -#endif - } - else -#endif -/* - * For the moment I view all non-single floats as double floats. Extra - * stuff will be needed here if I ever implement long floats as 3-word - * objects. - */ - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) return NO; - else return YES; -#else - return (double_float_val(a) == double_float_val(b)); -#endif - } - } - else /* ratio, complex or bignum */ - { Header h = numhdr(a); - if (h != numhdr(b)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)a + hh) != - *(Lisp_Object *)((char *)b + hh)) - return NO; - } - return YES; - } -#ifdef COMMON - else return eql_numbers(a, b); -#else - else return NO; -#endif - } -} - -static CSLbool cl_vec_equal(Lisp_Object a, Lisp_Object b) -/* - * here a and b are known to be vectors or arrays. This should compare - * them following the Common Lisp recipe, where strings or bitvectors - * (simple or complex) have their contents compared, while all other types of - * vector or array are tested using EQ. - */ -{ - Header ha = vechdr(a), hb = vechdr(b); - int32 offa = 0, offb = 0; - int ta = type_of_header(ha), tb = type_of_header(hb); - int32 la = length_of_header(ha), lb = length_of_header(hb); -#ifdef COMMON - if (header_of_bitvector(ha)) ta = TYPE_BITVEC1; - if (header_of_bitvector(hb)) tb = TYPE_BITVEC1; -#endif - switch (ta) - { -/* -case TYPE_ARRAY: -/* My moan here is that, as noted above, I ought to process even - * non-simple strings and bit-vectors by comparing contents, but as a - * matter of idleness I have not yet got around to that. In fact if I get - * arrays to compare here I will pretend that they are not strings or - * bit-vectors and compare using EQ... - */ -case TYPE_STRING: - switch (tb) - { -/* /* - case TYPE_ARRAY: -*/ - case TYPE_STRING: - goto compare_strings; - default:return NO; - } -#ifdef COMMON -case TYPE_BITVEC1: - switch (tb) - { -/* /* - case TYPE_ARRAY: -*/ - case TYPE_BITVEC1: - goto compare_bits; - default:return NO; - } -#endif -default: return (a == b); - } -compare_strings: - if (la != lb) return NO; - while (la > 0) - { la--; - if (*((char *)a + la + offa - TAG_VECTOR) != - *((char *)b + la + offb - TAG_VECTOR)) return NO; - } - return YES; -#ifdef COMMON -compare_bits: - if (la != lb) return NO; - while (la > 0) - { la--; - if (*((char *)a + la + offa - TAG_VECTOR) != - *((char *)b + la + offb - TAG_VECTOR)) return NO; - } - return YES; -#endif -} - -CSLbool cl_equal_fn(Lisp_Object a, Lisp_Object b) -/* - * a and b are not EQ at this stage.. I guarantee to have checked that - * before entering this general purpose code. - */ -{ - Lisp_Object nil = C_nil; - CSL_IGNORE(nil); -/* - * The for loop at the top here is so that cl_equal can iterate along the - * length of linear lists. - */ -#ifdef CHECK_STACK - if (check_stack(__FILE__,__LINE__)) - { err_printf("Stack too deep in cl_equal\n"); - my_exit(EXIT_FAILURE); - } -#endif - for (;;) - { - int32 ta = (int32)a & TAG_BITS; - if (ta == TAG_CONS -#ifdef COMMON - && a != nil -#endif - ) - { if (!consp(b) -#ifdef COMMON - || b == nil -#endif - ) return NO; - else - { Lisp_Object ca = qcar(a), cb = qcar(b); - if (ca == cb) - { a = qcdr(a); - b = qcdr(b); - if (a == b) return YES; - continue; - } -/* - * And here, because cl_equal() seems to be a very important low-level - * primitive, I unwind one level of the recursion that would arise - * with nested lists. - */ - for (;;) - { - int32 tca = (int32)ca & TAG_BITS; - if (tca == TAG_CONS -#ifdef COMMON - && ca != nil -#endif - ) - { if (!consp(cb) -#ifdef COMMON - || cb == nil -#endif - ) return NO; - else - { Lisp_Object cca = qcar(ca), ccb = qcar(cb); - if (cca == ccb) - { ca = qcdr(ca); - cb = qcdr(cb); - if (ca == cb) break; - continue; - } -/* - * Do a real recursion when I get down to args like - * ((x ...) ...) ((y ...) ...) - */ - if (!cl_equal(cca, ccb)) return NO; - ca = qcdr(ca); - cb = qcdr(cb); - if (ca == cb) break; - continue; - } - } - else if (tca <= TAG_SYMBOL || - ((int32)cb & TAG_BITS) != tca) return NO; - else switch (tca) - { - case TAG_NUMBERS: - { Header h = numhdr(ca); - if (h != numhdr(cb)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)ca + hh) != - *(Lisp_Object *)((char *)cb + hh)) - return NO; - } - break; - } -#ifdef COMMON - else if (!eql_numbers(ca, cb)) return NO; - else break; -#else - else return NO; -#endif - } - case TAG_VECTOR: - if (!cl_vec_equal(ca, cb)) return NO; - break; - default: - case TAG_BOXFLOAT: - { Header h = flthdr(ca); - if (h != flthdr(cb)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != - *(int32 *)(cb + (4 - TAG_BOXFLOAT))) - return NO; -#else - if (single_float_val(ca) != - single_float_val(cb)) return NO; -#endif - else break; - } - else -#endif - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)ca + - (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)ca + - (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (12 - TAG_BOXFLOAT)))) return NO; -#else - if (double_float_val(ca) != - double_float_val(cb)) return NO; -#endif - else break; - } - } - } - break; /* out of the for (;;) loop */ - } - a = qcdr(a); - b = qcdr(b); - if (a == b) return YES; - continue; - } - } - else if (ta <= TAG_SYMBOL || - ((int32)b & TAG_BITS) != ta) return NO; - else switch (ta) - { - case TAG_NUMBERS: - { Header h = numhdr(a); - if (h != numhdr(b)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)a + hh) != - *(Lisp_Object *)((char *)b + hh)) - return NO; - } - return YES; - } -#ifdef COMMON - else return eql_numbers(a, b); - -#else - else return NO; -#endif - } - case TAG_VECTOR: - return cl_vec_equal(a, b); - default: - case TAG_BOXFLOAT: - { Header h = flthdr(a); - if (h != flthdr(b)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != - *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; -#else - if (single_float_val(a) != single_float_val(b)) - return NO; -#endif - else return YES; - } - else -#endif -/* - * For the moment I view all non-single floats as double floats. Extra - * stuff will be needed here if I ever implement long floats as 3-word - * objects. - */ - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) - return NO; -#else - if (double_float_val(a) != double_float_val(b)) - return NO; -#endif - else return YES; - } - } - } - } -} - -static CSLbool vec_equal(Lisp_Object a, Lisp_Object b); - -#ifdef TRACED_EQUAL -#define LOG_SIZE 10000 -typedef struct equal_record -{ - char file[24]; - int line; - int depth; - int count; -} equal_record; - -static equal_record equal_counts[LOG_SIZE]; - -static void record_equal(char *file, int line, int depth) -{ - int hash = 169*line + depth; - char *p = file; - while (*p != 0) hash = 168*hash + (*p++ & 0xff); - hash = ((169*hash) & 0x7fffffff) % LOG_SIZE; - while (equal_counts[hash].count != 0) - { if (equal_counts[hash].line == line && - equal_counts[hash].depth == depth && - strncmp(equal_counts[hash].file, file, 24) == 0) - { equal_counts[hash].count++; - return; - } - hash = (hash + 1) % LOG_SIZE; - } - strncpy(equal_counts[hash].file, file, 24); - equal_counts[hash].line = line; - equal_counts[hash].depth = depth; - equal_counts[hash].count = 1; - return; -} - -void dump_equals() -{ - int i; - FILE *log = fopen("equal.log", "w"); - if (log == NULL) log = stdout; - fprintf(log, "\nCalls to equal...\n"); - for (i=0; i (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)ca + hh) != - *(Lisp_Object *)((char *)cb + hh)) - return NO; - } - break; - } -#ifdef COMMON - else if (!eql_numbers(ca, cb)) return NO; - else break; -#else - else return NO; -#endif - } - case TAG_VECTOR: - if (!vec_equal(ca, cb)) return NO; - break; - default: - case TAG_BOXFLOAT: - { Header h = flthdr(ca); - if (h != flthdr(cb)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != - *(int32 *)(cb + (4 - TAG_BOXFLOAT))) - return NO; -#else - if (single_float_val(ca) != - single_float_val(cb)) return NO; -#endif - else break; - } - else -#endif - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)ca + - (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)ca + - (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (12 - TAG_BOXFLOAT)))) return NO; -#else - if (double_float_val(ca) != - double_float_val(cb)) return NO; -#endif - - else break; - } - } - } - break; /* out of the for (;;) loop */ - } - a = qcdr(a); - b = qcdr(b); - if (a == b) return YES; - continue; - } - } - else if (ta <= TAG_SYMBOL || - ((int32)b & TAG_BITS) != ta) return NO; - else switch (ta) - { - case TAG_NUMBERS: - { Header h = numhdr(a); - if (h != numhdr(b)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)a + hh) != - *(Lisp_Object *)((char *)b + hh)) - return NO; - } - return YES; - } -#ifdef COMMON - else return eql_numbers(a, b); - -#else - else return NO; -#endif - } - case TAG_VECTOR: - return vec_equal(a, b); - default: - case TAG_BOXFLOAT: - { Header h = flthdr(a); - if (h != flthdr(b)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != - *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; -#else - if (single_float_val(a) != single_float_val(b)) - return NO; -#endif - else return YES; - } - else -#endif -/* - * For the moment I view all non-single floats as double floats. Extra - * stuff will be needed here if I ever implement long floats as 3-word - * objects. - */ - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) - return NO; -#else - if (double_float_val(a) != double_float_val(b)) - return NO; -#endif - else return YES; - } - } - } - } -} - -#ifdef TRACED_EQUAL -#undef equal_fn -#define equal_fn(a, b) traced_equal(a, b, __FILE__, __LINE__, 0) -#endif - -static CSLbool vec_equal(Lisp_Object a, Lisp_Object b) -/* - * Here a and b are known to be vectors. Compare using recursive calls to - * EQUAL on all components. - */ -{ - Header ha = vechdr(a), hb = vechdr(b); - int32 l; - if (ha != hb) return NO; - l = (int32)doubleword_align_up(length_of_header(ha)); - if (vector_holds_binary(ha)) - { while ((l -= 4) != 0) - if (*((int32 *)((char *)a + l - TAG_VECTOR)) != - *((int32 *)((char *)b + l - TAG_VECTOR))) return NO; - return YES; - } - else - { if (is_mixed_header(ha)) - { while (l > 16) - { unsigned32 ea = *((unsigned32 *)((char *)a + l - TAG_VECTOR - 4)), - eb = *((unsigned32 *)((char *)b + l - TAG_VECTOR - 4)); - if (ea != eb) return NO; - l -= 4; - } - } - while ((l -= 4) != 0) - { Lisp_Object ea = *((Lisp_Object *)((char *)a + l - TAG_VECTOR)), - eb = *((Lisp_Object *)((char *)b + l - TAG_VECTOR)); - if (ea == eb) continue; - if (!equal(ea, eb)) return NO; - } - return YES; - } -} - -CSLbool equalp(Lisp_Object a, Lisp_Object b) -/* - * a and b are not EQ at this stage.. I guarantee to have checked that - * before entering this general purpose code. - */ -{ - Lisp_Object nil = C_nil; - CSL_IGNORE(nil); -/* - * The for loop at the top here is so that equalp can iterate along the - * length of linear lists. - */ -#ifdef CHECK_STACK - if (check_stack(__FILE__,__LINE__)) - { err_printf("Stack too deep in equalp\n"); - my_exit(EXIT_FAILURE); - } -#endif - for (;;) - { - int32 ta = (int32)a & TAG_BITS; - if (ta == TAG_CONS -#ifdef COMMON - && a != nil -#endif - ) - { if (!consp(b) -#ifdef COMMON - || b == nil -#endif - ) return NO; - else - { Lisp_Object ca = qcar(a), cb = qcar(b); - if (ca == cb) - { a = qcdr(a); - b = qcdr(b); - if (a == b) return YES; - continue; - } -/* - * And here, because equalp() seems to be a very important low-level - * primitive, I unwind one level of the recursion that would arise - * with nested lists. - */ - for (;;) - { - int32 tca = (int32)ca & TAG_BITS; - if (tca == TAG_CONS -#ifdef COMMON - && ca != nil -#endif - ) - { if (!consp(cb) -#ifdef COMMON - || cb == nil -#endif - ) return NO; - else - { Lisp_Object cca = qcar(ca), ccb = qcar(cb); - if (cca == ccb) - { ca = qcdr(ca); - cb = qcdr(cb); - if (ca == cb) break; - continue; - } -/* - * Do a real recursion when I get down to args like - * ((x ...) ...) ((y ...) ...) - */ - if (!equalp(cca, ccb)) return NO; - ca = qcdr(ca); - cb = qcdr(cb); - if (ca == cb) break; - continue; - } - } - else if (tca <= TAG_SYMBOL || - ((int32)cb & TAG_BITS) != tca) return NO; - else switch (tca) - { - case TAG_NUMBERS: - { Header h = numhdr(ca); - if (h != numhdr(cb)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)ca + hh) != - *(Lisp_Object *)((char *)cb + hh)) - return NO; - } - break; - } -#ifdef COMMON - else if (!eql_numbers(ca, cb)) return NO; - else break; -#else - else return NO; -#endif - } - case TAG_VECTOR: -/* /* At present vec_equal() is not right here */ - if (!vec_equal(ca, cb)) return NO; - break; - default: - case TAG_BOXFLOAT: - { Header h = flthdr(ca); - if (h != flthdr(cb)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != - *(int32 *)(cb + (4 - TAG_BOXFLOAT))) - return NO; -#else - if (single_float_val(ca) != - single_float_val(cb)) return NO; -#endif - - else break; - } - else -#endif - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)ca + - (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)ca + - (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)cb + - (12 - TAG_BOXFLOAT)))) return NO; -#else - if (double_float_val(ca) != - double_float_val(cb)) return NO; -#endif - else break; - } - } - } - break; /* out of the for (;;) loop */ - } - a = qcdr(a); - b = qcdr(b); - if (a == b) return YES; - continue; - } - } - else if (ta <= TAG_SYMBOL || - ((int32)b & TAG_BITS) != ta) return NO; - else switch (ta) - { - case TAG_NUMBERS: - { Header h = numhdr(a); - if (h != numhdr(b)) return NO; - if (type_of_header(h) == TYPE_BIGNUM) - { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; - while (hh > (4 - TAG_NUMBERS)) - { hh -= 4; - if (*(Lisp_Object *)((char *)a + hh) != - *(Lisp_Object *)((char *)b + hh)) - return NO; - } - return YES; - } -#ifdef COMMON - else return eql_numbers(a, b); - -#else - else return NO; -#endif - } - case TAG_VECTOR: -/* /* wrong for Common Lisp */ - return vec_equal(a, b); - default: - case TAG_BOXFLOAT: - { Header h = flthdr(a); - if (h != flthdr(b)) return NO; - h = length_of_header(h); -#ifdef COMMON - if (h == 8) /* Single float */ - { -#ifdef OLD_CODE - if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != - *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; -#else - if (single_float_val(a) != single_float_val(b)) - return NO; -#endif - else return YES; - } - else -#endif -/* - * For the moment I view all non-single floats as double floats. Extra - * stuff will be needed here if I ever implement long floats as 3-word - * objects. - */ - { -#ifdef OLD_CODE - if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || - (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != - *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) - return NO; -#else - if (double_float_val(a) != double_float_val(b)) - return NO; -#endif - - else return YES; - } - } - } - } -} - -Lisp_Object Leq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - return onevalue(Lispify_predicate(a == b)); -} - -Lisp_Object Leql(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -{ - return onevalue(Lispify_predicate(eql(a, b))); -} - -Lisp_Object Leqcar(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -{ - if (!consp(a)) return onevalue(nil); - a = qcar(a); -#ifdef COMMON - return onevalue(Lispify_predicate(eql(a, b))); -#else - return onevalue(Lispify_predicate(a == b)); -#endif -} - -Lisp_Object Lequalcar(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -{ - if (!consp(a)) return onevalue(nil); - a = qcar(a); - if (a == b) return lisp_true; - else return onevalue(Lispify_predicate(equal(a, b))); -} - -Lisp_Object Lcl_equal(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - if (a == b) return onevalue(lisp_true); - else return onevalue(Lispify_predicate(cl_equal(a, b))); -} - -Lisp_Object Lequal(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - if (a == b) return onevalue(lisp_true); - else return onevalue(Lispify_predicate(equal(a, b))); -} - -Lisp_Object Lequalp(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - if (a == b) return onevalue(lisp_true); - else return onevalue(Lispify_predicate(equalp(a, b))); -} - -Lisp_Object Lneq(Lisp_Object nil, - Lisp_Object a, Lisp_Object b) -{ - CSLbool r; -#ifdef COMMON - r = cl_equal(a, b); -#else - r = equal(a, b); -#endif - return onevalue(Lispify_predicate(!r)); -} - -Lisp_Object Lnull(Lisp_Object nil, Lisp_Object a) -{ - return onevalue(Lispify_predicate(a == nil)); -} - -Lisp_Object Lendp(Lisp_Object nil, Lisp_Object a) -{ - if (a == nil) return onevalue(lisp_true); - else if (is_cons(a)) return onevalue(nil); - else return error(1, err_bad_endp, a); -} - -Lisp_Object Lnreverse(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object b = nil; -#ifdef COMMON - if (is_vector(a)) - { int32 n = Llength(nil, a) - 0x10; - int32 i = TAG_FIXNUM; - while (n > i) - { Lisp_Object w = Laref2(nil, a, i); - Laset(nil, 3, a, i, Laref2(nil, a, n)); - Laset(nil, 3, a, n, w); - i += 0x10; - n -= 0x10; - } - return onevalue(a); - } -#endif - while (consp(a)) - { Lisp_Object c = a; - a = qcdr(a); - qcdr(c) = b; - b = c; - } - return onevalue(b); -} - -#ifdef COMMON - -/* - * nreverse0 is like nreverse except that if its input is atomic it gets - * returned intact rather than being converted to nil. - */ - -Lisp_Object Lnreverse0(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object b = nil; - if (!consp(a)) return onevalue(a); - b = a; - a = qcdr(a); - qcdr(b) = nil; - while (consp(a)) - { Lisp_Object c = a; - a = qcdr(a); - qcdr(c) = b; - b = c; - } - return onevalue(b); -} - -#endif - -Lisp_Object Lreverse(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object r; - stackcheck1(0, a); - nil = C_nil; - r = nil; - while (consp(a)) - { push(a); - r = cons(qcar(a), r); - pop(a); - errexit(); - a = qcdr(a); - } - return onevalue(r); -} - -Lisp_Object Lassoc(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ -#ifdef TRACED_EQUAL - Lisp_Object save_b = b; - int pos = 0; -#endif - if (is_symbol(a) || is_fixnum(a)) - { while (consp(b)) - { Lisp_Object c = qcar(b); - if (consp(c) && a == qcar(c)) return onevalue(c); - b = qcdr(b); - } - return onevalue(nil); - } - while (consp(b)) - { Lisp_Object c = qcar(b); - if (consp(c)) - { Lisp_Object cc = qcar(c); -#ifdef COMMON - if (cl_equal(a, cc)) return onevalue(c); -#else - if (equal(a, cc)) - { -#ifdef TRACED_EQUAL - trace_printf("Assoc YES %3d %3d ", pos, int_of_fixnum(Llength(nil,save_b))); - prin_to_stdout(a); trace_printf("\n"); -#endif - return onevalue(c); - } -#endif - } - b = qcdr(b); -#ifdef TRACED_EQUAL - pos++; -#endif - } -#ifdef TRACED_EQUAL - trace_printf("Assoc NO %3d %3d ", pos, int_of_fixnum(Llength(nil,save_b))); - prin_to_stdout(a); trace_printf("\n"); -#endif - return onevalue(nil); -} - -Lisp_Object Latsoc(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ -#ifdef COMMON - if (is_symbol(a) || is_fixnum(a)) - { while (consp(b)) - { Lisp_Object c = qcar(b); - if (consp(c) && a == qcar(c)) return onevalue(c); - b = qcdr(b); - } - return onevalue(nil); - } -#endif - while (consp(b)) - { Lisp_Object c = qcar(b); -/* - * eql() can neither fail nor call the garbage collector, so I do - * not need to stack things here. - */ -#ifdef COMMON - if (consp(c) && eql(a, qcar(c))) return onevalue(c); -#else - if (consp(c) && a == qcar(c)) return onevalue(c); -#endif - b = qcdr(b); - } - return onevalue(nil); -} - -Lisp_Object Lmember(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - if (is_symbol(a) || is_fixnum(a)) - { while (consp(b)) - { if (a == qcar(b)) return onevalue(b); - b = qcdr(b); - } - return onevalue(nil); - } - while (consp(b)) - { Lisp_Object cb = qcar(b); -#ifdef COMMON - if (cl_equal(a, cb)) return onevalue(b); -#else - if (equal(a, cb)) return onevalue(b); -#endif - b = qcdr(b); - } - return onevalue(nil); -} - -Lisp_Object Lmemq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ -#ifdef COMMON - if (is_symbol(a) || is_fixnum(a)) - { while (consp(b)) - { if (a == qcar(b)) return onevalue(b); - b = qcdr(b); - } - return onevalue(nil); - } -#endif - while (consp(b)) -/* - * Note that eql() can never fail, and so checking for errors - * and stacking a and b across the call to it is not necessary. - */ - { -#ifdef COMMON - if (eql(a, qcar(b))) return onevalue(b); -#else - if (a == qcar(b)) return onevalue(b); -#endif - b = qcdr(b); - } - return onevalue(nil); -} - -static CSLbool smemq(Lisp_Object a, Lisp_Object b) -{ -/* - * /* This is a bit worrying - it can use C recursion to arbitrary - * depth without any checking for overflow, and hence it can ESCAPE - * if (e.g.) given cyclic structures. Some alteration is needed. As - * things stand the code can never give wrong answers via GC rearrangement - - * the problem is closer to being that it can never call the GC. - */ -#ifdef COMMON - Lisp_Object nil = C_nil; -#else - nil_as_base -#endif - while (consp(b)) - { Lisp_Object w = qcar(b); - if (w == quote_symbol) return NO; - else if (smemq(a, w)) return YES; - else b = qcdr(b); - } - return (a == b); -} - -Lisp_Object Lsmemq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) -{ - CSLbool r; - r = smemq(a, b); - errexit(); - return onevalue(Lispify_predicate(r)); -} - -/* - * (defun contained (x y) - * (cond ((atom y) (equal x y)) - * ((equal x y) 't) - * ('t (or (contained x (car y)) (contained x (cdr y)))))) - */ - -static CSLbool containedeq(Lisp_Object nil, Lisp_Object x, Lisp_Object y) -{ - while (consp(y)) - { if (containedeq(nil, x, qcar(y))) return YES; - y = qcdr(y); - } - return (x == y); -} - -static CSLbool containedequal(Lisp_Object nil, Lisp_Object x, Lisp_Object y) -{ - while (consp(y)) - { if (equal(x, y)) return YES; - if (containedequal(nil, x, qcar(y))) return YES; - y = qcdr(y); - } - return equal(x, y); -} - -static Lisp_Object Lcontained(Lisp_Object nil, Lisp_Object x, Lisp_Object y) -{ - CSLbool r; - if (is_symbol(x) || is_fixnum(x)) r = containedeq(nil, x, y); - else r = containedequal(nil, x, y); - errexit(); - return onevalue(Lispify_predicate(r)); -} - -Lisp_Object Llast(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object b; - if (!consp(a)) return aerror1("last", a); - while (b = qcdr(a), consp(b)) a = b; - return onevalue(qcar(a)); -} - -Lisp_Object Llastpair(Lisp_Object nil, Lisp_Object a) -{ - Lisp_Object b; - if (!consp(a)) return onevalue(a); /* aerror1("lastpair", a); */ - while (b = qcdr(a), consp(b)) a = b; - return onevalue(a); -} - -Lisp_Object Llength(Lisp_Object nil, Lisp_Object a) -{ - if (a == nil) return onevalue(fixnum_of_int(0)); - if (is_cons(a)) - { Lisp_Object n; -/* - * Possibly I should do something to trap cyclic lists.. ? - */ - n = fixnum_of_int(1); -/* - * I have unrolled the loop here 4 times since I expect length to be - * tolerably heavily used. Look at the assembly code generated for - * this to see if it was useful or counterproductive! - */ - for (;;) - { a = qcdr(a); - if (!consp(a)) return onevalue(n); - a = qcdr(a); - if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (1 << 4))); - a = qcdr(a); - if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (2 << 4))); - a = qcdr(a); - if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (3 << 4))); - n = (Lisp_Object)((int32)n + (4 << 4)); - } - } -#ifndef COMMON - return onevalue(fixnum_of_int(0)); /* aerror("length");??? */ -#else -/* - * Common Lisp expects length to find the length of vectors - * as well as lists. - */ - else if (!is_vector(a)) return aerror1("length", a); - else - { Header h = vechdr(a); - int32 n = length_of_header(h) - 4; - if (type_of_header(h) == TYPE_ARRAY) - { Lisp_Object dims = elt(a, 1); - Lisp_Object fillp = elt(a, 5); - if (consp(dims) && !consp(qcdr(dims))) dims = qcar(dims); - else return aerror1("length", a); /* Not one-dimensional */ - if (is_fixnum(fillp)) dims = fillp; - return onevalue(dims); - } - if (header_of_bitvector(h)) - { n = (n - 1)*8; -/* Dodgy constant on next line - critically dependent on tag codes used! */ - n += ((h & 0x380) >> 7) + 1; - } - else if (type_of_header(h) != TYPE_STRING) n = n >> 2; - return onevalue(fixnum_of_int(n)); - } -#endif -} - -#ifdef COMMON - -Lisp_Object MS_CDECL Lappend_n(Lisp_Object nil, int nargs, ...) -{ - va_list a; - int i; - Lisp_Object r; - if (nargs == 0) return onevalue(nil); - va_start(a, nargs); - push_args(a, nargs); -/* - * The actual args have been passed a C args - I can not afford to - * risk garbage collection until they have all been moved somewhere safe, - * and here that safe place is the Lisp stack. I have to delay checking for - * overflow on same until all args have been pushed. - */ - stackcheck0(nargs); - nil = C_nil; - r = nil; -/* - * rearrange order of items on the stack... - * The idea is that I will then reverse-copy the args in the order a1, - * a2 , ... to make a result list. But I want to pop the stack as soon as - * I can, so I need arg1 on the TOP of the stack. - */ - for (i = 0; 2*i+1 +#include +#include + +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "entries.h" +#include "arith.h" +#ifdef COMMON +#include "clsyms.h" +#endif +#ifdef TIMEOUT +#include "timeout.h" +#endif + +#ifdef SOCKETS +#include "sockhdr.h" +#endif + +Lisp_Object getcodevector(int32 type, int32 size) +{ +/* + * type is the code (e.g. TYPE_BPS) that gets packed, together with + * the size, into a header word. + * size is measured in bytes and must allow space for the header word. + * This obtains space in the BPS area + */ + Lisp_Object nil = C_nil; +#ifdef CHECK_FOR_CORRUPT_HEAP + validate_all(); +#endif + for (;;) + { int32 alloc_size = (int32)doubleword_align_up(size); + char *cf = (char *)codefringe, *cl = (char *)codelimit; + unsigned int free = cf - cl; + char *r; + if (alloc_size > (int32)free) + { char msg[40]; + sprintf(msg, "codevector %ld", (long)size); + reclaim(nil, msg, GC_BPS, alloc_size); + errexit(); + continue; + } + r = cf - alloc_size; + codefringe = (Lisp_Object)r; + *((Header *)r) = type + (size << 10) + TAG_ODDS; + return TAG_BPS + + (((int32)(r - cl + 12) & (PAGE_POWER_OF_TWO-4)) << 6) + + (((int32)(bps_pages_count-1))<<(PAGE_BITS+6)); /* Wow! Obscure!! */ + } +} + +Lisp_Object Lget_bps(Lisp_Object nil, Lisp_Object n) +{ + int32 n1; + if (!is_fixnum(n) || (int32)n<0) return aerror1("get-bps", n); + n1 = int_of_fixnum(n); + n = getcodevector(TYPE_BPS, n1+4); + errexit(); + return onevalue(n); +} + +Lisp_Object get_native_code_vector(int32 size) +{ +/* + * Create some space for native code and return a handle that identifies + * its start point. size is measured in bytes. + */ + Lisp_Object nil = C_nil; + if (size <= 0) size = 8; + for (;;) + { int32 alloc_size = (int32)doubleword_align_up(size); + int32 cf = native_fringe; + int32 free = CSL_PAGE_SIZE - cf - 0x100; /* 256 bytes to be safe */ +/* + * When I start up a cold CSL I will have native_fringe set to zero and + * native_pages_count also zero, indicating that there is none of this stuff + * active. + */ + if (native_fringe == 0 || alloc_size > free) + { char msg[40]; + sprintf(msg, "native code %ld", (long)size); + reclaim(nil, msg, GC_NATIVE, alloc_size); + errexit(); + continue; + } + free = (int32)native_pages[native_pages_count-1]; + free = doubleword_align_up(free); +/* + * I put the number of bytes in this block as the first word of the chunk + * of memory, and arrange that there is a zero in what would be the first + * word of unused space. Provided the user does not clobber bytes 0 to 4 + * or the block this is enough to allow restart code to scan through all + * native code segments. + */ + *(int32 *)(free+native_fringe) = alloc_size; + *(int32 *)(free+native_fringe+alloc_size) = 0; + native_fringe += alloc_size; + native_pages_changed = 1; + return Lcons(nil, + fixnum_of_int(native_pages_count-1), + fixnum_of_int(cf)); + } +} + +Lisp_Object Lget_native(Lisp_Object nil, Lisp_Object n) +{ + int32 n1; + if (!is_fixnum(n) || (int32)n<0) return aerror1("get-native", n); + n1 = int_of_fixnum(n); + n = get_native_code_vector(n1); + errexit(); + return onevalue(n); +} + +int do_not_kill_native_code = 0; + +void set_fns(Lisp_Object a, one_args *f1, two_args *f2, n_args *fn) +{ + Lisp_Object nil = C_nil; + Lisp_Object w1, w2, w3 = nil; +/* + * If I redefine a function for any reason (except to set trace options + * on a bytecoded definition) I will discard any native-coded definitions + * by splicing them out of the record. I provide a global variable to + * defeat this behaviour (ugh). + */ + if (!do_not_kill_native_code) + { for (w1 = native_code; w1!=nil; w1=qcdr(w1)) + { w2 = qcar(w1); + if (qcar(w2) == a) break; + w3 = w1; + } + if (w1 != nil) + { w1 = qcdr(w1); + if (w3 == nil) native_code = w1; + else qcdr(w3) = w1; + } + } + if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == + (SYM_C_DEF | SYM_CODEPTR)) + { +#ifdef NOISY_RE_PROTECTED_FNS + trace_printf("+++ protected function "); + prin_to_trace(a); + trace_printf(" not redefined\n"); +#endif + return; + } + ifn1(a) = (int32)f1; + ifn2(a) = (int32)f2; + ifnn(a) = (int32)fn; +} + +#ifdef HIDE_USELESS_SYMBOL_ENVIRONMENTS + +static CSLbool interpreter_entry(Lisp_Object a) +/* + * If a function will be handled by the interpreter, including the case + * of it being undefined, then the fn1() cell will tell me so. + */ +{ + return ( + qfn1(a) == interpreted1 || + qfn1(a) == traceinterpreted1 || + qfn1(a) == double_interpreted1 || + qfn1(a) == funarged1 || + qfn1(a) == tracefunarged1 || + qfn1(a) == double_funarged1 || + qfn1(a) == undefined1); +} + +#endif + +static char *show_fn(void *p) +{ + int i; + for (i=0; i MAX_FASTGET_SIZE)) return aerror1("symbol-make-fastget", a); + term_printf("+++ Fastget size was %d, now %d\n", n1, n); + fastget_size = n; + return onevalue(fixnum_of_int(n1)); +} + +Lisp_Object Lsymbol_make_fastget(Lisp_Object nil, Lisp_Object a, Lisp_Object n) +{ + int32 n1, p, q; + Header h; + if (!symbolp(a)) return onevalue(nil); + h = qheader(a); + p = header_fastget(h); + if (is_fixnum(n)) + { n1 = int_of_fixnum(n); + if (n1 < -1 || n1 >= fastget_size) + return aerror1("symbol-make-fastget", n); + trace_printf("+++ Use fastget slot %d for ", n1); + loop_print_trace(a); + errexit(); + trace_printf("\n"); + if (p != 0) elt(fastget_names, p-1) = SPID_NOPROP; + q = (n1 + 1) & 0x3f; + h = (h & ~SYM_FASTGET_MASK) | (q << SYM_FASTGET_SHIFT); + qheader(a) = h; + if (q != 0) elt(fastget_names, q-1) = a; + } + if (p == 0) return onevalue(nil); + else return onevalue(fixnum_of_int(p - 1)); +} + +static Lisp_Object deleqip(Lisp_Object a, Lisp_Object l) +/* + * This deletes the item a (tested for using EQ) from the list l, + * assuming that the list is nil-terminated and that the item a + * occurs at most once. It overwrites the list l in the process. + */ +{ + Lisp_Object nil = C_nil, w, r; + if (l == nil) return nil; + if (qcar(l) == a) return qcdr(l); + r = l; + while (w = l, (l = qcdr(l)) != nil) + { if (qcar(l) == a) + { qcdr(w) = qcdr(l); + return r; + } + } + return r; +} + +void lose_C_def(Lisp_Object a) +{ +/* + * None of the code here can cause garbage collection. + */ +#ifdef COMMON + Lisp_Object nil = C_nil; + Lisp_Object b = get(a, unset_var, nil), c; +#else + nil_as_base + Lisp_Object b = get(a, unset_var), c; +#endif + Lremprop(C_nil, a, unset_var); + qheader(a) &= ~SYM_C_DEF; +#ifdef COMMON + c = get(b, work_symbol, nil); +#else + c = get(b, work_symbol); +#endif + c = deleqip(a, c); + if (c == C_nil) Lremprop(C_nil, b, work_symbol); + else putprop(b, work_symbol, c); +} + +/* + * (symbol-set-native fn args bpsbase offset env) + * where bpsbase is as handed back by (make-native nnn) and offset is + * the offset in this block to enter at. + * If args has the actual arg count in its bottom byte. Usually the + * rest of it will be zero, and then one function cell is set to point to the + * given entrypoint and the other two are set to point at error handlers. + * If any bits in args beyond that are set then this call only changes the + * directly specified function cell, and the others are left in whatever state + * they were. If several of the fuction cells are to be filled in (eg to cope + * with &optional or &rest arguments) then a simple call with args<256 must + * be made first, followed by the calls (args>=256) that fill in the other + * two cells. + * The first time that symbol-set-native is called on a function that + * function MUST have a byte coded definition, and this definition is + * picked up and stored away, so that if (preserve) is called the bytecoded + * definition will be available for use on systems with different + * architectures. To make things tolerably consistent with that any operation + * that installs a new bytecoded (or for that matter other) definition + * will clear away any native-compiled versions of the function. + * + * The native code that is installed will be expected to have relocation + * records starting at the start of bpsbase, and these will be activated, + * filling in references from the bps to other executable parts of Lisp. + * Passing bad arguments to this function provide a quick and easy way to + * cayse UTTER havoc. Therefore I disable its use in server applications. + */ + +Lisp_Object MS_CDECL Lsymbol_set_native(Lisp_Object nil, int nargs, ...) +{ + va_list a; + Lisp_Object fn, args, bpsbase, offset, env, w1, w2, w3; + int32 pagenumber, page, bps, address, t_p, arginfo; +#ifdef SOCKETS +/* + * Security measure - deny symbol-set-native to remote users + */ + if (socket_server != 0) return aerror("symbol-set-native"); +#endif + argcheck(nargs, 5, "symbol-set-native"); + va_start(a, nargs); + fn = va_arg(a, Lisp_Object); + args = va_arg(a, Lisp_Object); + bpsbase = va_arg(a, Lisp_Object); + offset = va_arg(a, Lisp_Object); + env = va_arg(a, Lisp_Object); + va_end(a); + if (!is_symbol(fn) || + (qheader(fn) & (SYM_SPECIAL_FORM | SYM_CODEPTR)) != 0) + return aerror1("symbol-set-native", fn); + if (!is_fixnum(args)) return aerror1("symbol-set-native", args); + if (!consp(bpsbase) || + !is_fixnum(qcar(bpsbase)) || + !is_fixnum(qcdr(bpsbase))) + return aerror1("symbol-set-native", bpsbase); + if (!is_fixnum(offset)) return aerror1("symbol-set-native", offset); + nargs = int_of_fixnum(args); + pagenumber = int_of_fixnum(qcar(bpsbase)); + if (pagenumber<0 || pagenumber>=native_pages_count) + return aerror1("symbol-set-native", bpsbase); + bps = int_of_fixnum(qcdr(bpsbase)); + address = bps+int_of_fixnum(offset); + if (address<8 || address>=CSL_PAGE_SIZE) + return aerror1("symbol-set-native", offset); + page = (int32)native_pages[pagenumber]; + page = doubleword_align_up(page); + bps = page + bps; + relocate_native_function((unsigned char *)bps); +/* + * Here I need to push the info I have just collected onto + * the native_code list since otherwise things will not be re-loaded in + * from a checkpoint image. Also if the function is at present byte-coded + * I need to record that info about it in native_code. + */ + w1 = native_code; + while (w1!=nil) + { w2 = qcar(w1); + if (qcar(w2) == fn) break; + w1 = qcdr(w1); + } + if (w1 == nil) + { +/* + * Here the function has not been seen as native code ever before, so it has + * not been entered into the list. Do something about that... + */ + push2(env, fn); + args = Lsymbol_argcount(nil, fn); + errexitn(2); + if (args == nil) + return aerror1("No bytecode definition found for", fn); +/* + * Now I have to reverse the information that symbol_argcount gave me + * to get the single numeric code as wanted by symbol_set_definition. + * Oh what a mess. + */ + if (is_fixnum(args)) arginfo = int_of_fixnum(args); + else + { arginfo = int_of_fixnum(qcar(args)); + args = qcdr(args); + arginfo |= ((int_of_fixnum(qcar(args)) - arginfo) << 8); + args = qcdr(args); + arginfo |= int_of_fixnum(qcar(args)) << 16; + } + fn = stack[0]; + w2 = list2(fn, fixnum_of_int(arginfo)); + errexitn(2); + w2 = cons(w2, native_code); + errexitn(2); + native_code = w2; + w2 = qcar(w2); + pop2(fn, env); + } + w2 = qcdr(w2); /* {nargs,(type . offset . env),...} */ +/* + * If I was defining this function in the simple way I should clear any + * previous version (for this machine architecture) from the record. + * Just at present this does not release the memory, but at some stage + * in the future I may arrange to compact away old code when I do a + * preserve operation (say). + */ + if (nargs <= 0xff) + { w1 = w3 = w2; + for (w1=qcdr(w2); w1!=nil; w1=qcdr(w1)) + { w3 = qcar(w1); + if (qcar(w3) == fixnum_of_int(native_code_tag)) break; + w3 = w1; + } + if (w1 != nil) qcdr(w3) = qcdr(w1); + } +/* + * w2 is still the entry for this function in the native code list. It + * needs to have an entry of type 0 (ie for bytecoded) and so the next + * thing to do is to check that such an entry exists and if not to create + * it. + */ + w1 = w2; + while ((w1 = qcdr(w1)) != nil) + { w3 = qcar(w1); + if (qcar(w3) == fixnum_of_int(0)) break; + w1 = qcdr(w1); + } + if (w1 == nil) + { +/* + * This is where there was no bytecode entry on the native code list + * for this function, so I had better create one for it. Note that only + * one such entry will ever be stored so it does not matter much where on + * the list it goes. I suspect that the list ought always to be empty + * in this case anyway. + */ + push3(fn, env, w2); + w1 = list2star(fixnum_of_int(0), fixnum_of_int(0), qenv(fn)); + errexitn(3); + w2 = stack[0]; + w1 = cons(w1, qcdr(w2)); + errexitn(3); + pop3(w2, env, fn); + qcdr(w2) = w1; + } +/* + * Now the list of native code associated with this function certainly holds + * a byte-coded definition (and for sanity that had better be consistent + * with the native code I am installing now, but that is not something + * that can be checked at this level). Put in an entry referring to the + * current gubbins. + */ + push3(w2, fn, env); +/* + * now I pack the code type, arg category and offset into the + * single fixnum that that information has to end up in. + */ + t_p = (native_code_tag << 20); + if ((nargs & 0xffffff00) != 0) + { + switch (nargs & 0xff) + { + case 1: t_p |= (1<<18); break; + case 2: t_p |= (2<<18); break; + default:t_p |= (3<<18); break; + } + } + t_p |= (pagenumber & 0x3ffff); + w1 = list2star(fixnum_of_int(t_p), fixnum_of_int(address), env); + errexitn(3); + w1 = ncons(w1); + pop3(env, fn, w2); + errexit(); + while ((w3 = qcdr(w2)) != nil) w2 = w3; /* Tag onto the END */ + qcdr(w2) = w1; + qheader(fn) &= ~SYM_TRACED; + address = page + address; +/* + * The code here must do just about the equivalent to that in restart.c + */ + switch (nargs & 0xff) + { +case 0: ifnn(fn) = address; + if (nargs<=0xff) + ifn1(fn) = (int32)wrong_no_0a, ifn2(fn) = (int32)wrong_no_0b; + break; +case 1: ifn1(fn) = address; + if (nargs<=0xff) + ifn2(fn) = (int32)too_many_1, ifnn(fn) = (int32)wrong_no_1; + break; +case 2: ifn2(fn) = address; + if (nargs<=0xff) + ifn1(fn) = (int32)too_few_2, ifnn(fn) = (int32)wrong_no_2; + break; +case 3: ifnn(fn) = address; + if (nargs<=0xff) + ifn1(fn) = (int32)wrong_no_3a, ifn2(fn) = (int32)wrong_no_3b; + break; +default: ifnn(fn) = address; + if (nargs<=0xff) + ifn1(fn) = (int32)wrong_no_na, ifn2(fn) = (int32)wrong_no_nb; + break; + } + qenv(fn) = env; + return onevalue(fn); +} + +static CSLbool restore_fn_cell(Lisp_Object a, char *name, + int32 len, setup_type const s[]) +{ + int i; + for (i=0; s[i].name != NULL; i++) + { if (strlen(s[i].name) == len && + memcmp(name, s[i].name, len) == 0) break; + } + if (s[i].name == NULL) return NO; + set_fns(a, s[i].one, s[i].two, s[i].n); + return YES; +} + +static Lisp_Object Lrestore_c_code(Lisp_Object nil, Lisp_Object a) +{ + char *name; + int32 len; + Lisp_Object pn; + if (!symbolp(a)) return aerror1("restore-c-code", a); + push(a); + pn = get_pname(a); + pop(a); + errexit(); + name = (char *)&celt(pn, 0); + len = length_of_header(vechdr(pn)) - 4; + if (restore_fn_cell(a, name, len, u01_setup) || + restore_fn_cell(a, name, len, u02_setup) || + restore_fn_cell(a, name, len, u03_setup) || + restore_fn_cell(a, name, len, u04_setup) || + restore_fn_cell(a, name, len, u05_setup) || + restore_fn_cell(a, name, len, u06_setup) || + restore_fn_cell(a, name, len, u07_setup) || + restore_fn_cell(a, name, len, u08_setup) || + restore_fn_cell(a, name, len, u09_setup) || + restore_fn_cell(a, name, len, u10_setup) || + restore_fn_cell(a, name, len, u11_setup) || + restore_fn_cell(a, name, len, u12_setup)) + { Lisp_Object env; + push(a); +#ifdef COMMON + env = get(a, funarg, nil); +#else + env = get(a, funarg); +#endif + pop(a); + errexit(); + qenv(a) = env; + return onevalue(a); + } + else return onevalue(nil); +} + +Lisp_Object Lsymbol_set_definition(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +/* + * The odd case here is where the second argument represents a freshly + * created bit of compiled code. In which case the structure is + * (nargs . codevec . envvec) + * where nargs is an integer indicating the number of arguments, codevec + * is a vector of bytecodes, and envvec is something to go in the + * environment cell of the symbol. + * Here the low 8 bits of nargs indicate the number of required arguments. + * The next 8 bits give the number of optional arguments, and the next + * two bits are flags. Of these, the first is set if any of the optional + * arguments has an initform or supplied-p associate, and the other + * indicates that a "&rest" argument is required. + * Bits beyond that (if non-zero) indicate that the function definition + * is of the form (defun f1 (a b c) (f2 a b)) and the number coded is the + * length of the function body. + * Standard Lisp does not need &optional or &rest arguments, but it turned + * out to be pretty easy to make the bytecode compiler support them. + */ +{ + if (!is_symbol(a) || +/* + * Something flagged with the CODEPTR bit is a gensym manufactured to + * stand for a compiled-code object. It should NOT be reset! + */ + (qheader(a) & (SYM_SPECIAL_FORM | SYM_CODEPTR)) != 0) + { if (qheader(a) & SYM_C_DEF) return onevalue(nil); + return aerror1("symbol-set-definition", a); + } + qheader(a) &= ~SYM_TRACED; + set_fns(a, undefined1, undefined2, undefinedn); /* Tidy up first */ + qenv(a) = a; + if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); + if (b == nil) return onevalue(b); /* set defn to nil to undefine */ + else if (symbolp(b)) + { +/* + * One could imagine a view that the second arg to symbol-set-definition + * had to be a codepointer object. I will be kind (?) and permit the NAME + * of a function too. However for the second arg to be a macro or a + * special form would still be a calamity. + * if ((qheader(b) & SYM_CODEPTR) == 0) + * return aerror1("symbol-set-definition", b); + */ + if ((qheader(b) & (SYM_SPECIAL_FORM | SYM_MACRO)) != 0) + return aerror1("symbol-set-definition", b); + qheader(a) = qheader(a) & ~SYM_MACRO; + { set_fns(a, qfn1(b), qfn2(b), qfnn(b)); + qenv(a) = qenv(b); +/* + * In order that checkpoint files can be made there is some very + * ugly fooling around here for functions that are defined in the C coded + * kernel. Sorry. + */ + if ((qheader(b) & SYM_C_DEF) != 0) + { +#ifdef COMMON + Lisp_Object c = get(b, unset_var, nil); +#else + Lisp_Object c = get(b, unset_var); +#endif + if (c == nil) c = b; + push2(c, a); + putprop(a, unset_var, c); + errexitn(2); + pop(a); +#ifdef COMMON + a = cons(a, get(stack[0], work_symbol, nil)); +#else + a = cons(a, get(stack[0], work_symbol)); +#endif + errexitn(1); + putprop(stack[0], work_symbol, a); + pop(b); + errexit(); + } + } + } + else if (!consp(b)) return aerror1("symbol-set-definition", b); + else if (is_fixnum(qcar(b))) + { int32 nargs = (int)int_of_fixnum(qcar(b)), nopts, flagbits, ntail; + nopts = nargs >> 8; + flagbits = nopts >> 8; + ntail = flagbits >> 2; + nargs &= 0xff; + nopts &= 0xff; + flagbits &= 3; + if (ntail != 0) + { switch (100*nargs + ntail-1) + { + case 300: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_0); break; + case 301: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_1); break; + case 302: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_2); break; + case 303: set_fns(a, wrong_no_na, wrong_no_nb, f3_as_3); break; + case 200: set_fns(a, too_few_2, f2_as_0, wrong_no_2); break; + case 201: set_fns(a, too_few_2, f2_as_1, wrong_no_2); break; + case 202: set_fns(a, too_few_2, f2_as_2, wrong_no_2); break; + case 100: set_fns(a, f1_as_0, too_many_1, wrong_no_1); break; + case 101: set_fns(a, f1_as_1, too_many_1, wrong_no_1); break; + case 000: set_fns(a, wrong_no_na, wrong_no_nb, f0_as_0); break; + } + b = qcdr(b); + } + else if (flagbits != 0 || nopts != 0) + { if ((qheader(a) & SYM_TRACED) == 0) switch(flagbits) + { + default: + case 0: /* easy case optional arguments */ + set_fns(a, byteopt1, byteopt2, byteoptn); break; + case 1: /* optional args, but non-nil default, or supplied-p extra */ + set_fns(a, hardopt1, hardopt2, hardoptn); break; + case 2: /* easy opt args, but also a &rest arg */ + set_fns(a, byteoptrest1, byteoptrest2, byteoptrestn); break; + case 3: /* complicated &options and &rest */ + set_fns(a, hardoptrest1, hardoptrest2, hardoptrestn); break; + } + else switch (flagbits) + { + default: + case 0: /* easy case optional arguments */ + set_fns(a, tracebyteopt1, tracebyteopt2, tracebyteoptn); break; + case 1: /* optional args, but non-nil default, or supplied-p extra */ + set_fns(a, tracehardopt1, tracehardopt2, tracehardoptn); break; + case 2: /* easy opt args, but also a &rest arg */ + set_fns(a, tracebyteoptrest1, tracebyteoptrest2, tracebyteoptrestn); break; + case 3: /* complicated &options and &rest */ + set_fns(a, tracehardoptrest1, tracehardoptrest2, tracehardoptrestn); break; + } + } + else + { if (nargs > 4) nargs = 4; + if ((qheader(a) & SYM_TRACED) != 0) nargs += 5; + qheader(a) = qheader(a) & ~SYM_MACRO; + switch (nargs) + { + case 0: set_fns(a, wrong_no_0a, wrong_no_0b, bytecoded0); + break; + case 1: set_fns(a, bytecoded1, too_many_1, wrong_no_1); + break; + case 2: set_fns(a, too_few_2, bytecoded2, wrong_no_2); + break; + case 3: set_fns(a, wrong_no_3a, wrong_no_3b, bytecoded3); + break; + default: + case 4: set_fns(a, wrong_no_na, wrong_no_nb, bytecodedn); + break; + + case 5+0: set_fns(a, wrong_no_0a, wrong_no_0b, tracebytecoded0); + break; + case 5+1: set_fns(a, tracebytecoded1, too_many_1, wrong_no_1); + break; + case 5+2: set_fns(a, too_few_2, tracebytecoded2, wrong_no_2); + break; + case 5+3: set_fns(a, wrong_no_3a, wrong_no_3b, tracebytecoded3); + break; + case 5+4: set_fns(a, wrong_no_na, wrong_no_nb, tracebytecodedn); + break; + } + } + qenv(a) = qcdr(b); + } + else if (qcar(b) == lambda) + { Lisp_Object bvl = qcar(qcdr(b)); + int nargs = 0; + while (consp(bvl)) nargs++, bvl = qcdr(bvl); + qheader(a) = qheader(a) & ~SYM_MACRO; + if ((qheader(a) & SYM_TRACED) != 0) + set_fns(a, traceinterpreted1, traceinterpreted2, traceinterpretedn); + else set_fns(a, interpreted1, interpreted2, interpretedn); + qenv(a) = qcdr(b); + if (qvalue(comp_symbol) != nil && + qfn1(compiler_symbol) != undefined1) + { push(a); + a = ncons(a); + errexitn(1); + (qfn1(compiler_symbol))(qenv(compiler_symbol), a); + pop(a); + errexit(); + } + } + else if (qcar(b) == funarg) + { Lisp_Object bvl = qcar(qcdr(b)); + int nargs = 0; + while (consp(bvl)) nargs++, bvl = qcdr(bvl); + qheader(a) = qheader(a) & ~SYM_MACRO; + if ((qheader(a) & SYM_TRACED) != 0) + set_fns(a, tracefunarged1, tracefunarged2, tracefunargedn); + else set_fns(a, funarged1, funarged2, funargedn); + qenv(a) = qcdr(b); + } + else return aerror1("symbol-set-definition", b); + return onevalue(b); +} + +Lisp_Object Lgetd(Lisp_Object nil, Lisp_Object a) +{ + Header h; + Lisp_Object type; + CSL_IGNORE(nil); + if (a == nil) return onevalue(nil); + else if (!is_symbol(a)) return onevalue(nil); + h = qheader(a); + if ((h & SYM_SPECIAL_FORM) != 0) type = fexpr_symbol; + else if ((h & SYM_MACRO) != 0) + { a = cons(lambda, qenv(a)); + errexit(); + type = macro_symbol; + } + else + { a = Lsymbol_function(nil, a); + errexit(); + if (a == nil) return onevalue(nil); + type = expr_symbol; + } + a = cons(type, a); + errexit(); + return onevalue(a); +} + +Lisp_Object Lremd(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object res; + CSL_IGNORE(nil); + if (!is_symbol(a) || + (qheader(a) & SYM_SPECIAL_FORM) != 0) + return aerror1("remd", a); + if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == + (SYM_C_DEF | SYM_CODEPTR)) return onevalue(nil); + res = Lgetd(nil, a); + errexit(); + if (res == nil) return onevalue(nil); /* no definition to remove */ +/* + * I treat an explicit use of remd as a redefinition, and ensure that + * restarting a preserved image will not put the definition back. + */ + qheader(a) = qheader(a) & ~SYM_MACRO; + if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); + set_fns(a, undefined1, undefined2, undefinedn); + qenv(a) = a; + return onevalue(res); +} + +/* + * For set-autoload the first argument must be a symbol that will name + * a function, the second arg is either an atom or a list of atoms, each + * of which specified a module to be loaded if the names function is + * called. Loading the modules is expected to instate a definition for the + * function involved. This function is arranged so it does NOT do anything + * if the function being set for autoloading is already defined. This is + * on the supposition that the existing definition is in fact the desired + * one, say because the relevant module happens to have been loaded already. + * An explicit use of remd first can be used to ensure that no previous + * definition is present and thus that a real autoload stub will be instated, + * if that is what you really want. + */ + +Lisp_Object Lset_autoload(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + Lisp_Object res; + CSL_IGNORE(nil); + if (!is_symbol(a) || + (qheader(a) & SYM_SPECIAL_FORM) != 0) + return aerror1("set-autoload", a); + if (!(qfn1(a) == undefined1 && qfn2(a) == undefined2 && + qfnn(a) == undefinedn)) return onevalue(nil); + if ((qheader(a) & (SYM_C_DEF | SYM_CODEPTR)) == + (SYM_C_DEF | SYM_CODEPTR)) return onevalue(nil); + push2(a, b); + if (consp(b)) res = cons(a, b); + else res = list2(a, b); + pop2(b, a); + errexit(); +/* + * I treat an explicit use of set-autoload as a redefinition, and ensure that + * restarting a preserved image will not put the definition back. Note that + * I will not allow autoloadable macros... + */ + qheader(a) = qheader(a) & ~SYM_MACRO; + if ((qheader(a) & SYM_C_DEF) != 0) lose_C_def(a); + set_fns(a, autoload1, autoload2, autoloadn); + qenv(a) = res; + return onevalue(res); +} + +#define pack_funtable(a, n) ((((int32)(a)) << 16) | (n)) +#define funtable_nargs(u) ((u) >> 16) +#define funtable_index(u) ((u) & 0xffffU) + +static one_args *displaced1 = NULL; +static two_args *displaced2; +static n_args *displacedn; +static unsigned32 table_entry; + +static void trace_entering(char *s) +{ + int i; + for (i=0; i 15 args: not supported"); + } + popv(nargs); + pop(name); + errexit(); + push(r); + freshline_trace(); + loop_print_trace(name); + trace_printf(" = "); + loop_print_trace(r); + trace_exiting("\n"); + pop(r); + return onevalue(r); +} + +#define NOT_FOUND 100 + +static unsigned32 find_built_in_function(one_args *f1, + two_args *f2, + n_args *fn) +/* + * This take the entrypoint of a function and tries to identify it + * by scanning the tables used by the bytecode interpreter. If the + * function is found a record is returned indicating how many args + * it takes, and what its index is in the relevant table. The code + * is returned to indicate failure if the function + * is not found. + */ +{ + int32 index; + for (index=0; zero_arg_functions[index]!=NULL; index++) + if (fn == zero_arg_functions[index]) return pack_funtable(0, index); + for (index=0; one_arg_functions[index]!=NULL; index++) + if (f1 == one_arg_functions[index]) return pack_funtable(1, index); + for (index=0; two_arg_functions[index]!=NULL; index++) + if (f2 == two_arg_functions[index]) return pack_funtable(2, index); + for (index=0; three_arg_functions[index]!=NULL; index++) + if (fn == three_arg_functions[index]) return pack_funtable(3, index); + return pack_funtable(NOT_FOUND, NOT_FOUND); +} + +Lisp_Object Ltrace_all(Lisp_Object nil, Lisp_Object a) +{ +#ifdef DEBUG + if (a == nil) trace_all = 0; + else trace_all = 1; + return onevalue(nil); +#else + return aerror("trace-all only supported in DEBUG version"); +#endif +} + +Lisp_Object Ltrace(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object w = a; + if (symbolp(a)) + { a = ncons(a); + errexit(); + w = a; + } + while (consp(w)) + { Lisp_Object s = qcar(w); + w = qcdr(w); + if (symbolp(s)) + { one_args *f1 = qfn1(s); + two_args *f2 = qfn2(s); + n_args *fn = qfnn(s); + int fixenv = 0, done = 0; + if (f1 == undefined1) + { freshline_debug(); + debug_printf("+++ "); + loop_print_debug(s); + debug_printf(" not yet defined\n"); + continue; + } + qheader(s) |= SYM_TRACED; + if (f1 == interpreted1) + { set_fns(s, traceinterpreted1, traceinterpreted2, traceinterpretedn); + fixenv = done = 1; + } + if (f1 == funarged1) + { set_fns(s, tracefunarged1, tracefunarged2, tracefunargedn); + fixenv = done = 1; + } + if (fn == bytecoded0) ifnn(s) = (int32)tracebytecoded0, done = 1; + if (f1 == bytecoded1) ifn1(s) = (int32)tracebytecoded1, done = 1; + if (f2 == bytecoded2) ifn2(s) = (int32)tracebytecoded2, done = 1; + if (fn == bytecoded3) ifnn(s) = (int32)tracebytecoded3, done = 1; + if (fn == bytecodedn) ifnn(s) = (int32)tracebytecodedn, done = 1; + if (f1 == byteopt1) ifn1(s) = (int32)tracebyteopt1, done = 1; + if (f2 == byteopt2) ifn2(s) = (int32)tracebyteopt2, done = 1; + if (fn == byteoptn) ifnn(s) = (int32)tracebyteoptn, done = 1; + if (f1 == hardopt1) ifn1(s) = (int32)tracehardopt1, done = 1; + if (f2 == hardopt2) ifn2(s) = (int32)tracehardopt2, done = 1; + if (fn == hardoptn) ifnn(s) = (int32)tracehardoptn, done = 1; + if (f1 == byteoptrest1) ifn1(s) = (int32)tracebyteoptrest1, done = 1; + if (f2 == byteoptrest2) ifn2(s) = (int32)tracebyteoptrest2, done = 1; + if (fn == byteoptrestn) ifnn(s) = (int32)tracebyteoptrestn, done = 1; + if (f1 == hardoptrest1) ifn1(s) = (int32)tracehardoptrest1, done = 1; + if (f2 == hardoptrest2) ifn2(s) = (int32)tracehardoptrest2, done = 1; + if (fn == hardoptrestn) ifnn(s) = (int32)tracehardoptrestn, done = 1; + if (fixenv) + { push2(a, s); + a = cons(s, qenv(s)); + errexitn(2); + pop(s); + qenv(s) = a; + pop(a); + } + if (done) continue; +/* + * I permit the tracing of just one function from the kernel, and achieve + * this by installing a wrapper function in place of the real definition. + * Indeed this is just like Lisp-level embedding, except that I can get at the + * entrypoint table used by the bytecode interpreter and so trap calls made + * via there, and I can use that table to tell me how many arguments the + * traced function needed. + */ + if (displaced1 == NULL) + { int nargs = funtable_nargs(table_entry); +/* + * Remember what function was being traced, so that it can eventually be + * invoked, and its name printed. + */ + displaced1 = f1; + displaced2 = f2; + displacedn = fn; + tracedfn = s; +/* + * This makes calls via the regular interpreter see the traced version... + */ + set_fns(s, traced1_function, traced2_function, + tracedn_function); + table_entry = find_built_in_function(f1, f2, fn); + nargs = funtable_nargs(table_entry); + table_entry = funtable_index(table_entry); + if (nargs != NOT_FOUND) + { +/* + * .. and now I make calls via short-form bytecodes do likewise. + */ + switch (nargs) + { + default: + case 0: zero_arg_functions[funtable_index(table_entry)] = + tracedn_function; + break; + case 1: one_arg_functions[funtable_index(table_entry)] = + traced1_function; + break; + case 2: two_arg_functions[funtable_index(table_entry)] = + traced2_function; + break; + case 3: three_arg_functions[funtable_index(table_entry)] = + tracedn_function; + break; + } + } + } + continue; + } + } + return onevalue(a); +} + +Lisp_Object Luntrace(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object w = a; + CSL_IGNORE(nil); + if (symbolp(a)) + { a = ncons(a); + errexit(); + w = a; + } + while (consp(w)) + { Lisp_Object s = qcar(w); + w = qcdr(w); + if (symbolp(s)) + { one_args *f1 = qfn1(s); + two_args *f2 = qfn2(s); + n_args *fn = qfnn(s); + if (f1 == traceinterpreted1) + { set_fns(a, interpreted1, interpreted2, interpretedn); + qenv(s) = qcdr(qenv(s)); + } + else if (f1 == tracefunarged1) + { set_fns(s, funarged1, funarged2, funargedn); + qenv(s) = qcdr(qenv(s)); + } + if (f1 == tracebytecoded1) ifn1(s) = (int32)bytecoded1; + if (f2 == tracebytecoded2) ifn2(s) = (int32)bytecoded2; + if (fn == tracebytecoded0) ifnn(s) = (int32)bytecoded0; + if (fn == tracebytecoded3) ifnn(s) = (int32)bytecoded3; + if (fn == tracebytecodedn) ifnn(s) = (int32)bytecodedn; + if (f1 == tracebyteopt1) ifn1(s) = (int32)byteopt1; + if (f2 == tracebyteopt2) ifn2(s) = (int32)byteopt2; + if (fn == tracebyteoptn) ifnn(s) = (int32)byteoptn; + if (f1 == tracebyteoptrest1) ifn1(s) = (int32)byteoptrest1; + if (f2 == tracebyteoptrest2) ifn2(s) = (int32)byteoptrest2; + if (fn == tracebyteoptrestn) ifnn(s) = (int32)byteoptrestn; + if (f1 == tracehardopt1) ifn1(s) = (int32)hardopt1; + if (f2 == tracehardopt2) ifn2(s) = (int32)hardopt2; + if (fn == tracehardoptn) ifnn(s) = (int32)hardoptn; + if (f1 == tracehardoptrest1) ifn1(s) = (int32)hardoptrest1; + if (f2 == tracehardoptrest2) ifn2(s) = (int32)hardoptrest2; + if (fn == tracehardoptrestn) ifnn(s) = (int32)hardoptrestn; + if (f1 == traced1_function) + { int nargs = funtable_nargs(table_entry); + set_fns(s, displaced1, displaced2, displacedn); + if (nargs != NOT_FOUND) + switch (nargs) + { + default: + case 0: zero_arg_functions[funtable_index(table_entry)] = + displacedn; + break; + case 1: one_arg_functions[funtable_index(table_entry)] = + displaced1; + break; + case 2: two_arg_functions[funtable_index(table_entry)] = + displaced2; + break; + case 3: three_arg_functions[funtable_index(table_entry)] = + displacedn; + break; + } + displaced1 = NULL; + displaced2 = NULL; + displacedn = NULL; + } + qheader(s) &= ~SYM_TRACED; + } + } + return onevalue(a); +} + +Lisp_Object Ldouble(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object w = a; + if (symbolp(a)) + { a = ncons(a); + errexit(); + w = a; + } + while (consp(w)) + { Lisp_Object s = qcar(w); + w = qcdr(w); + if (symbolp(s)) + { one_args *f1 = qfn1(s); + two_args *f2 = qfn2(s); + n_args *fn = qfnn(s); + int fixenv = 0, done = 0; + if (f1 == undefined1) continue; + if (f1 == interpreted1) + { set_fns(s, double_interpreted1, double_interpreted2, double_interpretedn); + fixenv = done = 1; + } + if (f1 == funarged1) + { set_fns(s, double_funarged1, double_funarged2, double_funargedn); + fixenv = done = 1; + } + if (fn == bytecoded0) ifnn(s) = (int32)double_bytecoded0, done = 1; + if (f1 == bytecoded1) ifn1(s) = (int32)double_bytecoded1, done = 1; + if (f2 == bytecoded2) ifn2(s) = (int32)double_bytecoded2, done = 1; + if (fn == bytecoded3) ifnn(s) = (int32)double_bytecoded3, done = 1; + if (fn == bytecodedn) ifnn(s) = (int32)double_bytecodedn, done = 1; + if (f1 == byteopt1) ifn1(s) = (int32)double_byteopt1, done = 1; + if (f2 == byteopt2) ifn2(s) = (int32)double_byteopt2, done = 1; + if (fn == byteoptn) ifnn(s) = (int32)double_byteoptn, done = 1; + if (f1 == hardopt1) ifn1(s) = (int32)double_hardopt1, done = 1; + if (f2 == hardopt2) ifn2(s) = (int32)double_hardopt2, done = 1; + if (fn == hardoptn) ifnn(s) = (int32)double_hardoptn, done = 1; + if (f1 == byteoptrest1) ifn1(s) = (int32)double_byteoptrest1, done = 1; + if (f2 == byteoptrest2) ifn2(s) = (int32)double_byteoptrest2, done = 1; + if (fn == byteoptrestn) ifnn(s) = (int32)double_byteoptrestn, done = 1; + if (f1 == hardoptrest1) ifn1(s) = (int32)double_hardoptrest1, done = 1; + if (f2 == hardoptrest2) ifn2(s) = (int32)double_hardoptrest2, done = 1; + if (fn == hardoptrestn) ifnn(s) = (int32)double_hardoptrestn, done = 1; + if (fixenv) + { push2(a, s); + a = cons(s, qenv(s)); + errexitn(2); + pop(s); + qenv(s) = a; + pop(a); + } + if (done) continue; + debug_printf("Unable to execution-double: "); loop_print_debug(s); + trace_printf("\n"); + continue; + } + } + return onevalue(a); +} + +Lisp_Object Lundouble(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object w = a; + CSL_IGNORE(nil); + if (symbolp(a)) + { a = ncons(a); + errexit(); + w = a; + } + while (consp(w)) + { Lisp_Object s = qcar(w); + w = qcdr(w); + if (symbolp(s)) + { one_args *f1 = qfn1(s); + two_args *f2 = qfn2(s); + n_args *fn = qfnn(s); + if (f1 == double_interpreted1) + { set_fns(a, interpreted1, interpreted2, interpretedn); + qenv(s) = qcdr(qenv(s)); + } + else if (f1 == double_funarged1) + { set_fns(s, funarged1, funarged2, funargedn); + qenv(s) = qcdr(qenv(s)); + } + else if (f1 == double_bytecoded1) ifn1(s) = (int32)bytecoded1; + else if (f2 == double_bytecoded2) ifn2(s) = (int32)bytecoded2; + else if (fn == double_bytecoded0) ifnn(s) = (int32)bytecoded0; + else if (fn == double_bytecoded3) ifnn(s) = (int32)bytecoded3; + else if (fn == double_bytecodedn) ifnn(s) = (int32)bytecodedn; + else if (f1 == double_byteopt1) ifn1(s) = (int32)byteopt1; + else if (f2 == double_byteopt2) ifn2(s) = (int32)byteopt2; + else if (fn == double_byteoptn) ifnn(s) = (int32)byteoptn; + else if (f1 == double_byteoptrest1) ifn1(s) = (int32)byteoptrest1; + else if (f2 == double_byteoptrest2) ifn2(s) = (int32)byteoptrest2; + else if (fn == double_byteoptrestn) ifnn(s) = (int32)byteoptrestn; + else if (f1 == double_hardopt1) ifn1(s) = (int32)hardopt1; + else if (f2 == double_hardopt2) ifn2(s) = (int32)hardopt2; + else if (fn == double_hardoptn) ifnn(s) = (int32)hardoptn; + else if (f1 == double_hardoptrest1) ifn1(s) = (int32)hardoptrest1; + else if (f2 == double_hardoptrest2) ifn2(s) = (int32)hardoptrest2; + else if (fn == double_hardoptrestn) ifnn(s) = (int32)hardoptrestn; + } + } + return onevalue(a); +} + +Lisp_Object Lmacro_function(Lisp_Object nil, Lisp_Object a) +{ + if (!symbolp(a)) return onevalue(nil); + else if ((qheader(a) & SYM_MACRO) == 0) return onevalue(nil); +/* If the MACRO bit is set in the header I know there is a definition */ + else return onevalue(cons(lambda, qenv(a))); +} + + +Lisp_Object get_pname(Lisp_Object a) +{ + Lisp_Object name = qpname(a); +#ifndef COMMON +/* + * When a gensym is first created its pname field points at a string that + * will form the base of its name, and a magic bit is set in its header. + * If at some stage it is necessary to inspect the print name (mainly in + * order to print the symbol) it becomes necessary to create a new string + * and insert a serial number. Doing things this way means that the serial + * numbers that users see will tend to be smaller, and space for per-gensym + * strings does not get allocated unless really needed. The down side is + * that every time I want to grab the pname of anything I have to check for + * this case and admit the possibility of garbage collection or even + * failure. + */ + if (qheader(a) & SYM_UNPRINTED_GENSYM) + { unsigned32 len; + Lisp_Object nil = C_nil; + char genname[64]; + len = length_of_header(vechdr(name)) - 4; + if (len > 60) len = 60; /* Unpublished truncation of the string */ + sprintf(genname, "%.*s%lu", (int)len, + (char *)name + (4 - TAG_VECTOR), (long)gensym_ser++); + push(a); + name = make_string(genname); + pop(a); + errexit(); + qpname(a) = name; + qheader(a) &= ~SYM_UNPRINTED_GENSYM; + } +#endif + return name; +} + +Lisp_Object Lsymbol_name(Lisp_Object nil, Lisp_Object a) +{ + if (!symbolp(a)) return aerror1("symbol-name", a); + a = get_pname(a); + errexit(); + return onevalue(a); +} + +#ifdef COMMON + +Lisp_Object Lsymbol_package(Lisp_Object nil, Lisp_Object a) +{ + if (!symbolp(a)) return aerror1("symbol-package", a); + a = qpackage(a); + return onevalue(a); +} + +#endif + +static Lisp_Object Lrestart_csl2(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +/* + * If the argument is given as nil then this is a cold-start, and when + * I begin again it would be a VERY good idea to do a (load!-module 'compat) + * rather promptly (otherwise some Lisp functions will not work at all). + * I do not automate that because this function is intended for use in + * delicate system rebuilding contexts and I want the user to have ultimate + * control. (restart!-csl t) reloads a heap-image in the normal way. + * (restart!-csl 'xx) where xx is neither nil nor t starts by reloading a + * heap image, but then it looks for a function with the same name as xx + * (since a heap image is reloaded it is NOT easy (possible?) to keep the + * symbol) and calls it as a function. Finally the case + * (restart!-csl '(module fn)) restart the system, then calls load-module + * on the named module and finally calls the given restart function. + * This last option can be useful since otherwise the function to be called + * in (restart!-csl 'xx) would need to be in the base image as re-loaded. + */ +{ + int n; + char *v; +#ifdef SOCKETS +/* + * Security measure - deny restart-csl to remote users + */ + if (socket_server != 0) return aerror("restart-csl"); +#endif + n = 0; + v = NULL; +/* + * A comment seems in order here. The case b==SPID_NOARG should only + * arise if I came from Lrestart_csl: it indicates that there was + * no second argument provided. + */ + if (b != SPID_NOARG) + { Lisp_Object b1 = b = Lexploden(nil, b); + errexit(); + while (b1 != nil) + { n++; /* number of chars of arg */ + b1 = qcdr(b1); + } + v = (char *)malloc(n+1); + if (v == NULL) return aerror("space exhausted in restart-csl"); + n = 0; + while (b != nil) + { v[n++] = int_of_fixnum(qcar(b)); + b = qcdr(b); + } + v[n] = 0; + } + term_printf("\nThe system is about to do a restart...\n"); +/* Almost all unpicking of the argument is done back in csl.c */ + exit_value = a; + exit_tag = fixnum_of_int(2); /* Flag to say "restart" */ + exit_reason = UNWIND_RESTART; + exit_charvec = v; + flip_exception(); + return nil; +} + +static Lisp_Object Lrestart_csl(Lisp_Object nil, Lisp_Object a) +{ + return Lrestart_csl2(nil, a, SPID_NOARG); +} + +static Lisp_Object Lpreserve(Lisp_Object nil, + Lisp_Object startup, Lisp_Object banner) +/* + * (preserve ) saves a Lisp image in a standard place + * and arranges that when restarted the saved image will call the specified + * startup function. In the process of doing all this it unwinds down to + * the top level of Lisp. If a startup function is not given then the + * previously active one is used. If nil is specified then the previously + * active startup function is retained. If banner is non-nil (well really + * I want a string) is is a message of up to 40 characters to display + * when the system restart. + */ +{ + char filename[LONGEST_LEGAL_FILENAME]; + CSLbool failed; +#ifdef SOCKETS +/* + * Security measure - deny preserve to remote users + */ + if (socket_server != 0) return aerror("preserve"); +#endif + if (startup != nil) supervisor = startup; + failed = Iwriterootp(filename); /* Can I open image file for writing? */ + term_printf("\nThe system will be preserved on file \"%s\"\n", filename); + if (failed) return aerror("preserve"); + exit_count = 0; + nil = C_nil; + exit_value = banner; + exit_tag = fixnum_of_int(1); /* Flag to say "preserve" */ + exit_reason = UNWIND_RESTART; + flip_exception(); + return nil; +} + +static Lisp_Object MS_CDECL Lpreserve_0(Lisp_Object nil, int nargs, ...) +{ + argcheck(nargs, 0, "preserve"); + return Lpreserve(nil, nil, nil); +} + +static Lisp_Object Lpreserve_1(Lisp_Object nil, Lisp_Object startup) +{ + return Lpreserve(nil, startup, nil); +} + + +/* + * This is an experimental addition - a version of PRESERVE that allows + * CSL to continue executing after it has written out an image file. + */ + +static Lisp_Object Lcheckpoint(Lisp_Object nil, + Lisp_Object startup, Lisp_Object banner) +{ + char filename[LONGEST_LEGAL_FILENAME]; + CSLbool failed = 0; + char *msg = ""; +#ifdef SOCKETS +/* + * Security measure - deny checkpoint to remote users + */ + if (socket_server != 0) return aerror("checkpoint"); +#endif + if (startup != nil) supervisor = startup; + failed = Iwriterootp(filename); /* Can I open image file for writing? */ + term_printf("\nThe system will be preserved on file \"%s\"\n", filename); + if (failed) return aerror("checkpoint"); + if (is_vector(banner) && + type_of_header(vechdr(banner)) == TYPE_STRING) + msg = &celt(banner, 0); +/* + * Note, with some degree of nervousness, that things on the C stack will + * be updated by the garbage collection that happens during the processing + * of the call to preserve(), but they will be neither adjusted into + * relative addresses nor unadjusted (and hence restored) by in the + * image-writing. But the image writing will not actually move any data + * around so all is still OK, I hope! + */ + push5(codevec, litvec, catch_tags, faslvec, faslgensyms); + preserve(msg); + nil = C_nil; + if (exception_pending()) failed = 1, flip_exception(); + adjust_all(); + pop5(faslgensyms, faslvec, catch_tags, litvec, codevec); + eq_hash_tables = eq_hash_table_list; + equal_hash_tables = equal_hash_table_list; + eq_hash_table_list = equal_hash_table_list = nil; + { Lisp_Object qq; + for (qq = eq_hash_tables; qq!=nil; qq=qcdr(qq)) + rehash_this_table(qcar(qq)); + for (qq = equal_hash_tables; qq!=nil; qq=qcdr(qq)) + rehash_this_table(qcar(qq)); + } + set_up_functions(YES); + if (failed) return aerror("checkpoint"); + return onevalue(nil); +} + +static Lisp_Object MS_CDECL Lcheckpoint_0(Lisp_Object nil, int nargs, ...) +{ + argcheck(nargs, 0, "checkpoint"); + return Lcheckpoint(nil, nil, nil); +} + +static Lisp_Object Lcheckpoint_1(Lisp_Object nil, Lisp_Object startup) +{ + return Lcheckpoint(nil, startup, nil); +} + + +#ifdef COMMON +static CSLbool eql_numbers(Lisp_Object a, Lisp_Object b) +/* + * This is only called from eql, and then only when a and b are both tagged + * as ratios or complex numbers. + */ +{ + Lisp_Object p, q; + p = *(Lisp_Object *)(a + (4 - TAG_NUMBERS)); + q = *(Lisp_Object *)(b + (4 - TAG_NUMBERS)); + if (!eql(p, q)) return NO; + p = *(Lisp_Object *)(a + (8 - TAG_NUMBERS)); + q = *(Lisp_Object *)(b + (8 - TAG_NUMBERS)); + return eql(p, q); +} +#endif + +CSLbool eql_fn(Lisp_Object a, Lisp_Object b) +/* + * This seems incredible - all the messing about that is needed to + * check that numeric values compare properly. Ugh. + */ +{ +/* + * (these tests done before eql_fn is called). + * if (a == b) return YES; + * if ((((int32)a ^ (int32)b) & TAG_BITS) != 0) return NO; + * + * Actually in Common Lisp mode where I have short floats as immediate data + * I have further pain here with (eql 0.0 -0.0). + */ +#ifdef COMMON + if ((a == TAG_SFLOAT && b == (TAG_SFLOAT|0x80000000)) || + (a == (TAG_SFLOAT|0x80000000) && b == TAG_SFLOAT) return YES; +#endif + if (!is_number(a) || is_immed_or_cons(a)) return NO; + if (is_bfloat(a)) + { Header h = flthdr(a); + if (h != flthdr(b)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != + *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; + else return YES; +#else + return (single_float_val(a) == single_float_val(b)); +#endif + } + else +#endif +/* + * For the moment I view all non-single floats as double floats. Extra + * stuff will be needed here if I ever implement long floats as 3-word + * objects. + */ + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) return NO; + else return YES; +#else + return (double_float_val(a) == double_float_val(b)); +#endif + } + } + else /* ratio, complex or bignum */ + { Header h = numhdr(a); + if (h != numhdr(b)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)a + hh) != + *(Lisp_Object *)((char *)b + hh)) + return NO; + } + return YES; + } +#ifdef COMMON + else return eql_numbers(a, b); +#else + else return NO; +#endif + } +} + +static CSLbool cl_vec_equal(Lisp_Object a, Lisp_Object b) +/* + * here a and b are known to be vectors or arrays. This should compare + * them following the Common Lisp recipe, where strings or bitvectors + * (simple or complex) have their contents compared, while all other types of + * vector or array are tested using EQ. + */ +{ + Header ha = vechdr(a), hb = vechdr(b); + int32 offa = 0, offb = 0; + int ta = type_of_header(ha), tb = type_of_header(hb); + int32 la = length_of_header(ha), lb = length_of_header(hb); +#ifdef COMMON + if (header_of_bitvector(ha)) ta = TYPE_BITVEC1; + if (header_of_bitvector(hb)) tb = TYPE_BITVEC1; +#endif + switch (ta) + { +/* +case TYPE_ARRAY: +/* My moan here is that, as noted above, I ought to process even + * non-simple strings and bit-vectors by comparing contents, but as a + * matter of idleness I have not yet got around to that. In fact if I get + * arrays to compare here I will pretend that they are not strings or + * bit-vectors and compare using EQ... + */ +case TYPE_STRING: + switch (tb) + { +/* /* + case TYPE_ARRAY: +*/ + case TYPE_STRING: + goto compare_strings; + default:return NO; + } +#ifdef COMMON +case TYPE_BITVEC1: + switch (tb) + { +/* /* + case TYPE_ARRAY: +*/ + case TYPE_BITVEC1: + goto compare_bits; + default:return NO; + } +#endif +default: return (a == b); + } +compare_strings: + if (la != lb) return NO; + while (la > 0) + { la--; + if (*((char *)a + la + offa - TAG_VECTOR) != + *((char *)b + la + offb - TAG_VECTOR)) return NO; + } + return YES; +#ifdef COMMON +compare_bits: + if (la != lb) return NO; + while (la > 0) + { la--; + if (*((char *)a + la + offa - TAG_VECTOR) != + *((char *)b + la + offb - TAG_VECTOR)) return NO; + } + return YES; +#endif +} + +CSLbool cl_equal_fn(Lisp_Object a, Lisp_Object b) +/* + * a and b are not EQ at this stage.. I guarantee to have checked that + * before entering this general purpose code. + */ +{ + Lisp_Object nil = C_nil; + CSL_IGNORE(nil); +/* + * The for loop at the top here is so that cl_equal can iterate along the + * length of linear lists. + */ +#ifdef CHECK_STACK + if (check_stack(__FILE__,__LINE__)) + { err_printf("Stack too deep in cl_equal\n"); + my_exit(EXIT_FAILURE); + } +#endif + for (;;) + { + int32 ta = (int32)a & TAG_BITS; + if (ta == TAG_CONS +#ifdef COMMON + && a != nil +#endif + ) + { if (!consp(b) +#ifdef COMMON + || b == nil +#endif + ) return NO; + else + { Lisp_Object ca = qcar(a), cb = qcar(b); + if (ca == cb) + { a = qcdr(a); + b = qcdr(b); + if (a == b) return YES; + continue; + } +/* + * And here, because cl_equal() seems to be a very important low-level + * primitive, I unwind one level of the recursion that would arise + * with nested lists. + */ + for (;;) + { + int32 tca = (int32)ca & TAG_BITS; + if (tca == TAG_CONS +#ifdef COMMON + && ca != nil +#endif + ) + { if (!consp(cb) +#ifdef COMMON + || cb == nil +#endif + ) return NO; + else + { Lisp_Object cca = qcar(ca), ccb = qcar(cb); + if (cca == ccb) + { ca = qcdr(ca); + cb = qcdr(cb); + if (ca == cb) break; + continue; + } +/* + * Do a real recursion when I get down to args like + * ((x ...) ...) ((y ...) ...) + */ + if (!cl_equal(cca, ccb)) return NO; + ca = qcdr(ca); + cb = qcdr(cb); + if (ca == cb) break; + continue; + } + } + else if (tca <= TAG_SYMBOL || + ((int32)cb & TAG_BITS) != tca) return NO; + else switch (tca) + { + case TAG_NUMBERS: + { Header h = numhdr(ca); + if (h != numhdr(cb)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)ca + hh) != + *(Lisp_Object *)((char *)cb + hh)) + return NO; + } + break; + } +#ifdef COMMON + else if (!eql_numbers(ca, cb)) return NO; + else break; +#else + else return NO; +#endif + } + case TAG_VECTOR: + if (!cl_vec_equal(ca, cb)) return NO; + break; + default: + case TAG_BOXFLOAT: + { Header h = flthdr(ca); + if (h != flthdr(cb)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != + *(int32 *)(cb + (4 - TAG_BOXFLOAT))) + return NO; +#else + if (single_float_val(ca) != + single_float_val(cb)) return NO; +#endif + else break; + } + else +#endif + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)ca + + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)ca + + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (12 - TAG_BOXFLOAT)))) return NO; +#else + if (double_float_val(ca) != + double_float_val(cb)) return NO; +#endif + else break; + } + } + } + break; /* out of the for (;;) loop */ + } + a = qcdr(a); + b = qcdr(b); + if (a == b) return YES; + continue; + } + } + else if (ta <= TAG_SYMBOL || + ((int32)b & TAG_BITS) != ta) return NO; + else switch (ta) + { + case TAG_NUMBERS: + { Header h = numhdr(a); + if (h != numhdr(b)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)a + hh) != + *(Lisp_Object *)((char *)b + hh)) + return NO; + } + return YES; + } +#ifdef COMMON + else return eql_numbers(a, b); + +#else + else return NO; +#endif + } + case TAG_VECTOR: + return cl_vec_equal(a, b); + default: + case TAG_BOXFLOAT: + { Header h = flthdr(a); + if (h != flthdr(b)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != + *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; +#else + if (single_float_val(a) != single_float_val(b)) + return NO; +#endif + else return YES; + } + else +#endif +/* + * For the moment I view all non-single floats as double floats. Extra + * stuff will be needed here if I ever implement long floats as 3-word + * objects. + */ + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) + return NO; +#else + if (double_float_val(a) != double_float_val(b)) + return NO; +#endif + else return YES; + } + } + } + } +} + +static CSLbool vec_equal(Lisp_Object a, Lisp_Object b); + +#ifdef TRACED_EQUAL +#define LOG_SIZE 10000 +typedef struct equal_record +{ + char file[24]; + int line; + int depth; + int count; +} equal_record; + +static equal_record equal_counts[LOG_SIZE]; + +static void record_equal(char *file, int line, int depth) +{ + int hash = 169*line + depth; + char *p = file; + while (*p != 0) hash = 168*hash + (*p++ & 0xff); + hash = ((169*hash) & 0x7fffffff) % LOG_SIZE; + while (equal_counts[hash].count != 0) + { if (equal_counts[hash].line == line && + equal_counts[hash].depth == depth && + strncmp(equal_counts[hash].file, file, 24) == 0) + { equal_counts[hash].count++; + return; + } + hash = (hash + 1) % LOG_SIZE; + } + strncpy(equal_counts[hash].file, file, 24); + equal_counts[hash].line = line; + equal_counts[hash].depth = depth; + equal_counts[hash].count = 1; + return; +} + +void dump_equals() +{ + int i; + FILE *log = fopen("equal.log", "w"); + if (log == NULL) log = stdout; + fprintf(log, "\nCalls to equal...\n"); + for (i=0; i (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)ca + hh) != + *(Lisp_Object *)((char *)cb + hh)) + return NO; + } + break; + } +#ifdef COMMON + else if (!eql_numbers(ca, cb)) return NO; + else break; +#else + else return NO; +#endif + } + case TAG_VECTOR: + if (!vec_equal(ca, cb)) return NO; + break; + default: + case TAG_BOXFLOAT: + { Header h = flthdr(ca); + if (h != flthdr(cb)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != + *(int32 *)(cb + (4 - TAG_BOXFLOAT))) + return NO; +#else + if (single_float_val(ca) != + single_float_val(cb)) return NO; +#endif + else break; + } + else +#endif + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)ca + + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)ca + + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (12 - TAG_BOXFLOAT)))) return NO; +#else + if (double_float_val(ca) != + double_float_val(cb)) return NO; +#endif + + else break; + } + } + } + break; /* out of the for (;;) loop */ + } + a = qcdr(a); + b = qcdr(b); + if (a == b) return YES; + continue; + } + } + else if (ta <= TAG_SYMBOL || + ((int32)b & TAG_BITS) != ta) return NO; + else switch (ta) + { + case TAG_NUMBERS: + { Header h = numhdr(a); + if (h != numhdr(b)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)a + hh) != + *(Lisp_Object *)((char *)b + hh)) + return NO; + } + return YES; + } +#ifdef COMMON + else return eql_numbers(a, b); + +#else + else return NO; +#endif + } + case TAG_VECTOR: + return vec_equal(a, b); + default: + case TAG_BOXFLOAT: + { Header h = flthdr(a); + if (h != flthdr(b)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != + *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; +#else + if (single_float_val(a) != single_float_val(b)) + return NO; +#endif + else return YES; + } + else +#endif +/* + * For the moment I view all non-single floats as double floats. Extra + * stuff will be needed here if I ever implement long floats as 3-word + * objects. + */ + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) + return NO; +#else + if (double_float_val(a) != double_float_val(b)) + return NO; +#endif + else return YES; + } + } + } + } +} + +#ifdef TRACED_EQUAL +#undef equal_fn +#define equal_fn(a, b) traced_equal(a, b, __FILE__, __LINE__, 0) +#endif + +static CSLbool vec_equal(Lisp_Object a, Lisp_Object b) +/* + * Here a and b are known to be vectors. Compare using recursive calls to + * EQUAL on all components. + */ +{ + Header ha = vechdr(a), hb = vechdr(b); + int32 l; + if (ha != hb) return NO; + l = (int32)doubleword_align_up(length_of_header(ha)); + if (vector_holds_binary(ha)) + { while ((l -= 4) != 0) + if (*((int32 *)((char *)a + l - TAG_VECTOR)) != + *((int32 *)((char *)b + l - TAG_VECTOR))) return NO; + return YES; + } + else + { if (is_mixed_header(ha)) + { while (l > 16) + { unsigned32 ea = *((unsigned32 *)((char *)a + l - TAG_VECTOR - 4)), + eb = *((unsigned32 *)((char *)b + l - TAG_VECTOR - 4)); + if (ea != eb) return NO; + l -= 4; + } + } + while ((l -= 4) != 0) + { Lisp_Object ea = *((Lisp_Object *)((char *)a + l - TAG_VECTOR)), + eb = *((Lisp_Object *)((char *)b + l - TAG_VECTOR)); + if (ea == eb) continue; + if (!equal(ea, eb)) return NO; + } + return YES; + } +} + +CSLbool equalp(Lisp_Object a, Lisp_Object b) +/* + * a and b are not EQ at this stage.. I guarantee to have checked that + * before entering this general purpose code. + */ +{ + Lisp_Object nil = C_nil; + CSL_IGNORE(nil); +/* + * The for loop at the top here is so that equalp can iterate along the + * length of linear lists. + */ +#ifdef CHECK_STACK + if (check_stack(__FILE__,__LINE__)) + { err_printf("Stack too deep in equalp\n"); + my_exit(EXIT_FAILURE); + } +#endif + for (;;) + { + int32 ta = (int32)a & TAG_BITS; + if (ta == TAG_CONS +#ifdef COMMON + && a != nil +#endif + ) + { if (!consp(b) +#ifdef COMMON + || b == nil +#endif + ) return NO; + else + { Lisp_Object ca = qcar(a), cb = qcar(b); + if (ca == cb) + { a = qcdr(a); + b = qcdr(b); + if (a == b) return YES; + continue; + } +/* + * And here, because equalp() seems to be a very important low-level + * primitive, I unwind one level of the recursion that would arise + * with nested lists. + */ + for (;;) + { + int32 tca = (int32)ca & TAG_BITS; + if (tca == TAG_CONS +#ifdef COMMON + && ca != nil +#endif + ) + { if (!consp(cb) +#ifdef COMMON + || cb == nil +#endif + ) return NO; + else + { Lisp_Object cca = qcar(ca), ccb = qcar(cb); + if (cca == ccb) + { ca = qcdr(ca); + cb = qcdr(cb); + if (ca == cb) break; + continue; + } +/* + * Do a real recursion when I get down to args like + * ((x ...) ...) ((y ...) ...) + */ + if (!equalp(cca, ccb)) return NO; + ca = qcdr(ca); + cb = qcdr(cb); + if (ca == cb) break; + continue; + } + } + else if (tca <= TAG_SYMBOL || + ((int32)cb & TAG_BITS) != tca) return NO; + else switch (tca) + { + case TAG_NUMBERS: + { Header h = numhdr(ca); + if (h != numhdr(cb)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)ca + hh) != + *(Lisp_Object *)((char *)cb + hh)) + return NO; + } + break; + } +#ifdef COMMON + else if (!eql_numbers(ca, cb)) return NO; + else break; +#else + else return NO; +#endif + } + case TAG_VECTOR: +/* /* At present vec_equal() is not right here */ + if (!vec_equal(ca, cb)) return NO; + break; + default: + case TAG_BOXFLOAT: + { Header h = flthdr(ca); + if (h != flthdr(cb)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(ca + (4 - TAG_BOXFLOAT)) != + *(int32 *)(cb + (4 - TAG_BOXFLOAT))) + return NO; +#else + if (single_float_val(ca) != + single_float_val(cb)) return NO; +#endif + + else break; + } + else +#endif + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)ca + + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)ca + + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)cb + + (12 - TAG_BOXFLOAT)))) return NO; +#else + if (double_float_val(ca) != + double_float_val(cb)) return NO; +#endif + else break; + } + } + } + break; /* out of the for (;;) loop */ + } + a = qcdr(a); + b = qcdr(b); + if (a == b) return YES; + continue; + } + } + else if (ta <= TAG_SYMBOL || + ((int32)b & TAG_BITS) != ta) return NO; + else switch (ta) + { + case TAG_NUMBERS: + { Header h = numhdr(a); + if (h != numhdr(b)) return NO; + if (type_of_header(h) == TYPE_BIGNUM) + { int32 hh = (int32)length_of_header(h) - TAG_NUMBERS; + while (hh > (4 - TAG_NUMBERS)) + { hh -= 4; + if (*(Lisp_Object *)((char *)a + hh) != + *(Lisp_Object *)((char *)b + hh)) + return NO; + } + return YES; + } +#ifdef COMMON + else return eql_numbers(a, b); + +#else + else return NO; +#endif + } + case TAG_VECTOR: +/* /* wrong for Common Lisp */ + return vec_equal(a, b); + default: + case TAG_BOXFLOAT: + { Header h = flthdr(a); + if (h != flthdr(b)) return NO; + h = length_of_header(h); +#ifdef COMMON + if (h == 8) /* Single float */ + { +#ifdef OLD_CODE + if (*(int32 *)(a + (4 - TAG_BOXFLOAT)) != + *(int32 *)(b + (4 - TAG_BOXFLOAT))) return NO; +#else + if (single_float_val(a) != single_float_val(b)) + return NO; +#endif + else return YES; + } + else +#endif +/* + * For the moment I view all non-single floats as double floats. Extra + * stuff will be needed here if I ever implement long floats as 3-word + * objects. + */ + { +#ifdef OLD_CODE + if ((*(int32 *)((char *)a + (8 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (8 - TAG_BOXFLOAT))) || + (*(int32 *)((char *)a + (12 - TAG_BOXFLOAT)) != + *(int32 *)((char *)b + (12 - TAG_BOXFLOAT)))) + return NO; +#else + if (double_float_val(a) != double_float_val(b)) + return NO; +#endif + + else return YES; + } + } + } + } +} + +Lisp_Object Leq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + return onevalue(Lispify_predicate(a == b)); +} + +Lisp_Object Leql(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +{ + return onevalue(Lispify_predicate(eql(a, b))); +} + +Lisp_Object Leqcar(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +{ + if (!consp(a)) return onevalue(nil); + a = qcar(a); +#ifdef COMMON + return onevalue(Lispify_predicate(eql(a, b))); +#else + return onevalue(Lispify_predicate(a == b)); +#endif +} + +Lisp_Object Lequalcar(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +{ + if (!consp(a)) return onevalue(nil); + a = qcar(a); + if (a == b) return lisp_true; + else return onevalue(Lispify_predicate(equal(a, b))); +} + +Lisp_Object Lcl_equal(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + if (a == b) return onevalue(lisp_true); + else return onevalue(Lispify_predicate(cl_equal(a, b))); +} + +Lisp_Object Lequal(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + if (a == b) return onevalue(lisp_true); + else return onevalue(Lispify_predicate(equal(a, b))); +} + +Lisp_Object Lequalp(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + if (a == b) return onevalue(lisp_true); + else return onevalue(Lispify_predicate(equalp(a, b))); +} + +Lisp_Object Lneq(Lisp_Object nil, + Lisp_Object a, Lisp_Object b) +{ + CSLbool r; +#ifdef COMMON + r = cl_equal(a, b); +#else + r = equal(a, b); +#endif + return onevalue(Lispify_predicate(!r)); +} + +Lisp_Object Lnull(Lisp_Object nil, Lisp_Object a) +{ + return onevalue(Lispify_predicate(a == nil)); +} + +Lisp_Object Lendp(Lisp_Object nil, Lisp_Object a) +{ + if (a == nil) return onevalue(lisp_true); + else if (is_cons(a)) return onevalue(nil); + else return error(1, err_bad_endp, a); +} + +Lisp_Object Lnreverse(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object b = nil; +#ifdef COMMON + if (is_vector(a)) + { int32 n = Llength(nil, a) - 0x10; + int32 i = TAG_FIXNUM; + while (n > i) + { Lisp_Object w = Laref2(nil, a, i); + Laset(nil, 3, a, i, Laref2(nil, a, n)); + Laset(nil, 3, a, n, w); + i += 0x10; + n -= 0x10; + } + return onevalue(a); + } +#endif + while (consp(a)) + { Lisp_Object c = a; + a = qcdr(a); + qcdr(c) = b; + b = c; + } + return onevalue(b); +} + +#ifdef COMMON + +/* + * nreverse0 is like nreverse except that if its input is atomic it gets + * returned intact rather than being converted to nil. + */ + +Lisp_Object Lnreverse0(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object b = nil; + if (!consp(a)) return onevalue(a); + b = a; + a = qcdr(a); + qcdr(b) = nil; + while (consp(a)) + { Lisp_Object c = a; + a = qcdr(a); + qcdr(c) = b; + b = c; + } + return onevalue(b); +} + +#endif + +Lisp_Object Lreverse(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object r; + stackcheck1(0, a); + nil = C_nil; + r = nil; + while (consp(a)) + { push(a); + r = cons(qcar(a), r); + pop(a); + errexit(); + a = qcdr(a); + } + return onevalue(r); +} + +Lisp_Object Lassoc(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ +#ifdef TRACED_EQUAL + Lisp_Object save_b = b; + int pos = 0; +#endif + if (is_symbol(a) || is_fixnum(a)) + { while (consp(b)) + { Lisp_Object c = qcar(b); + if (consp(c) && a == qcar(c)) return onevalue(c); + b = qcdr(b); + } + return onevalue(nil); + } + while (consp(b)) + { Lisp_Object c = qcar(b); + if (consp(c)) + { Lisp_Object cc = qcar(c); +#ifdef COMMON + if (cl_equal(a, cc)) return onevalue(c); +#else + if (equal(a, cc)) + { +#ifdef TRACED_EQUAL + trace_printf("Assoc YES %3d %3d ", pos, int_of_fixnum(Llength(nil,save_b))); + prin_to_stdout(a); trace_printf("\n"); +#endif + return onevalue(c); + } +#endif + } + b = qcdr(b); +#ifdef TRACED_EQUAL + pos++; +#endif + } +#ifdef TRACED_EQUAL + trace_printf("Assoc NO %3d %3d ", pos, int_of_fixnum(Llength(nil,save_b))); + prin_to_stdout(a); trace_printf("\n"); +#endif + return onevalue(nil); +} + +Lisp_Object Latsoc(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ +#ifdef COMMON + if (is_symbol(a) || is_fixnum(a)) + { while (consp(b)) + { Lisp_Object c = qcar(b); + if (consp(c) && a == qcar(c)) return onevalue(c); + b = qcdr(b); + } + return onevalue(nil); + } +#endif + while (consp(b)) + { Lisp_Object c = qcar(b); +/* + * eql() can neither fail nor call the garbage collector, so I do + * not need to stack things here. + */ +#ifdef COMMON + if (consp(c) && eql(a, qcar(c))) return onevalue(c); +#else + if (consp(c) && a == qcar(c)) return onevalue(c); +#endif + b = qcdr(b); + } + return onevalue(nil); +} + +Lisp_Object Lmember(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + if (is_symbol(a) || is_fixnum(a)) + { while (consp(b)) + { if (a == qcar(b)) return onevalue(b); + b = qcdr(b); + } + return onevalue(nil); + } + while (consp(b)) + { Lisp_Object cb = qcar(b); +#ifdef COMMON + if (cl_equal(a, cb)) return onevalue(b); +#else + if (equal(a, cb)) return onevalue(b); +#endif + b = qcdr(b); + } + return onevalue(nil); +} + +Lisp_Object Lmemq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ +#ifdef COMMON + if (is_symbol(a) || is_fixnum(a)) + { while (consp(b)) + { if (a == qcar(b)) return onevalue(b); + b = qcdr(b); + } + return onevalue(nil); + } +#endif + while (consp(b)) +/* + * Note that eql() can never fail, and so checking for errors + * and stacking a and b across the call to it is not necessary. + */ + { +#ifdef COMMON + if (eql(a, qcar(b))) return onevalue(b); +#else + if (a == qcar(b)) return onevalue(b); +#endif + b = qcdr(b); + } + return onevalue(nil); +} + +static CSLbool smemq(Lisp_Object a, Lisp_Object b) +{ +/* + * /* This is a bit worrying - it can use C recursion to arbitrary + * depth without any checking for overflow, and hence it can ESCAPE + * if (e.g.) given cyclic structures. Some alteration is needed. As + * things stand the code can never give wrong answers via GC rearrangement - + * the problem is closer to being that it can never call the GC. + */ +#ifdef COMMON + Lisp_Object nil = C_nil; +#else + nil_as_base +#endif + while (consp(b)) + { Lisp_Object w = qcar(b); + if (w == quote_symbol) return NO; + else if (smemq(a, w)) return YES; + else b = qcdr(b); + } + return (a == b); +} + +Lisp_Object Lsmemq(Lisp_Object nil, Lisp_Object a, Lisp_Object b) +{ + CSLbool r; + r = smemq(a, b); + errexit(); + return onevalue(Lispify_predicate(r)); +} + +/* + * (defun contained (x y) + * (cond ((atom y) (equal x y)) + * ((equal x y) 't) + * ('t (or (contained x (car y)) (contained x (cdr y)))))) + */ + +static CSLbool containedeq(Lisp_Object nil, Lisp_Object x, Lisp_Object y) +{ + while (consp(y)) + { if (containedeq(nil, x, qcar(y))) return YES; + y = qcdr(y); + } + return (x == y); +} + +static CSLbool containedequal(Lisp_Object nil, Lisp_Object x, Lisp_Object y) +{ + while (consp(y)) + { if (equal(x, y)) return YES; + if (containedequal(nil, x, qcar(y))) return YES; + y = qcdr(y); + } + return equal(x, y); +} + +static Lisp_Object Lcontained(Lisp_Object nil, Lisp_Object x, Lisp_Object y) +{ + CSLbool r; + if (is_symbol(x) || is_fixnum(x)) r = containedeq(nil, x, y); + else r = containedequal(nil, x, y); + errexit(); + return onevalue(Lispify_predicate(r)); +} + +Lisp_Object Llast(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object b; + if (!consp(a)) return aerror1("last", a); + while (b = qcdr(a), consp(b)) a = b; + return onevalue(qcar(a)); +} + +Lisp_Object Llastpair(Lisp_Object nil, Lisp_Object a) +{ + Lisp_Object b; + if (!consp(a)) return onevalue(a); /* aerror1("lastpair", a); */ + while (b = qcdr(a), consp(b)) a = b; + return onevalue(a); +} + +Lisp_Object Llength(Lisp_Object nil, Lisp_Object a) +{ + if (a == nil) return onevalue(fixnum_of_int(0)); + if (is_cons(a)) + { Lisp_Object n; +/* + * Possibly I should do something to trap cyclic lists.. ? + */ + n = fixnum_of_int(1); +/* + * I have unrolled the loop here 4 times since I expect length to be + * tolerably heavily used. Look at the assembly code generated for + * this to see if it was useful or counterproductive! + */ + for (;;) + { a = qcdr(a); + if (!consp(a)) return onevalue(n); + a = qcdr(a); + if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (1 << 4))); + a = qcdr(a); + if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (2 << 4))); + a = qcdr(a); + if (!consp(a)) return onevalue((Lisp_Object)((int32)n + (3 << 4))); + n = (Lisp_Object)((int32)n + (4 << 4)); + } + } +#ifndef COMMON + return onevalue(fixnum_of_int(0)); /* aerror("length");??? */ +#else +/* + * Common Lisp expects length to find the length of vectors + * as well as lists. + */ + else if (!is_vector(a)) return aerror1("length", a); + else + { Header h = vechdr(a); + int32 n = length_of_header(h) - 4; + if (type_of_header(h) == TYPE_ARRAY) + { Lisp_Object dims = elt(a, 1); + Lisp_Object fillp = elt(a, 5); + if (consp(dims) && !consp(qcdr(dims))) dims = qcar(dims); + else return aerror1("length", a); /* Not one-dimensional */ + if (is_fixnum(fillp)) dims = fillp; + return onevalue(dims); + } + if (header_of_bitvector(h)) + { n = (n - 1)*8; +/* Dodgy constant on next line - critically dependent on tag codes used! */ + n += ((h & 0x380) >> 7) + 1; + } + else if (type_of_header(h) != TYPE_STRING) n = n >> 2; + return onevalue(fixnum_of_int(n)); + } +#endif +} + +#ifdef COMMON + +Lisp_Object MS_CDECL Lappend_n(Lisp_Object nil, int nargs, ...) +{ + va_list a; + int i; + Lisp_Object r; + if (nargs == 0) return onevalue(nil); + va_start(a, nargs); + push_args(a, nargs); +/* + * The actual args have been passed a C args - I can not afford to + * risk garbage collection until they have all been moved somewhere safe, + * and here that safe place is the Lisp stack. I have to delay checking for + * overflow on same until all args have been pushed. + */ + stackcheck0(nargs); + nil = C_nil; + r = nil; +/* + * rearrange order of items on the stack... + * The idea is that I will then reverse-copy the args in the order a1, + * a2 , ... to make a result list. But I want to pop the stack as soon as + * I can, so I need arg1 on the TOP of the stack. + */ + for (i = 0; 2*i+1>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### + +# DEC Alpha, with OSF (tested on 1.3) and the DEC C compiler. Note that +# this is a 64-bit machine, but I use it with the "-taso" linker option +# so that I run in a 32-bit address space. + +CC = cc +OPTFLAGS = -O2 +MPIFLAGS = +CFLAGS = -c $(OPTFLAGS) -std1 -Olimit 3000 -I$(CSLBASE) $(MPIFLAGS) +LIBS = -lm -lcurses -taso + +########################################################################### + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.cc ================================================================== --- r36/cslsrc/Makefile.cc +++ r36/cslsrc/Makefile.cc @@ -1,834 +1,834 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### - -# Generic Unix with "cc". Note that if you use this you should review -# the file "machine.h" to ensure that CSL knows what name to report for -# your system. Also if the system you are running on needs more libraries -# scanned during the link phase. The Makefile create here will VERY -# probably need to be adjusted by hand. - -CC = cc -OPTFLAGS = -O -MPIFLAGS = -CFLAGS = -c $(OPTFLAGS) -I$(CSLBASE) $(MPIFLAGS) -LIBS = -lm -lcurses - -########################################################################### - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### + +# Generic Unix with "cc". Note that if you use this you should review +# the file "machine.h" to ensure that CSL knows what name to report for +# your system. Also if the system you are running on needs more libraries +# scanned during the link phase. The Makefile create here will VERY +# probably need to be adjusted by hand. + +CC = cc +OPTFLAGS = -O +MPIFLAGS = +CFLAGS = -c $(OPTFLAGS) -I$(CSLBASE) $(MPIFLAGS) +LIBS = -lm -lcurses + +########################################################################### + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.gcc ================================================================== --- r36/cslsrc/Makefile.gcc +++ r36/cslsrc/Makefile.gcc @@ -1,878 +1,878 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### - -# Generic Unix with GCC. Note that if you use this you should review -# the file "machine.h" to ensure that CSL knows what name to report for -# your system. Also if the system you are running on needs more libraries -# scanned in the link-phase. - -CC = gcc -OPTFLAGS = -O3 -MPIFLAGS = -CFLAGS = -c $(OPTFLAGS) -ansi -I$(CSLBASE) $(MPIFLAGS) -LIBS = -lm -lc -lcurses - -########################################################################### - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### + +# Generic Unix with GCC. Note that if you use this you should review +# the file "machine.h" to ensure that CSL knows what name to report for +# your system. Also if the system you are running on needs more libraries +# scanned in the link-phase. + +CC = gcc +OPTFLAGS = -O3 +MPIFLAGS = +CFLAGS = -c $(OPTFLAGS) -ansi -I$(CSLBASE) $(MPIFLAGS) +LIBS = -lm -lc -lcurses + +########################################################################### + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.gcc.solaris64 ================================================================== --- r36/cslsrc/Makefile.gcc.solaris64 +++ r36/cslsrc/Makefile.gcc.solaris64 @@ -1,888 +1,888 @@ - -From hearn@rand.org Sat Oct 30 11:44:17 1999 -Date: Fri, 29 Oct 1999 11:10:08 -0700 -From: Tony Hearn -To: Arthur Norman -Subject: gcc solaris64 makefile - -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### -# Sun SPARC, using GCC - -CC = gcc -OPTFLAGS = -O3 -PROFFLAGS = -SPARCFLAGS = -SUNOSFLAGS = -MPIFLAGS = -CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) -SUNOSLIBS = -lsocket -lnsl -SUNOSLIBS1 = -lm -lc -LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses - -########################################################################### -########################################################################### - - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile + +From hearn@rand.org Sat Oct 30 11:44:17 1999 +Date: Fri, 29 Oct 1999 11:10:08 -0700 +From: Tony Hearn +To: Arthur Norman +Subject: gcc solaris64 makefile + +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### +# Sun SPARC, using GCC + +CC = gcc +OPTFLAGS = -O3 +PROFFLAGS = +SPARCFLAGS = +SUNOSFLAGS = +MPIFLAGS = +CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) +SUNOSLIBS = -lsocket -lnsl +SUNOSLIBS1 = -lm -lc +LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses + +########################################################################### +########################################################################### + + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.linux ================================================================== --- r36/cslsrc/Makefile.linux +++ r36/cslsrc/Makefile.linux @@ -1,878 +1,878 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### - -# Generic Unix with GCC. Note that if you use this you should review -# the file "machine.h" to ensure that CSL knows what name to report for -# your system. Also if the system you are running on needs more libraries -# scanned in the link-phase. - -CC = gcc -OPTFLAGS = -O3 -MPIFLAGS = -CFLAGS = -c $(OPTFLAGS) -ansi -I$(CSLBASE) $(MPIFLAGS) -LIBS = -lm -lc -lcurses - -########################################################################### - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### + +# Generic Unix with GCC. Note that if you use this you should review +# the file "machine.h" to ensure that CSL knows what name to report for +# your system. Also if the system you are running on needs more libraries +# scanned in the link-phase. + +CC = gcc +OPTFLAGS = -O3 +MPIFLAGS = +CFLAGS = -c $(OPTFLAGS) -ansi -I$(CSLBASE) $(MPIFLAGS) +LIBS = -lm -lc -lcurses + +########################################################################### + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.sgi ================================================================== --- r36/cslsrc/Makefile.sgi +++ r36/cslsrc/Makefile.sgi @@ -1,833 +1,833 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - -########################################################################### - -# Silicon Graphics, using the SGI C compiler -# I have not yet worked out how to exploit -O3 or -O4 optimisation -# but see sketches later down this file where I have tried same for -# the DEC Alpha. - -CC = cc -OPTFLAGS = -O2 -MPIFLAGS = -CFLAGS = -c -ansi -DSGICC=1 $(OPTFLAGS) -Olimit 3000 -I$(CSLBASE) $(MPIFLAGS) -LIBS = -lm -lc -lcurses - -########################################################################### - - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + +########################################################################### + +# Silicon Graphics, using the SGI C compiler +# I have not yet worked out how to exploit -O3 or -O4 optimisation +# but see sketches later down this file where I have tried same for +# the DEC Alpha. + +CC = cc +OPTFLAGS = -O2 +MPIFLAGS = +CFLAGS = -c -ansi -DSGICC=1 $(OPTFLAGS) -Olimit 3000 -I$(CSLBASE) $(MPIFLAGS) +LIBS = -lm -lc -lcurses + +########################################################################### + + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.solaris ================================================================== --- r36/cslsrc/Makefile.solaris +++ r36/cslsrc/Makefile.solaris @@ -1,881 +1,881 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### -# Sun SPARC, using GCC - -CC = gcc -OPTFLAGS = -O3 -PROFFLAGS = -SPARCFLAGS = -SUNOSFLAGS = -MPIFLAGS = -CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) -SUNOSLIBS = -lsocket -lnsl -SUNOSLIBS1 = -lm -lc -LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses - -########################################################################### -########################################################################### - - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### +# Sun SPARC, using GCC + +CC = gcc +OPTFLAGS = -O3 +PROFFLAGS = +SPARCFLAGS = +SUNOSFLAGS = +MPIFLAGS = +CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) +SUNOSLIBS = -lsocket -lnsl +SUNOSLIBS1 = -lm -lc +LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses + +########################################################################### +########################################################################### + + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.solaris64 ================================================================== --- r36/cslsrc/Makefile.solaris64 +++ r36/cslsrc/Makefile.solaris64 @@ -1,888 +1,888 @@ -# UNSUPPORTED: Not created using "makemake" and uses a Sun compiler -# that will not be available in all installations, but that -# on suitable hardware generates fast code. -# Contributed via A C Hearn, November 1999 - - -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### -# Sun SPARC, using SUN's Workshop compilers 5.0 - -CC = /opt/SUNWspro/bin/cc -OPTFLAGS = -fast -PROFFLAGS = -SPARCFLAGS = -SUNOSFLAGS = -MPIFLAGS = -CFLAGS = -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) -$(MPIFLAGS) -SUNOSLIBS = -lsocket -lnsl -SUNOSLIBS1 = -lm -lc -LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses - -########################################################################### -########################################################################### - - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +# UNSUPPORTED: Not created using "makemake" and uses a Sun compiler +# that will not be available in all installations, but that +# on suitable hardware generates fast code. +# Contributed via A C Hearn, November 1999 + + +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### +# Sun SPARC, using SUN's Workshop compilers 5.0 + +CC = /opt/SUNWspro/bin/cc +OPTFLAGS = -fast +PROFFLAGS = +SPARCFLAGS = +SUNOSFLAGS = +MPIFLAGS = +CFLAGS = -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) +$(MPIFLAGS) +SUNOSLIBS = -lsocket -lnsl +SUNOSLIBS1 = -lm -lc +LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses + +########################################################################### +########################################################################### + + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.sunos ================================================================== --- r36/cslsrc/Makefile.sunos +++ r36/cslsrc/Makefile.sunos @@ -1,881 +1,881 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### -# Sun SPARC, using GCC - -CC = gcc -OPTFLAGS = -O3 -PROFFLAGS = -SPARCFLAGS = -SUNOSFLAGS = -I/usr/5include -MPIFLAGS = -CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) -SUNOSLIBS = -L/usr/5lib -lresolv -SUNOSLIBS1 = -lm -lc -LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses - -########################################################################### -########################################################################### - - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith01.o \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith02.o \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith03.o \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith04.o \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o arith05.o \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith06.o \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith07.o \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith08.o \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith09.o \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith10.o \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o arith11.o \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o arith12.o \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes.o \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o bytes1.o \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - -o bytes1.o \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o char.o \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o csl.o \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval1.o \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval2.o \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o eval3.o \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o eval4.o \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - -o fasl.o \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns1.o \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o fns2.o \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o fns3.o \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o gc.o \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - -o $(SYS).o \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - -o preserve.o \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o print.o \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - -o read.o \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - -o restart.o \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o stubs.o \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - -o cslmpi.o \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u01.o \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u02.o \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u03.o \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u04.o \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u05.o \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u06.o \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u07.o \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u08.o \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u09.o \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u10.o \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u11.o \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - -o u12.o \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### +# Sun SPARC, using GCC + +CC = gcc +OPTFLAGS = -O3 +PROFFLAGS = +SPARCFLAGS = +SUNOSFLAGS = -I/usr/5include +MPIFLAGS = +CFLAGS = -ansi -c $(PROFFLAGS) $(OPTFLAGS) $(SPARCFLAGS) $(SUNOSFLAGS) -I$(CSLBASE) $(MPIFLAGS) +SUNOSLIBS = -L/usr/5lib -lresolv +SUNOSLIBS1 = -lm -lc +LIBS = $(SUNOSLIBS) $(SUNOSLIBS1) -lcurses + +########################################################################### +########################################################################### + + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) -o $(ASMOBJ).o $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith01.o \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith02.o \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith03.o \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith04.o \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o arith05.o \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith06.o \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith07.o \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith08.o \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith09.o \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith10.o \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o arith11.o \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o arith12.o \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes.o \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o bytes1.o \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + -o bytes1.o \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o char.o \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o csl.o \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval1.o \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval2.o \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o eval3.o \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o eval4.o \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + -o fasl.o \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns1.o \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o fns2.o \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o fns3.o \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o gc.o \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + -o $(SYS).o \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + -o preserve.o \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o print.o \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + -o read.o \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + -o restart.o \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o stubs.o \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + -o cslmpi.o \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u01.o \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u02.o \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u03.o \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u04.o \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u05.o \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u06.o \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u07.o \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u08.o \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u09.o \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u10.o \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u11.o \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + -o u12.o \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/Makefile.ultra ================================================================== --- r36/cslsrc/Makefile.ultra +++ r36/cslsrc/Makefile.ultra @@ -1,833 +1,833 @@ -########################################################################### -# # -# makefile for REDUCE 3.6 using CSL # -# # -########################################################################### - -# The following lines indicates the place on your disc where the "cslbase" -# directory exists. This is the place where the C sources files for CSL -# live. There are two versions here, the first should use Unix-like -# file name conventions (in particular "/" as a directory separator) while -# the second will (in some cases) be a host-specific translation. - -UCSLBASE = ../cslbase -CSLBASE = ../cslbase - - -########################################################################### - -# Sun Super SPARC, using the Sun C compiler. - -# I get conflicting reports about where to find the C compiler... -# please adjust this file by hand if you need to. -CC = /opt/EA/SUNWspro/bin/cc -SPARCOPTS = -xO5 -xdepend -dalign -xtarget=ultra1/170 -DLONG_LONG_64=1 -DMULDIV64=1 -SPARCLIBS = -lfast -lm -MPIFLAGS = -CFLAGS = -c $(SPARCOPTS) -DBSD_LIB=1 -I$(CSLBASE) $(MPIFLAGS) -LIBS = $(SPARCLIBS) -lcurses - -########################################################################### - -########################################################################### - -SHELL = /bin/sh -LINK = $(CC) -LFLAGS = -OUT = -o -OUTOBJ = -o -ASM = $(CC) -ASMFLAGS = $(CFLAGS) -ASMSRC = -ASMOBJ = -ASMOBJDEP = notused.obj -SYS = sysunix -STORE = -k8000 -XSTORE = -k8000 -RM = rm -MKDIR = mkdir -COPY = cp -STRIP = strip -WX = - -########################################################################### - - -########################################################################### -########################################################################### -# # -# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # -# on MSDOS, Windows and Unix. This part of the file expects a number of # -# symbols to have been defined: # -# # -# CSLBASE = file-path for CSLBASE directory # -# CC = The C compiler to use # -# CFLAGS = Flags for C compiler when compiling CSL # -# LINK = Linker to use # -# LFLAGS = Flags for linker # -# LIBS = Libraries to quote to linker # -# OUT = "-o" or "-out:" See link commands # -# OUTOBJ = "-o" often : where to put object code from C compilation # -# ASM = The assembler to use # -# ASMFLAGS = Flags for the assembler # -# ASMSRC = Assembly code source file to use # -# ASMOBJ = Object file for above (or NULL if no assembly used) # -# ASMOBJDEP = Ditto, but may not be NULL # -# SYS = name of system-specific file (sysdos or sysnt etc) # -# STORE = Memory option to pass to CSL (-k2500 is minimum) # -# XSTORE = Memory for the rebuild job that generates C code # -# RM = del for DOS, = rm for Unix # -# MKDIR = mkdir # -# COPY = copy for DOS, = cp for Unix # -# STRIP = echo for DOS, = strip for Unix # -# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # -# WX = wx for Windows 3.1, null in all other cases # -# # -# The master version of this file is called "makebase" and is used to # -# create both DOS and Unix makefiles. Use the Codemist "makemake" # -# program to perform the conversion - eg # -# makemake -f makebase -o makemake.386 watcom dos # -# makemake -f makebase -o Makefile.sgi sgi # -# Just "makemake -f makebase" gives list of systems supported # -########################################################################### -########################################################################### - - - -########################################################################### -########################################################################### -# -# The main final target is r36.img, the image file for full REDUCE. -# If you want to rebuild stage-by-stage (eg while testing), try the -# sequence -# make csl compiles and links C coded kernel -# make csl.img builds compiler image on top of above -# make slowr36.img makes bootstrap REDUCE -# (roughly twice as slow as final one) -# only used for system recompilation. -# make ccode runs test file to collect statistics -# and create files u*.c and u*.lsp -# out of hot-spot parts of REDUCE. Note that -# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main -# >>>> N. B. >>>> set of "make" dependences, since the -# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but -# you need to do it again if the main REDUCE -# sources are altered -# make fasl36.img final compilation of most of REDUCE -# make r36 build final executable binary -# make r36.img build final image file -# make testall runs test files, output to log directory -# -########################################################################### -########################################################################### - - -# -# C is another name for CSLBASE, the directory that CSL source files live -# in. I introduce it here mainly because $(C) is so much more compact -# then $(CSLBASE). -# - -C = $(CSLBASE) - -# -# DOBJS is a list of all the object files that are common to all variants -# on the system built here -# - -DOBJS = arith01.o arith02.o arith03.o arith04.o \ - arith05.o arith06.o arith07.o arith08.o \ - arith09.o arith10.o arith11.o arith12.o \ - char.o csl.o cslmpi.o eval1.o eval2.o \ - eval3.o eval4.o fns1.o fns2.o fns3.o \ - print.o read.o restart.o $(ASMOBJ) \ - $(SYS).o - -CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ - arith05.o,arith06.o,arith07.o,arith08.o,\ - arith09.o,arith10.o,arith11.o,arith12.o,\ - char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ - eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ - print.o,read.o,restart.o,$(ASMOBJ),\ - $(SYS).o - -# -# OBJS adds in the files used when I am not building a demonstration-mode CSL -# - -OBJS = $(DOBJS) fasl.o gc.o preserve.o - -COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o - -# -# UOBJS come from that code that is compiled from Lisp into C -# - -UOBJS = u01.o u02.o u03.o u04.o u05.o \ - u06.o u07.o u08.o u09.o u10.o \ - u11.o u12.o - -CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ - u06.o,u07.o,u08.o,u09.o,u10.o,\ - u11.o,u12.o - - -########################################################################### -########################################################################### -# -# "r36.img" is an image file for the main parts of Reduce - -r36.img: fasl36.img r36 - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - -$(MKDIR) log - -# "make patches" can be used after the "src/patches.red" file has changed - -patches: ../src/patches.red $(SYMBOLIC) - $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log - $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log - $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log - - -# -# "make testall" tests the final production version of Reduce -# - -testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ - log/boolean.log log/cali.log log/camal.log log/changevr.log \ - log/compact.log log/complex.log log/crack.log log/cvit.log \ - log/decompos.log log/defint.log log/desir.log log/dfpart.log \ - log/dummy.log log/elem.log log/excalc.log log/factor.log \ - log/fide.log log/fps.log log/gcd.log log/gentran.log \ - log/groebner.log log/ideals.log log/ineq.log log/int.log \ - log/invbase.log log/laplace.log log/lie.log log/limits.log \ - log/linalg.log log/math.log log/matrix.log log/modsr.log \ - log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ - log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ - log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ - log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ - log/scope.log log/sets.log log/solve.log log/spde.log \ - log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ - log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ - log/zeilberg.log log/ztrans.log $(SYMBOLIC) - -echo all tests done - - - -########################################################################### -########################################################################### -# -# The targets from here on down are used in the process of doing a full -# system re-build - -# fasl36.img is a file needed during a re-build of Reduce. It contains -# compiled versions of all the Reduce modules. - -fasl36.img: csl slowr36.img - -$(RM) fasl36.img - $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ - ../cslsrc/fasl36.red -- fasl36.log - -# "make personal" downgrades a full version of Reduce to make a"personal" -# version (without the compiler). - -personal: r36 r36.img $(SYMBOLIC) - $(COPY) r36 ../r36 - $(COPY) r36.img ../r36.img - $(WX) ../r36 ../cslsrc/remcmp.lsp - -# "make rl" manufactures an image file that contains just an Rlisp parser - -rl: $(SYMBOLIC) rlisp rlisp.img - -rlisp: $(SYMBOLIC) csl - $(COPY) csl rlisp - -rlisp.img: rlisp - $(WX) rlisp $(STORE) -v -z -o rlisp.img \ - ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log - -# -# r36 can only be built when all the user-generated C code has been -# built. -# - -r36: bytes.o $(OBJS) \ - $(UOBJS) - $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) - $(STRIP) r36 - -# -# slowr36 is a version of Reduce used just to compile the final version. -# It is larger and slower than the final release version, and will not have -# all the optional modules built into it. -# - -slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ - ../src/cslprolo.red ../src/module.red \ - ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ - ../src/alg.red ../src/arith.red ../src/mathpr.red \ - ../src/entry.red - $(WX) csl $(STORE) -o slowr36.img -v -z \ - ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log - -# -# A few targets here may help me tidy up my filespace from time to time -# - -cleansmall: $(SYMBOLIC) - -$(RM) slowr36.img - -clean: $(SYMBOLIC) - -$(RM) slowr36.img - -$(RM) r36 - -$(RM) fasl36.img - -$(RM) r36.img - -# -# demored is a demonstration version of Reduce with built-in resource -# limitations. -# - -demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ - stubs.o - $(CC) $(CFLAGS) $(C)/demo.c - $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) - $(STRIP) demored - -$(RM) demored.img - $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ - -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log - - -########################################################################### - - -csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ - $(C)/ccomp.lsp $(C)/extras.lsp - -$(RM) csl.img - $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ - -D@cslbase="$(C)" -- cslimg.log - - -csl: bytes.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) - $(STRIP) csl - -slowcsl: bytes1.o $(OBJS) \ - stubs.o - $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) - $(STRIP) slowcsl - - -# -# "make lispfile" -# recreates compiler.lsp, extras.lsp and ccomp.lsp from -# the corresponding master sources which are held in RLISP -# form. Temporarily builds an RLISP parser on the way. - -lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) - $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ - -D@cslbase="$(C)" -- lispfile.log - -signature: $(C)/version.hhh register.key $(SYMBOLIC) - filesign -u $(C)/version.hhh $(C)/version.h Developer or tester - -# -# Now rules for re-compiling the main collection of CSL source files. I -# write each case out individually since that makes the makefile less -# delicate than one that relies on setting up general rules - and I want this -# file to work on several different systems. -# - -$(ASMOBJDEP): $(C)/$(ASMSRC) - $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) - -arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith01.c - -arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith02.c - -arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith03.c - -arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith04.c - -arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/arith05.c - -arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith06.c - -arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith07.c - -arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith08.c - -arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith09.c - -arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith10.c - -arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/arith11.c - -arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/arith12.c - -bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes.c - -bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/bytes1.c - -# -# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that -# arranges that the number of GET operations performed and the associated -# indicators will be recorded, so that (bytecounts) will display statistics -# about it. This slows things down considerably, but can help when you are in -# the process of deciding which indicators are specified as "fast" ones. -# - -bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ - $(C)/bytes.h $(C)/arith.h - $(CC) $(CFLAGS) -DRECORD_GET=1 \ - $(C)/bytes1.c - -char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/char.c - -csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/csl.c - - - -eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval1.c - -eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval2.c - -eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/eval3.c - -eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/eval4.c - -fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/arith.h - $(CC) $(CFLAGS) \ - $(C)/fasl.c - -fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns1.c - -fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ - $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/fns2.c - -fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h - $(CC) $(CFLAGS) \ - $(C)/fns3.c - -gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/gc.c - -# -# For each major target I have one file that is system specific - eg -# sysdos.c, sysunix.c, ... -# - -$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ - $(C)/filename.c - $(CC) $(CFLAGS) \ - $(C)/$(SYS).c - -preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ - $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h - $(CC) $(CFLAGS) \ - $(C)/preserve.c - -print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/print.c - -read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h - $(CC) $(CFLAGS) \ - $(C)/read.c - -restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ - $(C)/arith.h $(C)/entries.h $(C)/stream.h - $(CC) $(CFLAGS) \ - $(C)/restart.c - -stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/stubs.c - -cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ - $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h - $(CC) $(CFLAGS) \ - $(C)/cslmpi.c - - -########################################################################### - -u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u01.c - -u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u02.c - -u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u03.c - -u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u04.c - -u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u05.c - -u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u06.c - -u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u07.c - -u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u08.c - -u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u09.c - -u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u10.c - -u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u11.c - -u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ - $(C)/cslerror.h $(C)/entries.h - $(CC) $(CFLAGS) \ - u12.c - -# -# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp -# I do not put in dependencies that cause this to happen automatically -# since experience shows that if I did it would happen (at significant -# expense) much too often. However when things alter in the Reduce -# source directory or when major changes are made to CSL this should be -# activated. -# - -# -# N.B. the step here used $(XSTORE) rather than $(STORE) because this -# build step may take more memory than any other. -# - -ccode: slowcsl slowr36.img $(SYMBOLIC) - $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log - -# -# Code to recreate the log files from the production version of the system. -# -# Note that for Windows benefit I use my own private output redirection with -# "--" rather than ">", since ">" seems incompatible with fully window -# applications, even when launched from the command line. Then to make this -# file consistent across platforms I use the same scheme all the time. -# - -log/algint.log: r36 r36.img ../xmpl/algint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log - -log/applysym.log: r36 r36.img ../xmpl/applysym.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log - -log/arnum.log: r36 r36.img ../xmpl/arnum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log - -log/assist.log: r36 r36.img ../xmpl/assist.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log - -log/avector.log: r36 r36.img ../xmpl/avector.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log - -log/boolean.log: r36 r36.img ../xmpl/boolean.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log - -log/cali.log: r36 r36.img ../xmpl/cali.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log - -log/camal.log: r36 r36.img ../xmpl/camal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log - -log/changevr.log: r36 r36.img ../xmpl/changevr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log - -log/compact.log: r36 r36.img ../xmpl/compact.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log - -log/complex.log: r36 r36.img ../xmpl/complex.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log - -log/crack.log: r36 r36.img ../xmpl/crack.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log - -log/cvit.log: r36 r36.img ../xmpl/cvit.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log - -log/decompos.log: r36 r36.img ../xmpl/decompos.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log - -log/defint.log: r36 r36.img ../xmpl/defint.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log - -log/desir.log: r36 r36.img ../xmpl/desir.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log - -log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log - -log/dummy.log: r36 r36.img ../xmpl/dummy.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log - -log/elem.log: r36 r36.img ../xmpl/elem.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log - -log/excalc.log: r36 r36.img ../xmpl/excalc.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log - -log/factor.log: r36 r36.img ../xmpl/factor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log - -log/fide.log: r36 r36.img ../xmpl/fide.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log - -log/fps.log: r36 r36.img ../xmpl/fps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log - -log/gcd.log: r36 r36.img ../xmpl/gcd.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log - -log/gentran.log: r36 r36.img ../xmpl/gentran.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log - -log/groebner.log: r36 r36.img ../xmpl/groebner.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log - -log/ideals.log: r36 r36.img ../xmpl/ideals.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log - -log/ineq.log: r36 r36.img ../xmpl/ineq.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log - -log/int.log: r36 r36.img ../xmpl/int.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log - -log/invbase.log: r36 r36.img ../xmpl/invbase.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log - -log/laplace.log: r36 r36.img ../xmpl/laplace.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log - -log/lie.log: r36 r36.img ../xmpl/lie.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log - -log/limits.log: r36 r36.img ../xmpl/limits.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log - -log/linalg.log: r36 r36.img ../xmpl/linalg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log - -log/math.log: r36 r36.img ../xmpl/math.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log - -log/matrix.log: r36 r36.img ../xmpl/matrix.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log - -log/modsr.log: r36 r36.img ../xmpl/modsr.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log - -log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log - -log/normform.log: r36 r36.img ../xmpl/normform.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log - -log/numeric.log: r36 r36.img ../xmpl/numeric.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log - -log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log - -log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log - -log/pf.log: r36 r36.img ../xmpl/pf.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log - -log/physop.log: r36 r36.img ../xmpl/physop.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log - -log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log - -log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log - -log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log - -log/reduce.log: r36 r36.img ../xmpl/reduce.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log - -log/residue.log: r36 r36.img ../xmpl/residue.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log - -log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log - -log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log - -log/roots.log: r36 r36.img ../xmpl/roots.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log - -log/rounded.log: r36 r36.img ../xmpl/rounded.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log - -log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log - -log/scope.log: r36 r36.img ../xmpl/scope.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log - -log/sets.log: r36 r36.img ../xmpl/sets.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log - -log/solve.log: r36 r36.img ../xmpl/solve.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log - -log/spde.log: r36 r36.img ../xmpl/spde.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log - -log/specfn.log: r36 r36.img ../xmpl/specfn.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log - -log/sum.log: r36 r36.img ../xmpl/sum.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log - -log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log - -log/taylor.log: r36 r36.img ../xmpl/taylor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log - -log/tps.log: r36 r36.img ../xmpl/tps.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log - -log/tri.log: r36 r36.img ../xmpl/tri.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log - -log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log - -log/wu.log: r36 r36.img ../xmpl/wu.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log - -log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log - -log/xideal.log: r36 r36.img ../xmpl/xideal.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log - -log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log - -log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst - $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log - -# end of makefile +########################################################################### +# # +# makefile for REDUCE 3.6 using CSL # +# # +########################################################################### + +# The following lines indicates the place on your disc where the "cslbase" +# directory exists. This is the place where the C sources files for CSL +# live. There are two versions here, the first should use Unix-like +# file name conventions (in particular "/" as a directory separator) while +# the second will (in some cases) be a host-specific translation. + +UCSLBASE = ../cslbase +CSLBASE = ../cslbase + + +########################################################################### + +# Sun Super SPARC, using the Sun C compiler. + +# I get conflicting reports about where to find the C compiler... +# please adjust this file by hand if you need to. +CC = /opt/EA/SUNWspro/bin/cc +SPARCOPTS = -xO5 -xdepend -dalign -xtarget=ultra1/170 -DLONG_LONG_64=1 -DMULDIV64=1 +SPARCLIBS = -lfast -lm +MPIFLAGS = +CFLAGS = -c $(SPARCOPTS) -DBSD_LIB=1 -I$(CSLBASE) $(MPIFLAGS) +LIBS = $(SPARCLIBS) -lcurses + +########################################################################### + +########################################################################### + +SHELL = /bin/sh +LINK = $(CC) +LFLAGS = +OUT = -o +OUTOBJ = -o +ASM = $(CC) +ASMFLAGS = $(CFLAGS) +ASMSRC = +ASMOBJ = +ASMOBJDEP = notused.obj +SYS = sysunix +STORE = -k8000 +XSTORE = -k8000 +RM = rm +MKDIR = mkdir +COPY = cp +STRIP = strip +WX = + +########################################################################### + + +########################################################################### +########################################################################### +# # +# This is the main bulk of the "makefile" for building Reduce 3.6 and CSL # +# on MSDOS, Windows and Unix. This part of the file expects a number of # +# symbols to have been defined: # +# # +# CSLBASE = file-path for CSLBASE directory # +# CC = The C compiler to use # +# CFLAGS = Flags for C compiler when compiling CSL # +# LINK = Linker to use # +# LFLAGS = Flags for linker # +# LIBS = Libraries to quote to linker # +# OUT = "-o" or "-out:" See link commands # +# OUTOBJ = "-o" often : where to put object code from C compilation # +# ASM = The assembler to use # +# ASMFLAGS = Flags for the assembler # +# ASMSRC = Assembly code source file to use # +# ASMOBJ = Object file for above (or NULL if no assembly used) # +# ASMOBJDEP = Ditto, but may not be NULL # +# SYS = name of system-specific file (sysdos or sysnt etc) # +# STORE = Memory option to pass to CSL (-k2500 is minimum) # +# XSTORE = Memory for the rebuild job that generates C code # +# RM = del for DOS, = rm for Unix # +# MKDIR = mkdir # +# COPY = copy for DOS, = cp for Unix # +# STRIP = echo for DOS, = strip for Unix # +# SYMBOLIC = .SYMBOLIC is using Watcom's "make" utility # +# WX = wx for Windows 3.1, null in all other cases # +# # +# The master version of this file is called "makebase" and is used to # +# create both DOS and Unix makefiles. Use the Codemist "makemake" # +# program to perform the conversion - eg # +# makemake -f makebase -o makemake.386 watcom dos # +# makemake -f makebase -o Makefile.sgi sgi # +# Just "makemake -f makebase" gives list of systems supported # +########################################################################### +########################################################################### + + + +########################################################################### +########################################################################### +# +# The main final target is r36.img, the image file for full REDUCE. +# If you want to rebuild stage-by-stage (eg while testing), try the +# sequence +# make csl compiles and links C coded kernel +# make csl.img builds compiler image on top of above +# make slowr36.img makes bootstrap REDUCE +# (roughly twice as slow as final one) +# only used for system recompilation. +# make ccode runs test file to collect statistics +# and create files u*.c and u*.lsp +# out of hot-spot parts of REDUCE. Note that +# >>>>>>>>>>>>>>>>>>> this is not done automatically by the main +# >>>> N. B. >>>> set of "make" dependences, since the +# >>>>>>>>>>>>>>>>>>> files u*.* provided are probably OK - but +# you need to do it again if the main REDUCE +# sources are altered +# make fasl36.img final compilation of most of REDUCE +# make r36 build final executable binary +# make r36.img build final image file +# make testall runs test files, output to log directory +# +########################################################################### +########################################################################### + + +# +# C is another name for CSLBASE, the directory that CSL source files live +# in. I introduce it here mainly because $(C) is so much more compact +# then $(CSLBASE). +# + +C = $(CSLBASE) + +# +# DOBJS is a list of all the object files that are common to all variants +# on the system built here +# + +DOBJS = arith01.o arith02.o arith03.o arith04.o \ + arith05.o arith06.o arith07.o arith08.o \ + arith09.o arith10.o arith11.o arith12.o \ + char.o csl.o cslmpi.o eval1.o eval2.o \ + eval3.o eval4.o fns1.o fns2.o fns3.o \ + print.o read.o restart.o $(ASMOBJ) \ + $(SYS).o + +CDOBJS = arith01.o,arith02.o,arith03.o,arith04.o,\ + arith05.o,arith06.o,arith07.o,arith08.o,\ + arith09.o,arith10.o,arith11.o,arith12.o,\ + char.o,csl.o,cslmpi.o,eval1.o,eval2.o,\ + eval3.o,eval4.o,fns1.o,fns2.o,fns3.o,\ + print.o,read.o,restart.o,$(ASMOBJ),\ + $(SYS).o + +# +# OBJS adds in the files used when I am not building a demonstration-mode CSL +# + +OBJS = $(DOBJS) fasl.o gc.o preserve.o + +COBJS = $(CDOBJS),fasl.o,gc.o,preserve.o + +# +# UOBJS come from that code that is compiled from Lisp into C +# + +UOBJS = u01.o u02.o u03.o u04.o u05.o \ + u06.o u07.o u08.o u09.o u10.o \ + u11.o u12.o + +CUOBJS = u01.o,u02.o,u03.o,u04.o,u05.o,\ + u06.o,u07.o,u08.o,u09.o,u10.o,\ + u11.o,u12.o + + +########################################################################### +########################################################################### +# +# "r36.img" is an image file for the main parts of Reduce + +r36.img: fasl36.img r36 + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + -$(MKDIR) log + +# "make patches" can be used after the "src/patches.red" file has changed + +patches: ../src/patches.red $(SYMBOLIC) + $(WX) r36 $(STORE) -v ../cslsrc/mkpatch.red -- mkpatch.log + $(WX) r36 $(STORE) -v -i- -o fasl36.img ../cslsrc/mkpatch1.red -- mkpatch1.log + $(WX) r36 $(STORE) -v -z -i fasl36.img -o- ../cslsrc/r36.lsp -- r36.log + + +# +# "make testall" tests the final production version of Reduce +# + +testall: log/algint.log log/applysym.log log/arnum.log log/assist.log log/avector.log \ + log/boolean.log log/cali.log log/camal.log log/changevr.log \ + log/compact.log log/complex.log log/crack.log log/cvit.log \ + log/decompos.log log/defint.log log/desir.log log/dfpart.log \ + log/dummy.log log/elem.log log/excalc.log log/factor.log \ + log/fide.log log/fps.log log/gcd.log log/gentran.log \ + log/groebner.log log/ideals.log log/ineq.log log/int.log \ + log/invbase.log log/laplace.log log/lie.log log/limits.log \ + log/linalg.log log/math.log log/matrix.log log/modsr.log \ + log/ncpoly.log log/normform.log log/numeric.log log/odesolve.log \ + log/orthovec.log log/pf.log log/physop.log log/pmrules.log \ + log/randpoly.log log/reacteqn.log log/reduce.log log/residue.log log/rlfi.log \ + log/rlisp88.log log/roots.log log/rounded.log log/rsolve.log \ + log/scope.log log/sets.log log/solve.log log/spde.log \ + log/specfn.log log/sum.log log/symmetry.log log/taylor.log \ + log/tps.log log/tri.log log/trigsimp.log log/wu.log log/xcolor.log log/xideal.log \ + log/zeilberg.log log/ztrans.log $(SYMBOLIC) + -echo all tests done + + + +########################################################################### +########################################################################### +# +# The targets from here on down are used in the process of doing a full +# system re-build + +# fasl36.img is a file needed during a re-build of Reduce. It contains +# compiled versions of all the Reduce modules. + +fasl36.img: csl slowr36.img + -$(RM) fasl36.img + $(WX) csl $(STORE) -v -i slowr36.img -o fasl36.img \ + ../cslsrc/fasl36.red -- fasl36.log + +# "make personal" downgrades a full version of Reduce to make a"personal" +# version (without the compiler). + +personal: r36 r36.img $(SYMBOLIC) + $(COPY) r36 ../r36 + $(COPY) r36.img ../r36.img + $(WX) ../r36 ../cslsrc/remcmp.lsp + +# "make rl" manufactures an image file that contains just an Rlisp parser + +rl: $(SYMBOLIC) rlisp rlisp.img + +rlisp: $(SYMBOLIC) csl + $(COPY) csl rlisp + +rlisp.img: rlisp + $(WX) rlisp $(STORE) -v -z -o rlisp.img \ + ../cslsrc/mkrlisp.lsp -D@cslbase="$(C)" -- rlisp.log + +# +# r36 can only be built when all the user-generated C code has been +# built. +# + +r36: bytes.o $(OBJS) \ + $(UOBJS) + $(LINK) $(LFLAGS) bytes.o $(OBJS) $(UOBJS) $(LIBS) $(OUT) r36 $(TAIL) + $(STRIP) r36 + +# +# slowr36 is a version of Reduce used just to compile the final version. +# It is larger and slower than the final release version, and will not have +# all the optional modules built into it. +# + +slowr36.img: csl ../cslsrc/slowr36.lsp ../src/boot.sl \ + ../src/cslprolo.red ../src/module.red \ + ../src/rlisp.red ../src/cslrend.red ../src/poly.red \ + ../src/alg.red ../src/arith.red ../src/mathpr.red \ + ../src/entry.red + $(WX) csl $(STORE) -o slowr36.img -v -z \ + ../cslsrc/slowr36.lsp -D@cslbase="$(C)" -- slowr36.log + +# +# A few targets here may help me tidy up my filespace from time to time +# + +cleansmall: $(SYMBOLIC) + -$(RM) slowr36.img + +clean: $(SYMBOLIC) + -$(RM) slowr36.img + -$(RM) r36 + -$(RM) fasl36.img + -$(RM) r36.img + +# +# demored is a demonstration version of Reduce with built-in resource +# limitations. +# + +demored: csl slowr36.img bytes.o $(DOBJS) $(SYMBOLIC) \ + stubs.o + $(CC) $(CFLAGS) $(C)/demo.c + $(LINK) $(LFLAGS) bytes.o $(DOBJS) stubs.obj demo.o $(LIBS) $(OUT) demored $(TAIL) + $(STRIP) demored + -$(RM) demored.img + $(WX) csl $(STORE) -i slowr36.img -v -z -i fasl36.img \ + -o demored.img ../cslsrc/makedemo.lsp -- makedemo.log + + +########################################################################### + + +csl.img: csl $(C)/compat.lsp $(C)/compiler.lsp \ + $(C)/ccomp.lsp $(C)/extras.lsp + -$(RM) csl.img + $(WX) csl $(STORE) -v -z $(C)/build0.lsp \ + -D@cslbase="$(C)" -- cslimg.log + + +csl: bytes.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes.o $(OBJS) stubs.o $(LIBS) $(OUT) csl $(TAIL) + $(STRIP) csl + +slowcsl: bytes1.o $(OBJS) \ + stubs.o + $(LINK) $(LFLAGS) bytes1.o $(OBJS) stubs.o $(LIBS) $(OUT) slowcsl $(TAIL) + $(STRIP) slowcsl + + +# +# "make lispfile" +# recreates compiler.lsp, extras.lsp and ccomp.lsp from +# the corresponding master sources which are held in RLISP +# form. Temporarily builds an RLISP parser on the way. + +lispfile: csl csl.img $(C)/lispfile.lsp $(SYMBOLIC) + $(WX) csl $(STORE) -v -z $(C)/lispfile.lsp \ + -D@cslbase="$(C)" -- lispfile.log + +signature: $(C)/version.hhh register.key $(SYMBOLIC) + filesign -u $(C)/version.hhh $(C)/version.h Developer or tester + +# +# Now rules for re-compiling the main collection of CSL source files. I +# write each case out individually since that makes the makefile less +# delicate than one that relies on setting up general rules - and I want this +# file to work on several different systems. +# + +$(ASMOBJDEP): $(C)/$(ASMSRC) + $(ASM) $(ASMFLAGS) $(C)/$(ASMSRC) + +arith01.o: $(C)/arith01.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith01.c + +arith02.o: $(C)/arith02.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith02.c + +arith03.o: $(C)/arith03.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith03.c + +arith04.o: $(C)/arith04.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith04.c + +arith05.o: $(C)/arith05.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/arith05.c + +arith06.o: $(C)/arith06.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith06.c + +arith07.o: $(C)/arith07.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith07.c + +arith08.o: $(C)/arith08.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith08.c + +arith09.o: $(C)/arith09.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith09.c + +arith10.o: $(C)/arith10.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith10.c + +arith11.o: $(C)/arith11.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/arith11.c + +arith12.o: $(C)/arith12.c $(C)/arith.h $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/arith12.c + +bytes.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes.c + +bytes1.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/bytes1.c + +# +# The target "bytes1a.o" recompiles bytes1.c, but with the flag set that +# arranges that the number of GET operations performed and the associated +# indicators will be recorded, so that (bytecounts) will display statistics +# about it. This slows things down considerably, but can help when you are in +# the process of deciding which indicators are specified as "fast" ones. +# + +bytes1a.o: $(C)/bytes1.c $(C)/bytes.c $(C)/tags.h $(C)/machine.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h \ + $(C)/bytes.h $(C)/arith.h + $(CC) $(CFLAGS) -DRECORD_GET=1 \ + $(C)/bytes1.c + +char.o: $(C)/char.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/char.c + +csl.o: $(C)/csl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h $(C)/version.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/csl.c + + + +eval1.o: $(C)/eval1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval1.c + +eval2.o: $(C)/eval2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval2.c + +eval3.o: $(C)/eval3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/eval3.c + +eval4.o: $(C)/eval4.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/eval4.c + +fasl.o: $(C)/fasl.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/arith.h + $(CC) $(CFLAGS) \ + $(C)/fasl.c + +fns1.o: $(C)/fns1.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns1.c + +fns2.o: $(C)/fns2.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h \ + $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/fns2.c + +fns3.o: $(C)/fns3.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/entries.h + $(CC) $(CFLAGS) \ + $(C)/fns3.c + +gc.o: $(C)/gc.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/gc.c + +# +# For each major target I have one file that is system specific - eg +# sysdos.c, sysunix.c, ... +# + +$(SYS).o: $(C)/$(SYS).c $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/fileops.c $(C)/scandir.c $(C)/version.h \ + $(C)/filename.c + $(CC) $(CFLAGS) \ + $(C)/$(SYS).c + +preserve.o: $(C)/preserve.c $(C)/tags.h $(C)/machine.h $(C)/stream.h \ + $(C)/externs.h $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h + $(CC) $(CFLAGS) \ + $(C)/preserve.c + +print.o: $(C)/print.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/print.c + +read.o: $(C)/read.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h $(C)/sockhdr.h + $(CC) $(CFLAGS) \ + $(C)/read.c + +restart.o: $(C)/restart.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/sys.h $(C)/cslerror.h $(C)/read.h $(C)/version.h \ + $(C)/arith.h $(C)/entries.h $(C)/stream.h + $(CC) $(CFLAGS) \ + $(C)/restart.c + +stubs.o: $(C)/stubs.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/stubs.c + +cslmpi.o: $(C)/cslmpi.c $(C)/machine.h $(C)/externs.h $(C)/sys.h \ + $(C)/mpipack.c $(C)/tags.h $(C)/cslerror.h + $(CC) $(CFLAGS) \ + $(C)/cslmpi.c + + +########################################################################### + +u01.o: u01.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u01.c + +u02.o: u02.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u02.c + +u03.o: u03.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u03.c + +u04.o: u04.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u04.c + +u05.o: u05.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u05.c + +u06.o: u06.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u06.c + +u07.o: u07.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u07.c + +u08.o: u08.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u08.c + +u09.o: u09.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u09.c + +u10.o: u10.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u10.c + +u11.o: u11.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u11.c + +u12.o: u12.c $(C)/tags.h $(C)/machine.h $(C)/externs.h \ + $(C)/cslerror.h $(C)/entries.h + $(CC) $(CFLAGS) \ + u12.c + +# +# "make ccode" re-manufactures u01.c to u12.c and u01.lsp to u12.lsp +# I do not put in dependencies that cause this to happen automatically +# since experience shows that if I did it would happen (at significant +# expense) much too often. However when things alter in the Reduce +# source directory or when major changes are made to CSL this should be +# activated. +# + +# +# N.B. the step here used $(XSTORE) rather than $(STORE) because this +# build step may take more memory than any other. +# + +ccode: slowcsl slowr36.img $(SYMBOLIC) + $(WX) slowcsl $(XSTORE) -i slowr36.img -v ../cslsrc/select36.red -- select36.log + +# +# Code to recreate the log files from the production version of the system. +# +# Note that for Windows benefit I use my own private output redirection with +# "--" rather than ">", since ">" seems incompatible with fully window +# applications, even when launched from the command line. Then to make this +# file consistent across platforms I use the same scheme all the time. +# + +log/algint.log: r36 r36.img ../xmpl/algint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log + +log/applysym.log: r36 r36.img ../xmpl/applysym.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log + +log/arnum.log: r36 r36.img ../xmpl/arnum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log + +log/assist.log: r36 r36.img ../xmpl/assist.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log + +log/avector.log: r36 r36.img ../xmpl/avector.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log + +log/boolean.log: r36 r36.img ../xmpl/boolean.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log + +log/cali.log: r36 r36.img ../xmpl/cali.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log + +log/camal.log: r36 r36.img ../xmpl/camal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log + +log/changevr.log: r36 r36.img ../xmpl/changevr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log + +log/compact.log: r36 r36.img ../xmpl/compact.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log + +log/complex.log: r36 r36.img ../xmpl/complex.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log + +log/crack.log: r36 r36.img ../xmpl/crack.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log + +log/cvit.log: r36 r36.img ../xmpl/cvit.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log + +log/decompos.log: r36 r36.img ../xmpl/decompos.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log + +log/defint.log: r36 r36.img ../xmpl/defint.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log + +log/desir.log: r36 r36.img ../xmpl/desir.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log + +log/dfpart.log: r36 r36.img ../xmpl/dfpart.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log + +log/dummy.log: r36 r36.img ../xmpl/dummy.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log + +log/elem.log: r36 r36.img ../xmpl/elem.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log + +log/excalc.log: r36 r36.img ../xmpl/excalc.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log + +log/factor.log: r36 r36.img ../xmpl/factor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log + +log/fide.log: r36 r36.img ../xmpl/fide.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log + +log/fps.log: r36 r36.img ../xmpl/fps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log + +log/gcd.log: r36 r36.img ../xmpl/gcd.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log + +log/gentran.log: r36 r36.img ../xmpl/gentran.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log + +log/groebner.log: r36 r36.img ../xmpl/groebner.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log + +log/ideals.log: r36 r36.img ../xmpl/ideals.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log + +log/ineq.log: r36 r36.img ../xmpl/ineq.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log + +log/int.log: r36 r36.img ../xmpl/int.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=int -- log/int.log + +log/invbase.log: r36 r36.img ../xmpl/invbase.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log + +log/laplace.log: r36 r36.img ../xmpl/laplace.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log + +log/lie.log: r36 r36.img ../xmpl/lie.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log + +log/limits.log: r36 r36.img ../xmpl/limits.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log + +log/linalg.log: r36 r36.img ../xmpl/linalg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log + +log/math.log: r36 r36.img ../xmpl/math.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=math -- log/math.log + +log/matrix.log: r36 r36.img ../xmpl/matrix.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log + +log/modsr.log: r36 r36.img ../xmpl/modsr.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log + +log/ncpoly.log: r36 r36.img ../xmpl/ncpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log + +log/normform.log: r36 r36.img ../xmpl/normform.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log + +log/numeric.log: r36 r36.img ../xmpl/numeric.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log + +log/odesolve.log: r36 r36.img ../xmpl/odesolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log + +log/orthovec.log: r36 r36.img ../xmpl/orthovec.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log + +log/pf.log: r36 r36.img ../xmpl/pf.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log + +log/physop.log: r36 r36.img ../xmpl/physop.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log + +log/pmrules.log: r36 r36.img ../xmpl/pmrules.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log + +log/randpoly.log: r36 r36.img ../xmpl/randpoly.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log + +log/reacteqn.log: r36 r36.img ../xmpl/reacteqn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log + +log/reduce.log: r36 r36.img ../xmpl/reduce.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log + +log/residue.log: r36 r36.img ../xmpl/residue.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log + +log/rlfi.log: r36 r36.img ../xmpl/rlfi.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log + +log/rlisp88.log: r36 r36.img ../xmpl/rlisp88.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log + +log/roots.log: r36 r36.img ../xmpl/roots.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log + +log/rounded.log: r36 r36.img ../xmpl/rounded.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log + +log/rsolve.log: r36 r36.img ../xmpl/rsolve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log + +log/scope.log: r36 r36.img ../xmpl/scope.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log + +log/sets.log: r36 r36.img ../xmpl/sets.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log + +log/solve.log: r36 r36.img ../xmpl/solve.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log + +log/spde.log: r36 r36.img ../xmpl/spde.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log + +log/specfn.log: r36 r36.img ../xmpl/specfn.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log + +log/sum.log: r36 r36.img ../xmpl/sum.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log + +log/symmetry.log: r36 r36.img ../xmpl/symmetry.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log + +log/taylor.log: r36 r36.img ../xmpl/taylor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log + +log/tps.log: r36 r36.img ../xmpl/tps.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log + +log/tri.log: r36 r36.img ../xmpl/tri.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log + +log/trigsimp.log: r36 r36.img ../xmpl/trigsimp.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log + +log/wu.log: r36 r36.img ../xmpl/wu.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log + +log/xcolor.log: r36 r36.img ../xmpl/xcolor.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log + +log/xideal.log: r36 r36.img ../xmpl/xideal.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log + +log/zeilberg.log: r36 r36.img ../xmpl/zeilberg.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log + +log/ztrans.log: r36 r36.img ../xmpl/ztrans.tst + $(WX) r36 $(STORE) -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log + +# end of makefile Index: r36/cslsrc/gnuplot.tst ================================================================== --- r36/cslsrc/gnuplot.tst +++ r36/cslsrc/gnuplot.tst @@ -1,46 +1,46 @@ - -plot(sin x,x=(-3 .. 3)); -plot(s=sin phi,phi=(-3 .. 3)); -plot(sin phi,cos phi,phi=(-3 .. 3)); -plot(sin(1/x),x=(-1 .. 1),y=(-3 .. 3)); -plot(sin(1/x),x=(-10 .. 10)); -plot(y=tan x,y=(-10 .. 10)); - - -plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3)); -plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3),hidden3d); -plot(x*y, x=(0 .. 2), y=(0 .. 2)); -plot(x*y, x=(-2 .. 2), y=(-2 .. 2)); -plot(x+y, x=(0 .. 2), y=(0 .. 2)); -plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5)); -plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5),hidden3d); -plot(1/(x**2+y**2),x=(0.1 .. 5),y=(0.1 .. 5),size="0.7,1"); -plot(1/(x**2+y**2),x=(0.1 .. 5),y=(0.1 .. 5),view="30,89"); -plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5), - hidden3d,contour,view="70,20"); - -plot(sinh(x*y)/sinh(2*x*y),hidden3d); - -% general curves and surfaces computed as lists of data points - -plot {{0,0},{0,1},{1,1},{0,0},{1,0},{0,1},{0.5,1.5},{1,1},{1,0}}; -on rounded; -w:=for j:=1:200 collect {1/j*sin j,1/j*cos j,j/200}$ -plot w; - -w:= {for j:=1 step 0.1 until 20 collect - {1/j*sin j,1/j*cos j,j}, - for j:=1 step 0.1 until 20 collect - {(0.1+1/j)*sin j,(0.1+1/j)*cos j,j} - }$ -plot w; - -dd:=pi/15; - -w:=for u:=dd step dd until pi-dd collect - for v:=0 step dd until 2pi collect - {sin(u)*cos(v), sin(u)*sin(v), cos(u)}$ - -plot w; - -end; + +plot(sin x,x=(-3 .. 3)); +plot(s=sin phi,phi=(-3 .. 3)); +plot(sin phi,cos phi,phi=(-3 .. 3)); +plot(sin(1/x),x=(-1 .. 1),y=(-3 .. 3)); +plot(sin(1/x),x=(-10 .. 10)); +plot(y=tan x,y=(-10 .. 10)); + + +plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3)); +plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3),hidden3d); +plot(x*y, x=(0 .. 2), y=(0 .. 2)); +plot(x*y, x=(-2 .. 2), y=(-2 .. 2)); +plot(x+y, x=(0 .. 2), y=(0 .. 2)); +plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5)); +plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5),hidden3d); +plot(1/(x**2+y**2),x=(0.1 .. 5),y=(0.1 .. 5),size="0.7,1"); +plot(1/(x**2+y**2),x=(0.1 .. 5),y=(0.1 .. 5),view="30,89"); +plot(1/(x**2+y**2),x=(-0.5 .. 0.5),y=(-0.5 .. 0.5), + hidden3d,contour,view="70,20"); + +plot(sinh(x*y)/sinh(2*x*y),hidden3d); + +% general curves and surfaces computed as lists of data points + +plot {{0,0},{0,1},{1,1},{0,0},{1,0},{0,1},{0.5,1.5},{1,1},{1,0}}; +on rounded; +w:=for j:=1:200 collect {1/j*sin j,1/j*cos j,j/200}$ +plot w; + +w:= {for j:=1 step 0.1 until 20 collect + {1/j*sin j,1/j*cos j,j}, + for j:=1 step 0.1 until 20 collect + {(0.1+1/j)*sin j,(0.1+1/j)*cos j,j} + }$ +plot w; + +dd:=pi/15; + +w:=for u:=dd step dd until pi-dd collect + for v:=0 step dd until 2pi collect + {sin(u)*cos(v), sin(u)*sin(v), cos(u)}$ + +plot w; + +end; Index: r36/cslsrc/testall.unx ================================================================== --- r36/cslsrc/testall.unx +++ r36/cslsrc/testall.unx @@ -1,72 +1,72 @@ -mkdir log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=int -- log/int.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=math -- log/math.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log -r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log -echo all tests done +mkdir log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=algint -Dloadup=algint -- log/algint.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=applysym -Dloadup=applysym -- log/applysym.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=arnum -Dloadup=arnum -- log/arnum.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=assist -Dloadup=assist -- log/assist.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=avector -Dloadup=avector -- log/avector.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=boolean -Dloadup=boolean -- log/boolean.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=cali -Dloadup=cali -- log/cali.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=camal -Dloadup=camal -- log/camal.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=changevr -Dloadup=changevr -- log/changevr.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=compact -Dloadup=compact -- log/compact.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=complex -- log/complex.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=crack -Dloadup=crack -- log/crack.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=cvit -Dloadup=cvit -- log/cvit.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=decompos -- log/decompos.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=defint -Dloadup=defint -- log/defint.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=desir -Dloadup=desir -- log/desir.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=dfpart -Dloadup=dfpart -- log/dfpart.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=dummy -Dloadup=dummy -- log/dummy.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=elem -- log/elem.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=excalc -Dloadup=excalc -- log/excalc.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=factor -- log/factor.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=fide -Dloadup=fide -- log/fide.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=fps -Dloadup=fps -- log/fps.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=gcd -- log/gcd.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=gentran -Dloadup=gentran -- log/gentran.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=groebner -Dloadup=groebner -- log/groebner.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ideals -Dloadup=ideals -- log/ideals.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ineq -Dloadup=ineq -- log/ineq.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=int -- log/int.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=invbase -Dloadup=invbase -- log/invbase.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=laplace -Dloadup=laplace -- log/laplace.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=lie -Dloadup=lie -- log/lie.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=limits -- log/limits.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=linalg -Dloadup=linalg -- log/linalg.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=math -- log/math.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=matrix -- log/matrix.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=modsr -Dloadup=modsr -- log/modsr.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ncpoly -Dloadup=ncpoly -- log/ncpoly.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=normform -Dloadup=normform -- log/normform.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=numeric -Dloadup=numeric -- log/numeric.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=odesolve -Dloadup=odesolve -- log/odesolve.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=orthovec -Dloadup=orthovec -- log/orthovec.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=pf -- log/pf.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=physop -Dloadup=physop -- log/physop.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=pmrules -Dloadup=pmrules -- log/pmrules.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=randpoly -Dloadup=randpoly -- log/randpoly.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=reacteqn -Dloadup=reacteqn -- log/reacteqn.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=reduce -- log/reduce.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=residue -Dloadup=residue -- log/residue.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rlfi -Dloadup=rlfi -- log/rlfi.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rlisp88 -- log/rlisp88.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=roots -- log/roots.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rounded -- log/rounded.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=rsolve -Dloadup=rsolve -- log/rsolve.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=scope -Dloadup=scope -- log/scope.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=sets -Dloadup=sets -- log/sets.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=solve -- log/solve.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=spde -Dloadup=spde -- log/spde.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=specfn -Dloadup=specfn -- log/specfn.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=sum -- log/sum.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=symmetry -Dloadup=symmetry -- log/symmetry.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=taylor -Dloadup=taylor -- log/taylor.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=tps -Dloadup=tps -- log/tps.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=tri -Dloadup=tri -- log/tri.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=trigsimp -Dloadup=trigsimp -- log/trigsimp.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=wu -Dloadup=wu -- log/wu.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=xcolor -Dloadup=xcolor -- log/xcolor.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=xideal -Dloadup=xideal -- log/xideal.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=zeilberg -Dloadup=zeilberg -- log/zeilberg.log +r36 -k6000 -b ../cslsrc/ndotest.red -Dname=ztrans -Dloadup=ztrans -- log/ztrans.log +echo all tests done Index: r36/doc/APPLYSYM.TEX ================================================================== --- r36/doc/APPLYSYM.TEX +++ r36/doc/APPLYSYM.TEX @@ -1,1194 +1,1194 @@ -% This is a LaTeX file -\documentstyle[12pt]{article} - -%Sets size of page and margins -\oddsidemargin 10mm \evensidemargin 10mm -\topmargin 0pt \headheight 0pt \headsep 0pt -\footheight 14pt \footskip 40pt -\textheight 23cm \textwidth 15cm -%\textheight 15cm \textwidth 10cm - -%spaces lines at one and a half spacing -%\def\baselinestretch{1.5} - -%\parskip = \baselineskip - -%Defines capital R for the reals, ... -%\font\Edth=msym10 -%\def\Integer{\hbox{\Edth Z}} -%\def\Rational{\hbox{\Edth Q}} -%\def\Real{\hbox{\Edth R}} -%\def\Complex{\hbox{\Edth C}} - -\title{Programs for Applying Symmetries of PDEs} -\author{Thomas Wolf \\ - School of Mathematical Sciences \\ - Queen Mary and Westfield College \\ - University of London \\ - London E1 4NS \\ - T.Wolf@maths.qmw.ac.uk -} - -\begin{document} -\maketitle -\begin{abstract} -In this paper the programs {\tt APPLYSYM}, {\tt QUASILINPDE} and -{\tt DETRAFO} are described which aim at the utilization -of infinitesimal symmetries of differential equations. The purpose -of {\tt QUASILINPDE} is the general solution of -quasilinear PDEs. This procedure is used by {\tt APPLYSYM} -for the application of point symmetries for either -\begin{itemize} -\item calculating similarity variables to perform a point transformation -which lowers the order of an ODE or effectively reduces the number of -explicitly occuring independent variables in a PDE(-system) or for -\item generalizing given special solutions of ODEs/PDEs with new constant -parameters. -\end{itemize} - -The program {\tt DETRAFO} performs arbitrary point- and contact -transformations of ODEs/PDEs and is applied if similarity -and symmetry variables have been found. -The program {\tt APPLYSYM} is used in connection with the program -{\tt LIEPDE} for formulating and solving the conditions for point- and -contact symmetries which is described in \cite{LIEPDE}. -The actual problem solving is done in all these programs through a call -to the package {\tt CRACK} for solving overdetermined PDE-systems. -\end{abstract} - -\tableofcontents -%------------------------------------------------------------------------- -\section{Introduction and overview of the symmetry method} -The investigation of infinitesimal symmetries of differential equations -(DEs) with computer algebra programs attrackted considerable attention -over the last years. Corresponding programs are available in all -major computer algebra systems. In a review article by W.\ Hereman -\cite{WHer} about 200 references are given, many of them describing related -software. - -One reason for the popularity of the symmetry method -is the fact that Sophus Lie's method -\cite{lie1},\cite{lie2} is the most widely -used method for computing exact solutions of non-linear DEs. Another reason is -that the first step in this -method, the formulation of the determining equation for the generators -of the symmetries, can already be very cumbersome, especially in the -case of PDEs of higher order and/or in case of many dependent and independent -variables. Also, the formulation of the conditions is a straight forward -task involving only differentiations and basic algebra - an ideal task for -computer algebra systems. Less straight forward is the automatic solution -of the symmetry conditions which is the strength of the program {\tt LIEPDE} -(for a comparison with another program see \cite{LIEPDE}). - -The novelty described in this paper are programs aiming at -the final third step: Applying symmetries for -\begin{itemize} -\item calculating similarity variables to perform a point transformation -which lowers the order of an ODE or effectively reduces the number of -explicitly occuring independent variables of a PDE(-system) or for -\item generalizing given special solutions of ODEs/PDEs with new constant -parameters. -\end{itemize} -Programs which run on their own but also allow interactive user control -are indispensible for these calculations. On one hand the calculations can -become quite lengthy, like variable transformations of PDEs (of higher order, -with many variables). On the other hand the freedom of choosing the right -linear combination of symmetries and choosing the optimal new symmetry- and -similarity variables makes it necessary to `play' with the problem -interactively. - -The focus in this paper is directed on questions of implementation and -efficiency, no principally new mathematics is presented. - -In the following subsections a review of the first two steps of the symmetry -method is given as well as the third, i.e.\ the application step is outlined. -Each of the remaining sections is devoted to one procedure. -%--------------------------------------- -\subsection{The first step: Formulating the symmetry conditions} - -To obey classical Lie-symmetries, differential equations -\begin{equation} -H_A = 0 \label{PDEs} -\end{equation} -for unknown functions $y^\alpha,\;\;1\leq \alpha \leq p$ -of independent variables $x^i,\;\;1\leq i \leq q$ -must be forminvariant against infinitesimal transformations -\begin{equation} -\tilde{x}^i = x^i + \varepsilon \xi^i, \;\; \;\;\; - \tilde{y}^\alpha = y^\alpha + \varepsilon \eta^\alpha \label{tran} -\end{equation} -in first order of $\varepsilon.$ To transform the equations (\ref{PDEs}) -by (\ref{tran}), derivatives of $y^\alpha$ must be transformed, i.e. the part -linear in $\varepsilon$ must be determined. The corresponding formulas are -(see e.g. \cite{Olv}, \cite{Step}) -\begin{eqnarray} -\tilde{y}^\alpha_{j_1\ldots j_k} & = & -y^\alpha_{j_1\ldots j_k} + \varepsilon -\eta^\alpha_{j_1\ldots j_k} + O(\varepsilon^2) \nonumber \\ \vspace{3mm} -\eta^\alpha_{j_1\ldots j_{k-1}j_k} & = & - \frac{D \eta^\alpha_{j_1\ldots j_{k-1}}}{D x^k} - - y^\alpha_{ij_1\ldots j_{k-1}}\frac{D \xi^i}{D x^k} \label{recur} -\end{eqnarray} -where $D/Dx^k$ means total differentiation w.r.t.\ $x^k$ and -from now on lower latin indices of functions $y^\alpha,$ -(and later $u^\alpha$) -denote partial differentiation w.r.t.\ the independent variables $x^i,$ -(and later $v^i$). -The complete symmetry condition then takes the form -\begin{eqnarray} -X H_A & = & 0 \;\; \; \; \mbox{mod} \; \; \; H_A = 0\ \label{sbed1} \\ -X & = & \xi^i \frac{\partial}{\partial x^i} + - \eta^\alpha \frac{\partial}{\partial y^\alpha} + - \eta^\alpha_m \frac{\partial}{\partial y^\alpha_m} + - \eta^\alpha_{mn} \frac{\partial}{\partial y^\alpha_{mn}} + \ldots + - \eta^\alpha_{mn\ldots p} \frac{\partial}{\partial y^\alpha_{mn\ldots p}}. -\label{sbed2} -\end{eqnarray} -where mod $H_A = 0$ means that the original PDE-system is used to replace -some partial derivatives of $y^\alpha$ to reduce the number of independent -variables, because the symmetry condition (\ref{sbed1}) must be -fulfilled identically in $x^i, y^\alpha$ and all partial -derivatives of $y^\alpha.$ - -For point symmetries, $\xi^i, \eta^\alpha$ are functions of $x^j, -y^\beta$ and for contact symmetries they depend on $x^j, y^\beta$ and -$y^\beta_k.$ We restrict ourself to point symmetries as those are the only -ones that can be applied by the current version of the program {\tt APPLYSYM} -(see below). For literature about generalized symmetries see \cite{WHer}. - -Though the formulation of the symmetry conditions (\ref{sbed1}), -(\ref{sbed2}), (\ref{recur}) -is straightforward and handled in principle by all related -programs \cite{WHer}, the computational effort to formulate -the conditions (\ref{sbed1}) may cause problems if -the number of $x^i$ and $y^\alpha$ is high. This can -partially be avoided if at first only a few conditions are formulated -and solved such that the remaining ones are much shorter and quicker to -formulate. - -A first step in this direction is to investigate one PDE $H_A = 0$ -after another, as done in \cite{Cham}. Two methods to partition the -conditions for a single PDE are described by Bocharov/Bronstein -\cite{Alex} and Stephani \cite{Step}. - -In the first method only those terms of the symmetry condition -$X H_A = 0$ are calculated which contain -at least a derivative of $y^\alpha$ of a minimal order $m.$ -Setting coefficients -of these $u$-derivatives to zero provides symmetry conditions. Lowering the -minimal order $m$ successively then gradually provides all symmetry conditions. - -The second method is even more selective. If $H_A$ is of order $n$ -then only terms of the symmetry condition $X H_A = 0$ are generated which -contain $n'$th order derivatives of $y^\alpha.$ Furthermore these derivatives -must not occur in $H_A$ itself. They can therefore occur -in the symmetry condition -(\ref{sbed1}) only in -$\eta^\alpha_{j_1\ldots j_n},$ i.e. in the terms -\[\eta^\alpha_{j_1\ldots j_n} -\frac{\partial H_A}{\partial y^\alpha_{j_1\ldots j_n}}. \] -If only coefficients of $n'$th order derivatives of $y^\alpha$ need to be -accurate to formulate preliminary conditions -then from the total derivatives to be taken in -(\ref{recur}) only that part is performed which differentiates w.r.t.\ the -highest $y^\alpha$-derivatives. -This means, for example, to form only -$y^\alpha_{mnk} \partial/\partial y^\alpha_{mn} $ -if the expression, which is to be differentiated totally w.r.t.\ $x^k$, -contains at most second order derivatives of $y^\alpha.$ - -The second method is applied in {\tt LIEPDE}. -Already the formulation of the remaining conditions is speeded up -considerably through this iteration process. These methods can be applied if -systems of DEs or single PDEs of at least second order are investigated -concerning symmetries. -%--------------------------------------- -\subsection{The second step: Solving the symmetry conditions} -The second step in applying the whole method consists in solving the -determining conditions (\ref{sbed1}), (\ref{sbed2}), (\ref{recur}) -which are linear homogeneous PDEs for $\xi^i, \eta^\alpha$. The -complete solution of this system is not algorithmic any more because the -solution of a general linear PDE-system is as difficult as the solution of -its non-linear characteristic ODE-system which is not covered by algorithms -so far. - -Still algorithms are used successfully to simplify the PDE-system by -calculating -its standard normal form and by integrating exact PDEs -if they turn up in this simplification process \cite{LIEPDE}. -One problem in this respect, for example, -concerns the optimization of the symbiosis of both algorithms. By that we -mean the ranking of priorities between integrating, adding integrability -conditions and doing simplifications by substitutions - all depending on -the length of expressions and the overall structure of the PDE-system. -Also the extension of the class of PDEs which can be integrated exactly is -a problem to be pursuit further. - -The program {\tt LIEPDE} which formulates the symmetry conditions calls the -program {\tt CRACK} to solve them. This is done in a number of successive -calls in order to formulate and solve some first order PDEs of the -overdetermined system first and use their solution to formulate and solve the -next subset of conditions as described in the previous subsection. -Also, {\tt LIEPDE} can work on DEs that contain parametric constants and -parametric functions. An ansatz for the symmetry generators can be -formulated. For more details see \cite{LIEPDE} or \cite{WoBra}. - - -The call of {\tt LIEPDE} is \\ -{\tt LIEPDE}(\{{\it de}, {\it fun}, {\it var}\}, -\{{\it od}, {\it lp}, {\it fl}\}); \\ -where -\begin{itemize} -\item {\it de} is a single DE or a list of DEs in the form of a vanishing - expression or in the form $\ldots=\ldots\;\;$. -\item {\it fun} is the single function or the list of functions occuring - in {\it de}. -\item {\it var} is the single variable or the list of variables in {\it de}. -\item {\it od} is the order of the ansatz for $\xi, \eta.$ It is = 0 for -point symmetries and = 1 for contact symmetries (accepted by -{\tt LIEPDE} only in case of one ODE/PDE for one unknown function). -% and $>1$ for dynamical symmetries -%(only in case of one ODE for one unknown function) -\item If {\it lp} is $nil$ then the standard ansatz for $\xi^i, \eta^\alpha$ -is taken which is - \begin{itemize} - \item for point symmetries ({\it od} =0) is $\xi^i = \xi^i(x^j,y^\beta), - \eta^\alpha = \eta^\alpha(x^j,y^\beta)$ - \item for contact symmetries ({\it od} =1) is - $ \xi^i := \Omega_{u_i}, \;\;\; - \eta := u_i\Omega_{u_i} \; - \; \Omega, $ \\ - $\Omega:=\Omega(x^i, u, u_j)$ -%\item for dynamical symmetries ({\it od}$>1$) \\ -% $ \xi := \Omega,_{u'}, \;\;\; -% \eta := u'\Omega,_{u'} \; - \; \Omega, \;\;\; -% \Omega:=\Omega(x, u, u',\ldots, y^{({\it od}-1)})$ -% where {\it od} must be less than the order of the ODE. - \end{itemize} - - If {\it lp} is not $nil$ then {\it lp} is the ansatz for - $\xi^i, \eta^\alpha$ and must have the form - \begin{itemize} - \item for point symmetries - {\tt \{xi\_\mbox{$x1$} = ..., ..., eta\_\mbox{$u1$} = ..., ...\}} - where {\tt xi\_, eta\_ } - are fixed and $x1, \ldots, u1$ are to be replaced by the actual names - of the variables and functions. - \item otherwise {\tt spot\_ = ...} where the expression on the right hand - side is the ansatz for the Symmetry-POTential $\Omega.$ - \end{itemize} - -\item {\it fl} is the list of free functions in the ansatz -in case {\it lp} is not $nil.$ -\end{itemize} - - -The result of {\tt LIEPDE} is a list with 3 elements, each of which -is a list: -\[ \{\{{\it con}_1,{\it con}_2,\ldots\}, - \{{\tt xi}\__{\ldots}=\ldots, \ldots, - {\tt eta}\__{\ldots}=\ldots, \ldots\}, - \{{\it flist}\}\}. \] -The first list contains remaining unsolved symmetry conditions {\it con}$_i$. It -is the empty list \{\} if all conditions have been solved. The second list -gives the symmetry generators, i.e.\ expressions for $\xi_i$ and $\eta_j$. The -last list contains all free constants and functions occuring in the first -and second list. - -%That the automatic calculation of symmetries run in most practical cases -%is shown with the following example. It is insofar difficult, as many -%symmetries exist and the solution consequently more difficult is to deriv. -% -%--------------------------------------- -%\subsection{Example} -%For the following PDE-system, which takes its simplest form in the -%formalism of exterior forms: -% -%\begin{eqnarray*} -%0 & = & 3k_t,_{tt}-2k_t,_{xx}-2k_t,_{yy}-2k_t,_{zz}-k_x,_{tx}-2k_zk_x,_y \\ -% & & +2k_yk_x,_z-k_y,_{ty}+2k_zk_y,_x-2k_xk_y,_z-k_z,_{tz}-2k_yk_z,_x+2k_xk_z,_y \\ -%0 & = & k_t,_{tx}-2k_zk_t,_y+2k_yk_t,_z+2k_x,_{tt}-3k_x,_{xx}-2k_x,_{yy} \\ -% & & -2k_x,_{zz}+2k_zk_y,_t-k_y,_{xy}-2k_tk_y,_z-2k_yk_z,_t-k_z,_{xz}+2k_tk_z,_y \\ -%0 & = & k_t,_{ty}+2k_zk_t,_x-2k_xk_t,_z-2k_zk_x,_t-k_x,_{xy}+2k_tk_x,_z \\ -% & & +2k_y,_{tt}-2k_y,_{xx}-3k_y,_{yy}-2k_y,_{zz}+2k_xk_z,_t-2k_tk_z,_x-k_z,_{yz} \\ -%0 & = & k_t,_{tz}-2k_yk_t,_x+2k_xk_t,_y+2k_yk_x,_t-k_x,_{xz}-2k_tk_x,_y \\ -% & & -2k_xk_y,_t+2k_tk_y,_x-k_y,_{yz}+2k_z,_{tt}-2k_z,_{xx}-2k_z,_{yy}-3k_z,_{zz} -%\end{eqnarray*} -%--------------------------------------- -\subsection{The third step: Application of infinitesimal symmetries} -If infinitesimal symmetries have been found then -the program {\tt APPLYSYM} can use them for the following purposes: -\begin{enumerate} -\item Calculation of one symmetry variable and further similarity variables. -After transforming -the DE(-system) to these variables, the symmetry variable will not occur -explicitly any more. For ODEs this has the consequence that their order has -effectively been reduced. -\item Generalization of a special solution by one or more constants of -integration. -\end{enumerate} -Both methods are described in the following section. -%------------------------------------------------------------------------- -\section{Applying symmetries with {\tt APPLYSYM}} -%--------------------------------------- -\subsection{The first mode: Calculation of similarity and symmetry variables} -In the following we assume that a symmetry generator $X$, given -in (\ref{sbed2}), is known such that ODE(s)/PDE(s) $H_A=0$ -satisfy the symmetry condition (\ref{sbed1}). The aim is to -find new dependent functions $u^\alpha = u^\alpha(x^j,y^\beta)$ and -new independent variables $v^i = v^i(x^j,y^\beta),\;\; -1\leq\alpha,\beta\leq p,\;1\leq i,j \leq q$ -such that the symmetry generator -$X = \xi^i(x^j,y^\beta)\partial_{x^i} + - \eta^\alpha(x^j,y^\beta)\partial_{y^\alpha}$ -transforms to -\begin{equation} -X = \partial_{v^1}. \label{sbed3} -\end{equation} - -Inverting the above transformation to $x^i=x^i(v^j,u^\beta), -y^\alpha=y^\alpha(v^j,u^\beta)$ and setting -$H_A(x^i(v^j,u^\beta), y^\alpha(v^j,u^\beta),\ldots) = -h_A(v^j, u^\beta,\ldots)$ -this means that -\begin{eqnarray*} - 0 & = & X H_A(x^i,y^\alpha,y^\beta_j,\ldots)\;\;\; \mbox{mod} \;\;\; H_A=0 \\ - & = & X h_A(v^i,u^\alpha,u^\beta_j,\ldots)\;\;\; \mbox{mod} \;\;\; h_A=0 \\ - & = & \partial_{v^1}h_A(v^i,u^\alpha,u^\beta_j,\ldots)\;\;\; \mbox{mod} - \;\;\; h_A=0. -\end{eqnarray*} -Consequently, the variable $v^1$ does not occur explicitly in $h_A$. -In the case of an ODE(-system) $(v^1=v)$ -the new equations $0=h_A(v,u^\alpha,du^\beta/dv,\ldots)$ -are then of lower total order -after the transformation $z = z(u^1) = du^1/dv$ with now $z, u^2,\ldots u^p$ -as unknown functions and $u^1$ as independent variable. - -The new form (\ref{sbed3}) of $X$ leads directly to conditions for the -symmetry variable $v^1$ and the similarity variables -$v^i|_{i\neq 1}, u^\alpha$ (all functions of $x^k,y^\gamma$): -\begin{eqnarray} - X v^1 = 1 & = & \xi^i(x^k,y^\gamma)\partial_{x^i}v^1 + - \eta^\alpha(x^k,y^\gamma)\partial_{y^\alpha}v^1 \label{ql1} \\ - X v^j|_{j\neq 1} = X u^\beta = 0 & = & - \xi^i(x^k,y^\gamma)\partial_{x^i}u^\beta + - \eta^\alpha(x^k,y^\gamma)\partial_{y^\alpha}u^\beta \label{ql2} -\end{eqnarray} -The general solutions of (\ref{ql1}), (\ref{ql2}) involve free functions -of $p+q-1$ arguments. From the general solution of equation (\ref{ql2}), -$p+q-1$ functionally independent special solutions have to be selected -($v^2,\ldots,v^p$ and $u^1,\ldots,u^q$), -whereas from (\ref{ql1}) only one solution $v^1$ is needed. -Together, the expressions for the symmetry and similarity variables must -define a non-singular transformation $x,y \rightarrow u,v$. - -Different special solutions selected at this stage -will result in different -resulting DEs which are equivalent under point transformations but may -look quite differently. A transformation that is more difficult than another -one will in general -only complicate the new DE(s) compared with the simpler transformation. -We therefore seek the simplest possible special -solutions of (\ref{ql1}), (\ref{ql2}). They also -have to be simple because the transformation has to be inverted to solve for -the old variables in order to do the transformations. - -The following steps are performed in the corresponding mode of the -program {\tt APPLYSYM}: -\begin{itemize} -\item The user is asked to specify a symmetry by selecting one symmetry -from all the known symmetries or by specifying a linear combination of them. -\item Through a call of the procedure {\tt QUASILINPDE} (described in a later -section) the two linear first order PDEs (\ref{ql1}), (\ref{ql2}) are -investigated and, if possible, solved. -\item From the general solution of (\ref{ql1}) 1 special solution -is selected and from (\ref{ql2}) $p+q-1$ special -solutions are selected which should be as simple as possible. -\item The user is asked whether the symmetry variable should be one of the -independent variables (as it has been assumed so far) or one of the new -functions (then only derivatives of this function and not the function itself -turn up in the new DE(s)). -\item Through a call of the procedure {\tt DETRAFO} the transformation -$x^i,y^\alpha \rightarrow v^j,u^\beta$ of the DE(s) $H_A=0$ is finally done. -\item The program returns to the starting menu. -\end{itemize} -%--------------------------------------- -\subsection{The second mode: Generalization of special solutions} -A second application of infinitesimal symmetries is the generalization -of a known special solution given in implicit form through -$0 = F(x^i,y^\alpha)$. If one knows a symmetry variable $v^1$ and -similarity variables $v^r, u^\alpha,\;\;2\leq r\leq p$ then -$v^1$ can be shifted by a constant $c$ because of -$\partial_{v^1}H_A = 0$ and -therefore the DEs $0 = H_A(v^r,u^\alpha,u^\beta_j,\ldots)$ -are unaffected by the shift. Hence from -\[0 = F(x^i, y^\alpha) = F(x^i(v^j,u^\beta), y^\alpha(v^j,u^\beta)) = -\bar{F}(v^j,u^\beta)\] follows that -\[ 0 = \bar{F}(v^1+c,v^r,u^\beta) = -\bar{F}(v^1(x^i,y^\alpha)+c, v^r(x^i,y^\alpha), u^\beta(x^i,y^\alpha))\] -defines implicitly a generalized solution $y^\alpha=y^\alpha(x^i,c)$. - -This generalization works only if $\partial_{v^1}\bar{F} \neq 0$ and -if $\bar{F}$ does not already have -a constant additive to $v^1$. - -The method above needs to know $x^i=x^i(u^\beta,v^j),\; -y^\alpha=y^\alpha(u^\beta,v^j)$ \underline{and} -$u^\alpha = u^\alpha(x^j,y^\beta), v^\alpha = v^\alpha(x^j,y^\beta)$ -which may be practically impossible. -Better is, to integrate $x^i,y^\alpha$ along $X$: -\begin{equation} -\frac{d\bar{x}^i}{d\varepsilon} = \xi^i(\bar{x}^j(\varepsilon), - \bar{y}^\beta(\varepsilon)), \;\;\;\;\; -\frac{d\bar{y}^\alpha}{d\varepsilon} = \eta^\alpha(\bar{x}^j(\varepsilon), - \bar{y}^\beta(\varepsilon)) -\label{ODEsys} -\end{equation} -with initial values $\bar{x}^i = x^i, \bar{y}^\alpha = y^\alpha$ -for $\varepsilon = 0.$ -(This ODE-system is the characteristic system of (\ref{ql2}).) - -Knowing only the finite transformations -\begin{equation} -\bar{x}^i = \bar{x}^i(x^j,y^\beta,\varepsilon),\;\; -\bar{y}^\alpha = \bar{y}^\alpha(x^j,y^\beta,\varepsilon) \label{ODEsol} -\end{equation} -gives immediately the inverse transformation -$\bar{x}^i = \bar{x}^i(x^j,y^\beta,\varepsilon),\;\; -\bar{y}^\alpha = \bar{y}^\alpha(x^j,y^\beta,\varepsilon)$ -just by $\varepsilon \rightarrow -\varepsilon$ and renaming -$x^i,y^\alpha \leftrightarrow \bar{x}^i,\bar{y}^\alpha.$ - -The special solution $0 = F(x^i,y^\alpha)$ -is generalized by the new constant -$\varepsilon$ through -\[ 0 = F(x^i,y^\alpha) = F(x^i(\bar{x}^j,\bar{y}^\beta,\varepsilon), - y^\alpha(\bar{x}^j,\bar{y}^\beta,\varepsilon)) \] -after dropping the $\bar{ }$. - -The steps performed in the corresponding mode of the -program {\tt APPLYSYM} show features of both techniques: -\begin{itemize} -\item The user is asked to specify a symmetry by selecting one symmetry -from all the known symmetries or by specifying a linear combination of them. -\item The special solution to be generalized and the name of the new -constant have to be put in. -\item Through a call of the procedure {\tt QUASILINPDE}, the PDE (\ref{ql1}) -is solved which amounts to a solution of its characteristic ODE system -(\ref{ODEsys}) where $v^1=\varepsilon$. -\item {\tt QUASILINPDE} returns a list of constant expressions -\begin{equation} -c_i = c_i(x^k, y^\beta, \varepsilon),\;\;1\leq i\leq p+q -\end{equation} -which are solved for -$x^j=x^j(c_i,\varepsilon),\;\; y^\alpha=y^\alpha(c_i,\varepsilon)$ -to obtain the generalized solution through -\[ 0 = F(x^j, y^\alpha) - = F( x^j(c_i(x^k, y^\beta, 0), \varepsilon)), - y^\alpha(c_i(x^k, y^\beta, 0), \varepsilon))). \] -\item The new solution is availabe for further generalizations w.r.t.\ other -symmetries. -\end{itemize} -If one would like to generalize a given special solution with $m$ new -constants because $m$ symmetries are known, then one could run the whole -program $m$ times, each time with a different symmetry or one could run the -program once with a linear combination of $m$ symmetry generators which -again is a symmetry generator. Running the program once adds one constant -but we have in addition $m-1$ arbitrary constants in the linear combination -of the symmetries, so $m$ new constants are added. -Usually one will generalize the solution gradually to make solving -(\ref{ODEsys}) gradually more difficult. -%--------------------------------------- -\subsection{Syntax} -The call of {\tt APPLYSYM} is -{\tt APPLYSYM}(\{{\it de}, {\it fun}, {\it var}\}, \{{\it sym}, {\it cons}\}); -\begin{itemize} -\item {\it de} is a single DE or a list of DEs in the form of a vanishing - expression or in the form $\ldots=\ldots\;\;$. -\item {\it fun} is the single function or the list of functions occuring - in {\it de}. -\item {\it var} is the single variable or the list of variables in {\it de}. -\item {\it sym} is a linear combination of all symmetries, each with a - different constant coefficient, in form of a list of the $\xi^i$ and - $\eta^\alpha$: \{xi\_\ldots=\ldots,\ldots,eta\_\ldots=\ldots,\ldots\}, - where the indices after `xi\_' are the variable names and after `eta\_' - the function names. -\item {\it cons} is the list of constants in {\it sym}, one constant for each - symmetry. -\end{itemize} -The list that is the first argument of {\tt APPLYSYM} is the same as the -first argument of {\tt LIEPDE} and the -second argument is the list that {\tt LIEPDE} returns without its first -element (the unsolved conditions). An example is given below. - -What {\tt APPLYSYM} returns depends on the last performed modus. -After modus 1 the return is \\ -\{\{{\it newde}, {\it newfun}, {\it newvar}\}, {\it trafo}\} \\ -where -\begin{itemize} -\item {\it newde} lists the transformed equation(s) -\item {\it newfun} lists the new function name(s) -\item {\it newvar} lists the new variable name(s) -\item {\it trafo} lists the transformations $x^i=x^i(v^j,u^\beta), - y^\alpha=y^\alpha(v^j,u^\beta)$ -\end{itemize} -After modus 2, {\tt APPLYSYM} returns the generalized special solution. -%--------------------------------------- -\subsection{Example: A second order ODE} -Weyl's class of solutions of Einsteins field equations consists of -axialsymmetric time independent metrics of the form -\begin{equation} -{\rm{d}} s^2 = e^{-2 U} \left[ e^{2 k} \left( \rm{d} \rho^2 + \rm{d} -z^2 \right)+\rho^2 \rm{d} \varphi^2 \right] - e^{2 U} \rm{d} t^2, -\end{equation} -where $U$ and $k$ are functions of $\rho$ and $z$. If one is interested in -generalizing these solutions to have a time dependence then the resulting -DEs can be transformed such that one longer third order ODE for $U$ results -which contains only $\rho$ derivatives \cite{Markus}. Because $U$ appears -not alone but only as derivative, a substitution -\begin{equation} -g = dU/d\rho \label{g1dgl} -\end{equation} -lowers the order and the introduction of a function -\begin{equation} -h = \rho g - 1 \label{g2dgl} -\end{equation} -simplifies the ODE to -\begin{equation} -0 = 3\rho^2h\,h'' --5\rho^2\,h'^2+5\rho\,h\,h'-20\rho\,h^3h'-20\,h^4+16\,h^6+4\,h^2. \label{hdgl} -\end{equation} -where $'= d/d\rho$. -Calling {\tt LIEPDE} through -\small \begin{verbatim} -depend h,r; -prob:={{-20*h**4+16*h**6+3*r**2*h*df(h,r,2)+5*r*h*df(h,r) - -20*h**3*r*df(h,r)+4*h**2-5*r**2*df(h,r)**2}, - {h}, {r}}; -sym:=liepde(prob,{0,nil,nil}); -end; \end{verbatim} \normalsize -gives \small \begin{verbatim} - 3 2 -sym := {{}, {xi_r= - c10*r - c11*r, eta_h=c10*h*r }, {c10,c11}}. -\end{verbatim} \normalsize -All conditions have been solved because the first element of {\tt sym} -is $\{\}$. The two existing symmetries are therefore -\begin{equation} - - \rho^3 \partial_{\rho} + h \rho^2 \,\partial_{h} \;\;\;\;\;\;\mbox{and} - \;\;\;\;\;\;\rho \partial_{\rho}. -\end{equation} -Corresponding finite -transformations can be calculated with {\tt APPLYSYM} through -\small \begin{verbatim} -newde:=applysym(de,rest sym); -\end{verbatim} \normalsize -The interactive session is given below with the user input following -the prompt `{\tt Input:3:}' or following `?'. (Empty lines have been deleted.) -\small \begin{verbatim} -Do you want to find similarity and symmetry variables (enter `1;') -or generalize a special solution with new parameters (enter `2;') -or exit the program (enter `;') -Input:3: 1; -\end{verbatim} \normalsize -We enter `1;' because we want to reduce dependencies by finding similarity -variables and one symmetry variable and then doing the transformation such -that the symmetry variable does not explicitly occur in the DE. -\small \begin{verbatim} ----------------------- The 1. symmetry is: - 3 -xi_r= - r - 2 -eta_h=h*r ----------------------- The 2. symmetry is: -xi_r= - r ----------------------- -Which single symmetry or linear combination of symmetries -do you want to apply? "$ -Enter an expression with `sy_(i)' for the i'th symmetry. -sy_(1); -\end{verbatim} \normalsize -We could have entered `sy\_(2);' or a combination of both -as well with the calculation running then -differently. -\small \begin{verbatim} -The symmetry to be applied in the following is - 3 2 -{xi_r= - r ,eta_h=h*r } -Enter the name of the new dependent variables: -Input:3: u; -Enter the name of the new independent variables: -Input:3: v; -\end{verbatim} \normalsize -This was the input part, now the real calculation starts. -\small \begin{verbatim} -The ODE/PDE (-system) under investigation is : - 2 2 2 3 -0 = 3*df(h,r,2)*h*r - 5*df(h,r) *r - 20*df(h,r)*h *r - 6 4 2 - + 5*df(h,r)*h*r + 16*h - 20*h + 4*h -for the function(s) : h. -It will be looked for a new dependent variable u -and an independent variable v such that the transformed -de(-system) does not depend on u or v. -1. Determination of the similarity variable - 2 -The quasilinear PDE: 0 = r *(df(u_,h)*h - df(u_,r)*r). -The equivalent characteristic system: - 3 -0= - df(u_,r)*r - 2 -0= - r *(df(h,r)*r + h) -for the functions: h(r) u_(r). -\end{verbatim} \normalsize -The PDE is equation (\ref{ql2}). -\small \begin{verbatim} -The general solution of the PDE is given through -0 = ff(u_,h*r) -with arbitrary function ff(..). -A suggestion for this function ff provides: -0 = - h*r + u_ -Do you like this choice? (Y or N) -?y -\end{verbatim} \normalsize -For the following calculation only a single special solution of the PDE is -necessary -and this has to be specified from the general solution by choosing a special -function {\tt ff}. (This function is called {\tt ff} to prevent a clash with -names of user variables/functions.) In principle any choice of {\tt ff} would -work, if it defines a non-singular coordinate transformation, i.e.\ here $r$ -must be a function of $u\_$. If we have $q$ independent variables and -$p$ functions of them then {\tt ff} has $p+q$ arguments. Because of the -condition $0 = ${\tt ff} one has essentially the freedom of choosing a function -of $p+q-1$ arguments freely. This freedom is also necessary to select $p+q-1$ -different functions {\tt ff} and to find as many functionally independent -solutions $u\_$ which all become the new similarity variables. $q$ of them -become the new functions $u^\alpha$ and $p-1$ of them the new variables -$v^2,\ldots,v^p$. Here we have $p=q=1$ (one single ODE). - -Though the program could have done that alone, once the general solution -{\tt ff(..)} is known, the user can interfere here to enter a simpler solution, -if possible. -\small \begin{verbatim} -2. Determination of the symmetry variable - 2 3 -The quasilinear PDE: 0 = df(u_,h)*h*r - df(u_,r)*r - 1. -The equivalent characteristic system: - 3 -0=df(r,u_) + r - 2 -0=df(h,u_) - h*r -for the functions: r(u_) h(u_) . -New attempt with a different independent variable -The equivalent characteristic system: - 2 -0=df(u_,h)*h*r - 1 - 2 -0=r *(df(r,h)*h + r) -for the functions: r(h) u_(h) . -The general solution of the PDE is given through - 2 2 2 - - 2*h *r *u_ + h -0 = ff(h*r,--------------------) - 2 -with arbitrary function ff(..). -A suggestion for this function ff(..) yields: - 2 2 - h *( - 2*r *u_ + 1) -0 = --------------------- - 2 -Do you like this choice? (Y or N) -?y -\end{verbatim} \normalsize -Similar to above. -\small \begin{verbatim} -The suggested solution of the algebraic system which will -do the transformation is: - sqrt(v)*sqrt(2) -{h=sqrt(v)*sqrt(2)*u,r=-----------------} - 2*v -Is the solution ok? (Y or N) -?y -In the intended transformation shown above the dependent -variable is u and the independent variable is v. -The symmetry variable is v, i.e. the transformed expression -will be free of v. -Is this selection of dependent and independent variables ok? (Y or N) -?n -\end{verbatim} \normalsize -We so far assumed that the symmetry variable is one of the new variables, but, -of course we also could choose it to be one of the new functions. -If it is one of the functions then only derivatives of this function occur -in the new DE, not the function itself. If it is one of the variables then -this variable will not occur explicitly. - -In our case we prefer (without strong reason) to have the function as -symmetry variable. We therefore answered with `no'. As a consequence, $u$ and -$v$ will exchange names such that still all new functions have the name $u$ -and the new variables have name $v$: -\small \begin{verbatim} -Please enter a list of substitutions. For example, to -make the variable, which is so far call u1, to an -independent variable v2 and the variable, which is -so far called v2, to an dependent variable u1, -enter: `{u1=v2, v2=u1};' -Input:3: {u=v,v=u}; - -The transformed equation which should be free of u: - 3 6 2 3 -0=3*df(u,v,2)*v - 16*df(u,v) *v - 20*df(u,v) *v + 5*df(u,v) -Do you want to find similarity and symmetry variables (enter `1;') -or generalize a special solution with new parameters (enter `2;') -or exit the program (enter `;') -Input:3: ; -\end{verbatim} -We stop here. The following is returned from our {\tt APPLYSYM} call: -\small \begin{verbatim} - 3 6 2 3 -{{{3*df(u,v,2)*v - 16*df(u,v) *v - 20*df(u,v) *v + 5*df(u,v)}, - {u}, - {v}}, - sqrt(u)*sqrt(2) - {r=-----------------, h=sqrt(u)*sqrt(2)*v }} - 2*u -\end{verbatim} \normalsize -The use of {\tt APPLYSYM} effectively provided us the finite -transformation -\begin{equation} - \rho=(2\,u)^{-1/2},\;\;\;\;\;h=(2\,u)^{1/2}\,v \label{trafo1}. -\end{equation} -and the new ODE -\begin{equation} -0 = 3u''v - 16u'^3v^6 - 20u'^2v^3 + 5u' \label{udgl} -\end{equation} -where $u=u(v)$ and $'=d/dv.$ -Using one symmetry we reduced the 2.\,order ODE (\ref{hdgl}) -to a first order ODE (\ref{udgl}) for $u'$ plus one -integration. The second symmetry can be used to reduce the remaining ODE -to an integration too by introducing a variable $w$ through $v^3d/dv = d/dw$, -i.e. $w = -1/(2v^2)$. With -\begin{equation} -p=du/dw \label{udot} -\end{equation} -the remaining ODE is -\[0 = 3\,w\,\frac{dp}{dw} + 2\,p\,(p+1)(4\,p+1) \] -with solution -\[ \tilde{c}w^{-2}/4 = \tilde{c}v^4 = \frac{p^3(p+1)}{(4\,p+1)^4},\;\;\; - \tilde{c}=const. \] -Writing (\ref{udot}) as $p = v^3(du/dp)/(dv/dp)$ we get $u$ by integration -and with (\ref{trafo1}) further a parametric solution for $\rho,h$: -\begin{eqnarray} -\rho & = & \left(\frac{3c_1^2(2p-1)}{p^{1/2}(p+1)^{1/2}}+c_2\right)^{-1/2} \\ -h & = & \frac{(c_2p^{1/2}(p+1)^{1/2}+6c_1^2p-3c_1^2)^{1/2}p^{1/2}}{c_1(4p+1)} -\end{eqnarray} -where $c_1, c_2 = const.$ and $c_1=\tilde{c}^{1/4}.$ Finally, the metric -function $U(p)$ is obtained as an integral from (\ref{g1dgl}),(\ref{g2dgl}). -%--------------------------------------- -\subsection{Limitations of {\tt APPLYSYM}} -Restrictions of the applicability of the program {\tt APPLYSYM} result -from limitations of the program {\tt QUASILINPDE} described in a section below. -Essentially this means that symmetry generators may only be polynomially -non-linear in $x^i, y^\alpha$. -Though even then the solvability can not be guaranteed, the -generators of Lie-symmetries are mostly very simple such that the -resulting PDE (\ref{PDE}) and the corresponding characteristic -ODE-system have good chances to be solvable. - -Apart from these limitations implied through the solution of differential -equations with {\tt CRACK} and algebraic equations with {\tt SOLVE} -the program {\tt APPLYSYM} itself is free of restrictions, -i.e.\ if once new versions of {\tt CRACK, SOLVE} -would be available then {\tt APPLYSYM} would not have to be changed. - -Currently, whenever a computational step could not be performed -the user is informed and has the possibility of entering interactively -the solution of the unsolved algebraic system or the unsolved linear PDE. -%------------------------------------------------------------------------- -\section{Solving quasilinear PDEs} -%--------------------------------------- -\subsection{The content of {\tt QUASILINPDE}} -The generalization of special solutions of DEs as well as the computation of -similarity and symmetry variables involve the general solution of single -first order linear PDEs. -The procedure {\tt QUASILINPDE} is a general procedure -aiming at the general solution of -PDEs -\begin{equation} - a_1(w_i,\phi)\phi_{w_1} + a_2(w_i,\phi)\phi_{w_2} + \ldots + - a_n(w_i,\phi)\phi_{w_n} = b(w_i,\phi) \label{PDE} -\end{equation} -in $n$ independent variables $w_i, i=1\ldots n$ for one unknown function -$\phi=\phi(w_i)$. -\begin{enumerate} -\item -The first step in solving a quasilinear PDE (\ref{PDE}) -is the formulation of the corresponding characteristic ODE-system -\begin{eqnarray} -\frac{dw_i}{d\varepsilon} & = & a_i(w_j,\phi) \label{char1} \\ -\frac{d\phi}{d\varepsilon} & = & b(w_j,\phi) \label{char2} -\end{eqnarray} -for $\phi, w_i$ regarded now as functions of one variable $\varepsilon$. - -Because the $a_i$ and $b$ do not depend explicitly on $\varepsilon$, one of the -equations (\ref{char1}),(\ref{char2}) with non-vanishing right hand side -can be used to divide all others through it and by that having a system -with one less ODE to solve. -If the equation to divide through is one of -(\ref{char1}) then the remaining system would be -\begin{eqnarray} -\frac{dw_i}{dw_k} & = & \frac{a_i}{a_k} , \;\;\;i=1,2,\ldots k-1,k+1,\ldots n - \label{char3} \\ -\frac{d\phi}{dw_k} & = & \frac{b}{a_k} \label{char4} -\end{eqnarray} -with the independent variable $w_k$ instead of $\varepsilon$. -If instead we divide through equation -(\ref{char2}) then the remaining system would be -\begin{eqnarray} -\frac{dw_i}{d\phi} & = & \frac{a_i}{b} , \;\;\;i=1,2,\ldots n - \label{char3a} -\end{eqnarray} -with the independent variable $\phi$ instead of $\varepsilon$. - -The equation to divide through is chosen by a -subroutine with a heuristic to find the ``simplest'' non-zero -right hand side ($a_k$ or $b$), i.e.\ one which -\begin{itemize} -\item is constant or -\item depends only on one variable or -\item is a product of factors, each of which depends only on -one variable. -\end{itemize} - -One purpose of this division is to reduce the number of ODEs by one. -Secondly, the general solution of (\ref{char1}), (\ref{char2}) involves -an additive constant to $\varepsilon$ which is not relevant and would -have to be set to zero. By dividing through one ODE we eliminate -$\varepsilon$ and lose the problem of identifying this constant in the -general solution before we would have to set it to zero. - -\item % from enumerate -To solve the system (\ref{char3}), (\ref{char4}) or (\ref{char3a}), -the procedure {\tt CRACK} is called. -Although being designed primarily for the solution of overdetermined -PDE-systems, {\tt CRACK} can also be used to solve simple not -overdetermined ODE-systems. This solution -process is not completely algorithmic. Improved versions of {\tt CRACK} -could be used, without making any changes of {\tt QUASILINPDE} -necessary. - -If the characteristic ODE-system can not be solved in the form -(\ref{char3}), (\ref{char4}) or (\ref{char3a}) -then successively all other ODEs of (\ref{char1}), (\ref{char2}) -with non-vanishing right hand side are used for division until -one is found -such that the resulting ODE-system can be solved completely. -Otherwise the PDE can not be solved by {\tt QUASILINPDE}. - -\item % from enumerate -If the characteristic ODE-system (\ref{char1}), (\ref{char2}) has been -integrated completely and in full generality to the implicit solution -\begin{equation} -0 = G_i(\phi, w_j, c_k, \varepsilon),\;\; -i,k=1,\ldots,n+1,\;\;j=1,\ldots,n \label{charsol1} -\end{equation} -then according to the general theory for solving first order PDEs, -$\varepsilon$ has -to be eliminated from one of the equations and to be substituted in the -others to have left $n$ equations. -Also the constant that turns up additively to $\varepsilon$ -is to be set to zero. Both tasks are automatically -fulfilled, if, as described above, $\varepsilon$ is already eliminated -from the beginning by dividing all equations of (\ref{char1}), -(\ref{char2}) -through one of them. - -On either way one ends up with $n$ equations -\begin{equation} -0=g_i(\phi,w_j,c_k),\;\;i,j,k=1\ldots n \label{charsol2} -\end{equation} -involving $n$ constants $c_k$. - -The final step is to solve (\ref{charsol2}) for the $c_i$ to obtain -\begin{equation} -c_i = c_i(\phi, w_1,\ldots ,w_n) \;\;\;\;\;i=1,\ldots n . \label{cons} -\end{equation} -The final solution $\phi = \phi(w_i)$ of the PDE (\ref{PDE}) is then -given implicitly through -\[ 0 = F(c_1(\phi,w_i),c_2(\phi,w_i),\ldots,c_n(\phi,w_i)) \] -where $F$ is an arbitrary function with $n$ arguments. -\end{enumerate} -%--------------------------------------- -\subsection{Syntax} -The call of {\tt QUASILINPDE} is \\ -{\tt QUASILINPDE}({\it de}, {\it fun}, {\it varlist}); -\begin{itemize} -\item -{\it de} is the differential expression which vanishes due to the PDE -{\it de}$\; = 0$ or, {\it de} may be the differential equation itself in the -form $\;\;\ldots = \ldots\;\;$. -\item -{\it fun} is the unknown function. -\item -{\it varlist} is the list of variables of {\it fun}. -\end{itemize} -The result of {\tt QUASILINPDE} is a list of general solutions -\[ \{{\it sol}_1, {\it sol}_2, \ldots \}. \] -If {\tt QUASILINPDE} can not solve the PDE then it returns $\{\}$. -Each solution ${\it sol}_i$ is a list of expressions -\[ \{{\it ex}_1, {\it ex}_2, \ldots \} \] -such that the dependent function ($\phi$ in (\ref{PDE})) is determined -implicitly through an arbitrary function $F$ and the algebraic -equation \[ 0 = F({\it ex}_1, {\it ex}_2, \ldots). \] -%--------------------------------------- -\subsection{Examples} -{\em Example 1:}\\ -To solve the quasilinear first order PDE \[1 = xu,_x + uu,_y - zu,_z\] -for the function $u = u(x,y,z),$ the input would be -\small \begin{verbatim} -depend u,x,y,z; -de:=x*df(u,x)+u*df(u,y)-z*df(u,z) - 1; -varlist:={x,y,z}; -QUASILINPDE(de,u,varlist); -\end{verbatim} \normalsize -In this example the procedure returns -\[\{ \{ x/e^u, ze^u, u^2 - 2y \} \},\] -i.e. there is one general solution (because the outer list has only one -element which itself is a list) and $u$ is given implicitly through -the algebraic equation -\[ 0 = F(x/e^u, ze^u, u^2 - 2y)\] -with arbitrary function $F.$ \\ -{\em Example 2:}\\ -For the linear inhomogeneous PDE -\[ 0 = y z,_x + x z,_y - 1, \;\;\;\;\mbox{for}\;\;\;\;z=z(x,y)\] -{\tt QUASILINPDE} returns the result that for an arbitrary function $F,$ the -equation -\[ 0 = F\left(\frac{x+y}{e^z},e^z(x-y)\right) \] -defines the general solution for $z$. \\ -{\em Example 3:}\\ -For the linear inhomogeneous PDE (3.8) from \cite{KamkePDE} -\[ 0 = x w,_x + (y+z)(w,_y - w,_z), \;\;\;\;\mbox{for}\;\;\;\;w=w(x,y,z)\] -{\tt QUASILINPDE} returns the result -that for an arbitrary function $F,$ the equation -\[ 0 = F\left(w, \;y+z, \;\ln(x)(y+z)-y\right) \] -defines the general solution for $w$, i.e.\ for any function $f$ -\[ w = f\left(y+z, \;\ln(x)(y+z)-y\right) \] -solves the PDE. -%--------------------------------------- -\subsection{Limitations of {\tt QUASILINPDE}} -One restriction on the applicability of {\tt QUASILINPDE} results from -the program {\tt CRACK} which tries to solve the -characteristic ODE-system of the PDE. So far {\tt CRACK} can be -applied only to polynomially non-linear DE's, i.e.\ the characteristic -ODE-system (\ref{char3}),(\ref{char4}) or (\ref{char3a}) may -only be polynomially non-linear, i.e.\ in the PDE (\ref{PDE}) -the expressions $a_i$ and $b$ may only be rational in $w_j,\phi$. - -The task of {\tt CRACK} is simplified as (\ref{charsol1}) does not have to -be solved for $w_j, \phi$. On the other hand (\ref{charsol1}) has to be -solved for the $c_i$. This gives a -second restriction coming from the REDUCE function {\tt SOLVE}. -Though {\tt SOLVE} can be applied -to polynomial and transzendential equations, again no guarantee for -solvability can be given. -%------------------------------------------------------------------------- -\section{Transformation of DEs} -%--------------------------------------- -\subsection{The content of {\tt DETRAFO}} -Finally, after having found the finite transformations, -the program {\tt APPLYSYM} calls the procedure -{\tt DETRAFO} to perform the transformations. {\tt DETRAFO} -can also be used alone to do point- or higher order transformations -which involve a considerable computational effort if the -differential order of the expression to be transformed is high and -if many dependent and independent variables are involved. -This might be especially useful if one wants to experiment -and try out different coordinate transformations interactively, -using {\tt DETRAFO} as standalone procedure. - -To run {\tt DETRAFO}, the old functions $y^{\alpha}$ and old -variables $x^i$ must be -known explicitly in terms of algebraic or -differential expressions of the new functions $u^{\beta}$ -and new variables $v^j$. Then for point transformations the identity -\begin{eqnarray} -dy^{\alpha} & = & \left(y^{\alpha},_{v^i} + - y^{\alpha},_{u^{\beta}}u^{\beta},_{v^i}\right) dv^i \\ - & = & y^{\alpha},_{x^j}dx^j \\ - & = & y^{\alpha},_{x^j}\left(x^j,_{v^i} + - x^j,_{u^{\beta}}u^{\beta},_{v^i}\right) dv^i -\end{eqnarray} -provides the transformation -\begin{equation} -y^{\alpha},_{x^j} = \frac{dy^\alpha}{dv^i}\cdot - \left(\frac{dx^j}{dv^i}\right)^{-1} \label{trafo} -\end{equation} -with {\it det}$\left(dx^j/dv^i\right) \neq 0$ because of the regularity -of the transformation which is checked by {\tt DETRAFO}. Non-regular -transformations are not performed. - -{\tt DETRAFO} is not restricted to point transformations. -In the case of -contact- or higher order transformations, the total -derivatives $dy^{\alpha}/dv^i$ and $dx^j/dv^i$ then only include all -$v^i-$ derivatives of $u^{\beta}$ which occur in -\begin{eqnarray*} -y^{\alpha} & = & y^{\alpha}(v^i,u^{\beta},u^{\beta},_{v^j},\ldots) \\ -x^k & = & x^k(v^i,u^{\beta},u^{\beta},_{v^j},\ldots). -\end{eqnarray*} -%--------------------------------------- -\subsection{Syntax} -The call of {\tt DETRAFO} is -\begin{tabbing} -{\tt DETRAFO}(\=\{{\it ex}$_1$, {\it ex}$_2$, \ldots , {\it ex}$_m$\}, \\ - \>\{{\it ofun}$_1=${\it fex}$_1$, {\it ofun}$_2=${\it fex}$_2$, - \ldots ,{\it ofun}$_p=${\it fex}$_p$\}, \\ - \>\{{\it ovar}$_1=${\it vex}$_1$, {\it ovar}$_2=${\it vex}$_2$, \ldots , - {\it ovar}$_q=${\it vex}$_q$\}, \\ - \>\{{\it nfun}$_1$, {\it nfun}$_2$, \ldots , {\it nfun}$_p$\},\\ - \>\{{\it nvar}$_1$, {\it nvar}$_2$, \ldots , {\it nvar}$_q$\}); -\end{tabbing} -where $m,p,q$ are arbitrary. -\begin{itemize} -\item -The {\it ex}$_i$ are differential expressions to be transformed. -\item -The second list is the list of old functions {\it ofun} expressed -as expressions {\it fex} in terms -of new functions {\it nfun} and new independent variables {\it nvar}. -\item -Similarly the third list expresses the old independent variables {\it ovar} -as expressions {\it vex} in terms of new functions -{\it nfun} and new independent variables {\it nvar}. -\item -The last two lists include the new functions {\it nfun} -and new independent variables {\it nvar}. -\end{itemize} -Names for {\it ofun, ovar, nfun} and {\it nvar} can be arbitrarily -chosen. - -As the result {\tt DETRAFO} returns the first argument of its input, -i.e.\ the list -\[\{{\it ex}_1, {\it ex}_2, \ldots , {\it ex}_m\}\] -where all ${\it ex}_i$ are transformed. -%--------------------------------------- -\subsection{Limitations of {\tt DETRAFO}} -The only requirement is that -the old independent variables $x^i$ and old functions $y^\alpha$ must be -given explicitly in terms of new variables $v^j$ and new functions $u^\beta$ -as indicated in the syntax. -Then all calculations involve only differentiations and basic algebra. -%------------------------------------------------------------------------- -\section{Availability} -The programs run under {\tt REDUCE 3.4.1} or later versions and are available -by anonymous ftp from 138.37.80.15, directory {\tt ~ftp/pub/crack}. -%The manual file {\tt APPLYSYM.TEX} gives more details on the syntax. - -\begin{thebibliography}{99} -\bibitem{WHer} W.\,Hereman, Chapter 13 in vol 3 of the CRC Handbook of -Lie Group Analysis of Differential Equations, Ed.: N.H.\,Ibragimov, -CRC Press, Boca Raton, Florida (1995). -Systems described in this paper are among others: \\ -DELiA (Alexei Bocharov et.al.) Pascal \\ -DIFFGROB2 (Liz Mansfield) Maple \\ -DIMSYM (James Sherring and Geoff Prince) REDUCE \\ -HSYM (Vladimir Gerdt) Reduce \\ -LIE (V. Eliseev, R.N. Fedorova and V.V. Kornyak) Reduce \\ -LIE (Alan Head) muMath \\ -Lie (Gerd Baumann) Mathematica \\ -LIEDF/INFSYM (Peter Gragert and Paul Kersten) Reduce \\ -Liesymm (John Carminati, John Devitt and Greg Fee) Maple \\ -MathSym (Scott Herod) Mathematica \\ -NUSY (Clara Nucci) Reduce \\ -PDELIE (Peter Vafeades) Macsyma \\ -SPDE (Fritz Schwarz) Reduce and Axiom \\ -SYM\_DE (Stanly Steinberg) Macsyma \\ -Symmgroup.c (Dominique Berube and Marc de Montigny) Mathematica \\ -STANDARD FORM (Gregory Reid and Alan Wittkopf) Maple \\ -SYMCAL (Gregory Reid) Macsyma and Maple \\ -SYMMGRP.MAX (Benoit Champagne, Willy Hereman and Pavel Winternitz) Macsyma \\ -LIE package (Khai Vu) Maple \\ -Toolbox for symmetries (Mark Hickman) Maple \\ -Lie symmetries (Jeffrey Ondich and Nick Coult) Mathematica. - -\bibitem{lie1} S.\,Lie, Sophus Lie's 1880 Transformation Group Paper, -Translated by M.\,Ackerman, comments by R.\,Hermann, Mathematical Sciences -Press, Brookline, (1975). - -\bibitem{lie2} S.\,Lie, Differentialgleichungen, Chelsea Publishing Company, -New York, (1967). - -\bibitem{LIEPDE} T.\,Wolf, An efficiency improved program {\tt LIEPDE} -for determining Lie - symmetries of PDEs, Proceedings of the workshop on -Modern group theory methods in Acireale (Sicily) Nov.\,(1992) - -\bibitem{Riq} C.\,Riquier, Les syst\`{e}mes d'\'{e}quations -aux d\'{e}riv\'{e}es partielles, Gauthier--Villars, Paris (1910). - -\bibitem{Th} J.\,Thomas, Differential Systems, AMS, Colloquium -publications, v.\,21, N.Y.\,(1937). - -\bibitem{Ja} M.\,Janet, Le\c{c}ons sur les syst\`{e}mes d'\'{e}quations aux -d\'{e}riv\'{e}es, Gauthier--Villars, Paris (1929). - -\bibitem{Topu} V.L.\,Topunov, Reducing Systems of Linear Differential -Equations to a Passive Form, Acta Appl.\,Math.\,16 (1989) 191--206. - -\bibitem{Alex} A.V.\,Bocharov and M.L.\,Bronstein, Efficiently -Implementing Two Methods of the Geometrical Theory of Differential -Equations: An Experience in Algorithm and Software Design, Acta.\,Appl. -Math.\,16 (1989) 143--166. - -\bibitem{Olv} P.J. Olver, Applications of Lie Groups to Differential -Equations, Springer-Verlag New York (1986). - -\bibitem{Reid1} G.J.\,Reid, A triangularization algorithm which -determines the Lie symmetry algebra of any system of PDEs, J.Phys.\,A: -Math.\,Gen.\,23 (1990) L853-L859. - -\bibitem{FS} F.\,Schwarz, Automatically Determining Symmetries of Partial -Differential Equations, Computing 34, (1985) 91-106. - -\bibitem{Fush} W.I.\,Fushchich and V.V.\,Kornyak, Computer Algebra -Application for Determining Lie and Lie--B\"{a}cklund Symmetries of -Differential Equations, J.\,Symb.\,Comp.\,7 (1989) 611--619. - -\bibitem{Ka} E.\,Kamke, Differentialgleichungen, L\"{o}sungsmethoden -und L\"{o}sungen, Band 1, Gew\"{o}hnliche Differentialgleichungen, -Chelsea Publishing Company, New York, 1959. - -\bibitem{KamkePDE} E.\,Kamke, Differentialgleichungen, L\"{o}sungsmethoden -und L\"{o}sungen, Band 2, Partielle Differentialgleichungen, 6.Aufl., -Teubner, Stuttgart:Teubner, 1979. - -\bibitem{Wo} T.\,Wolf, An Analytic Algorithm for Decoupling and Integrating -systems of Nonlinear Partial Differential Equations, J.\,Comp.\,Phys., -no.\,3, 60 (1985) 437-446 and, Zur analytischen Untersuchung und exakten -L\"{o}sung von Differentialgleichungen mit Computeralgebrasystemen, -Dissertation B, Jena (1989). - -\bibitem{WoBra} T.\,Wolf, A. Brand, The Computer Algebra Package {\tt CRACK} - for Investigating PDEs, Manual for the package {\tt CRACK} in the REDUCE - network library and in Proceedings of ERCIM School on Partial - Differential Equations and Group Theory, April 1992 in Bonn, GMD Bonn. - -\bibitem{WM} M.A.H.\,MacCallum, F.J.\,Wright, Algebraic Computing with REDUCE, -Clarendon Press, Oxford (1991). - -\bibitem{Mal} M.A.H.\,MacCallum, An Ordinary Differential Equation -Solver for REDUCE, Proc.\,ISAAC'88, Springer Lect.\,Notes in Comp Sci. -358, 196--205. - -\bibitem{Step} H.\,Stephani, Differential equations, Their solution using -symmetries, Cambridge University Press (1989). - -\bibitem{Karp} V.I.\,Karpman, Phys.\,Lett.\,A 136, 216 (1989) - -\bibitem{Cham} B.\,Champagne, W.\,Hereman and P.\,Winternitz, The computer - calculation of Lie point symmetries of large systems of differential - equations, Comp.\,Phys.\,Comm.\,66, 319-340 (1991) - -\bibitem{Markus} M.\,Kubitza, private communication - -\end{thebibliography} - -\end{document} - - +% This is a LaTeX file +\documentstyle[12pt]{article} + +%Sets size of page and margins +\oddsidemargin 10mm \evensidemargin 10mm +\topmargin 0pt \headheight 0pt \headsep 0pt +\footheight 14pt \footskip 40pt +\textheight 23cm \textwidth 15cm +%\textheight 15cm \textwidth 10cm + +%spaces lines at one and a half spacing +%\def\baselinestretch{1.5} + +%\parskip = \baselineskip + +%Defines capital R for the reals, ... +%\font\Edth=msym10 +%\def\Integer{\hbox{\Edth Z}} +%\def\Rational{\hbox{\Edth Q}} +%\def\Real{\hbox{\Edth R}} +%\def\Complex{\hbox{\Edth C}} + +\title{Programs for Applying Symmetries of PDEs} +\author{Thomas Wolf \\ + School of Mathematical Sciences \\ + Queen Mary and Westfield College \\ + University of London \\ + London E1 4NS \\ + T.Wolf@maths.qmw.ac.uk +} + +\begin{document} +\maketitle +\begin{abstract} +In this paper the programs {\tt APPLYSYM}, {\tt QUASILINPDE} and +{\tt DETRAFO} are described which aim at the utilization +of infinitesimal symmetries of differential equations. The purpose +of {\tt QUASILINPDE} is the general solution of +quasilinear PDEs. This procedure is used by {\tt APPLYSYM} +for the application of point symmetries for either +\begin{itemize} +\item calculating similarity variables to perform a point transformation +which lowers the order of an ODE or effectively reduces the number of +explicitly occuring independent variables in a PDE(-system) or for +\item generalizing given special solutions of ODEs/PDEs with new constant +parameters. +\end{itemize} + +The program {\tt DETRAFO} performs arbitrary point- and contact +transformations of ODEs/PDEs and is applied if similarity +and symmetry variables have been found. +The program {\tt APPLYSYM} is used in connection with the program +{\tt LIEPDE} for formulating and solving the conditions for point- and +contact symmetries which is described in \cite{LIEPDE}. +The actual problem solving is done in all these programs through a call +to the package {\tt CRACK} for solving overdetermined PDE-systems. +\end{abstract} + +\tableofcontents +%------------------------------------------------------------------------- +\section{Introduction and overview of the symmetry method} +The investigation of infinitesimal symmetries of differential equations +(DEs) with computer algebra programs attrackted considerable attention +over the last years. Corresponding programs are available in all +major computer algebra systems. In a review article by W.\ Hereman +\cite{WHer} about 200 references are given, many of them describing related +software. + +One reason for the popularity of the symmetry method +is the fact that Sophus Lie's method +\cite{lie1},\cite{lie2} is the most widely +used method for computing exact solutions of non-linear DEs. Another reason is +that the first step in this +method, the formulation of the determining equation for the generators +of the symmetries, can already be very cumbersome, especially in the +case of PDEs of higher order and/or in case of many dependent and independent +variables. Also, the formulation of the conditions is a straight forward +task involving only differentiations and basic algebra - an ideal task for +computer algebra systems. Less straight forward is the automatic solution +of the symmetry conditions which is the strength of the program {\tt LIEPDE} +(for a comparison with another program see \cite{LIEPDE}). + +The novelty described in this paper are programs aiming at +the final third step: Applying symmetries for +\begin{itemize} +\item calculating similarity variables to perform a point transformation +which lowers the order of an ODE or effectively reduces the number of +explicitly occuring independent variables of a PDE(-system) or for +\item generalizing given special solutions of ODEs/PDEs with new constant +parameters. +\end{itemize} +Programs which run on their own but also allow interactive user control +are indispensible for these calculations. On one hand the calculations can +become quite lengthy, like variable transformations of PDEs (of higher order, +with many variables). On the other hand the freedom of choosing the right +linear combination of symmetries and choosing the optimal new symmetry- and +similarity variables makes it necessary to `play' with the problem +interactively. + +The focus in this paper is directed on questions of implementation and +efficiency, no principally new mathematics is presented. + +In the following subsections a review of the first two steps of the symmetry +method is given as well as the third, i.e.\ the application step is outlined. +Each of the remaining sections is devoted to one procedure. +%--------------------------------------- +\subsection{The first step: Formulating the symmetry conditions} + +To obey classical Lie-symmetries, differential equations +\begin{equation} +H_A = 0 \label{PDEs} +\end{equation} +for unknown functions $y^\alpha,\;\;1\leq \alpha \leq p$ +of independent variables $x^i,\;\;1\leq i \leq q$ +must be forminvariant against infinitesimal transformations +\begin{equation} +\tilde{x}^i = x^i + \varepsilon \xi^i, \;\; \;\;\; + \tilde{y}^\alpha = y^\alpha + \varepsilon \eta^\alpha \label{tran} +\end{equation} +in first order of $\varepsilon.$ To transform the equations (\ref{PDEs}) +by (\ref{tran}), derivatives of $y^\alpha$ must be transformed, i.e. the part +linear in $\varepsilon$ must be determined. The corresponding formulas are +(see e.g. \cite{Olv}, \cite{Step}) +\begin{eqnarray} +\tilde{y}^\alpha_{j_1\ldots j_k} & = & +y^\alpha_{j_1\ldots j_k} + \varepsilon +\eta^\alpha_{j_1\ldots j_k} + O(\varepsilon^2) \nonumber \\ \vspace{3mm} +\eta^\alpha_{j_1\ldots j_{k-1}j_k} & = & + \frac{D \eta^\alpha_{j_1\ldots j_{k-1}}}{D x^k} - + y^\alpha_{ij_1\ldots j_{k-1}}\frac{D \xi^i}{D x^k} \label{recur} +\end{eqnarray} +where $D/Dx^k$ means total differentiation w.r.t.\ $x^k$ and +from now on lower latin indices of functions $y^\alpha,$ +(and later $u^\alpha$) +denote partial differentiation w.r.t.\ the independent variables $x^i,$ +(and later $v^i$). +The complete symmetry condition then takes the form +\begin{eqnarray} +X H_A & = & 0 \;\; \; \; \mbox{mod} \; \; \; H_A = 0\ \label{sbed1} \\ +X & = & \xi^i \frac{\partial}{\partial x^i} + + \eta^\alpha \frac{\partial}{\partial y^\alpha} + + \eta^\alpha_m \frac{\partial}{\partial y^\alpha_m} + + \eta^\alpha_{mn} \frac{\partial}{\partial y^\alpha_{mn}} + \ldots + + \eta^\alpha_{mn\ldots p} \frac{\partial}{\partial y^\alpha_{mn\ldots p}}. +\label{sbed2} +\end{eqnarray} +where mod $H_A = 0$ means that the original PDE-system is used to replace +some partial derivatives of $y^\alpha$ to reduce the number of independent +variables, because the symmetry condition (\ref{sbed1}) must be +fulfilled identically in $x^i, y^\alpha$ and all partial +derivatives of $y^\alpha.$ + +For point symmetries, $\xi^i, \eta^\alpha$ are functions of $x^j, +y^\beta$ and for contact symmetries they depend on $x^j, y^\beta$ and +$y^\beta_k.$ We restrict ourself to point symmetries as those are the only +ones that can be applied by the current version of the program {\tt APPLYSYM} +(see below). For literature about generalized symmetries see \cite{WHer}. + +Though the formulation of the symmetry conditions (\ref{sbed1}), +(\ref{sbed2}), (\ref{recur}) +is straightforward and handled in principle by all related +programs \cite{WHer}, the computational effort to formulate +the conditions (\ref{sbed1}) may cause problems if +the number of $x^i$ and $y^\alpha$ is high. This can +partially be avoided if at first only a few conditions are formulated +and solved such that the remaining ones are much shorter and quicker to +formulate. + +A first step in this direction is to investigate one PDE $H_A = 0$ +after another, as done in \cite{Cham}. Two methods to partition the +conditions for a single PDE are described by Bocharov/Bronstein +\cite{Alex} and Stephani \cite{Step}. + +In the first method only those terms of the symmetry condition +$X H_A = 0$ are calculated which contain +at least a derivative of $y^\alpha$ of a minimal order $m.$ +Setting coefficients +of these $u$-derivatives to zero provides symmetry conditions. Lowering the +minimal order $m$ successively then gradually provides all symmetry conditions. + +The second method is even more selective. If $H_A$ is of order $n$ +then only terms of the symmetry condition $X H_A = 0$ are generated which +contain $n'$th order derivatives of $y^\alpha.$ Furthermore these derivatives +must not occur in $H_A$ itself. They can therefore occur +in the symmetry condition +(\ref{sbed1}) only in +$\eta^\alpha_{j_1\ldots j_n},$ i.e. in the terms +\[\eta^\alpha_{j_1\ldots j_n} +\frac{\partial H_A}{\partial y^\alpha_{j_1\ldots j_n}}. \] +If only coefficients of $n'$th order derivatives of $y^\alpha$ need to be +accurate to formulate preliminary conditions +then from the total derivatives to be taken in +(\ref{recur}) only that part is performed which differentiates w.r.t.\ the +highest $y^\alpha$-derivatives. +This means, for example, to form only +$y^\alpha_{mnk} \partial/\partial y^\alpha_{mn} $ +if the expression, which is to be differentiated totally w.r.t.\ $x^k$, +contains at most second order derivatives of $y^\alpha.$ + +The second method is applied in {\tt LIEPDE}. +Already the formulation of the remaining conditions is speeded up +considerably through this iteration process. These methods can be applied if +systems of DEs or single PDEs of at least second order are investigated +concerning symmetries. +%--------------------------------------- +\subsection{The second step: Solving the symmetry conditions} +The second step in applying the whole method consists in solving the +determining conditions (\ref{sbed1}), (\ref{sbed2}), (\ref{recur}) +which are linear homogeneous PDEs for $\xi^i, \eta^\alpha$. The +complete solution of this system is not algorithmic any more because the +solution of a general linear PDE-system is as difficult as the solution of +its non-linear characteristic ODE-system which is not covered by algorithms +so far. + +Still algorithms are used successfully to simplify the PDE-system by +calculating +its standard normal form and by integrating exact PDEs +if they turn up in this simplification process \cite{LIEPDE}. +One problem in this respect, for example, +concerns the optimization of the symbiosis of both algorithms. By that we +mean the ranking of priorities between integrating, adding integrability +conditions and doing simplifications by substitutions - all depending on +the length of expressions and the overall structure of the PDE-system. +Also the extension of the class of PDEs which can be integrated exactly is +a problem to be pursuit further. + +The program {\tt LIEPDE} which formulates the symmetry conditions calls the +program {\tt CRACK} to solve them. This is done in a number of successive +calls in order to formulate and solve some first order PDEs of the +overdetermined system first and use their solution to formulate and solve the +next subset of conditions as described in the previous subsection. +Also, {\tt LIEPDE} can work on DEs that contain parametric constants and +parametric functions. An ansatz for the symmetry generators can be +formulated. For more details see \cite{LIEPDE} or \cite{WoBra}. + + +The call of {\tt LIEPDE} is \\ +{\tt LIEPDE}(\{{\it de}, {\it fun}, {\it var}\}, +\{{\it od}, {\it lp}, {\it fl}\}); \\ +where +\begin{itemize} +\item {\it de} is a single DE or a list of DEs in the form of a vanishing + expression or in the form $\ldots=\ldots\;\;$. +\item {\it fun} is the single function or the list of functions occuring + in {\it de}. +\item {\it var} is the single variable or the list of variables in {\it de}. +\item {\it od} is the order of the ansatz for $\xi, \eta.$ It is = 0 for +point symmetries and = 1 for contact symmetries (accepted by +{\tt LIEPDE} only in case of one ODE/PDE for one unknown function). +% and $>1$ for dynamical symmetries +%(only in case of one ODE for one unknown function) +\item If {\it lp} is $nil$ then the standard ansatz for $\xi^i, \eta^\alpha$ +is taken which is + \begin{itemize} + \item for point symmetries ({\it od} =0) is $\xi^i = \xi^i(x^j,y^\beta), + \eta^\alpha = \eta^\alpha(x^j,y^\beta)$ + \item for contact symmetries ({\it od} =1) is + $ \xi^i := \Omega_{u_i}, \;\;\; + \eta := u_i\Omega_{u_i} \; - \; \Omega, $ \\ + $\Omega:=\Omega(x^i, u, u_j)$ +%\item for dynamical symmetries ({\it od}$>1$) \\ +% $ \xi := \Omega,_{u'}, \;\;\; +% \eta := u'\Omega,_{u'} \; - \; \Omega, \;\;\; +% \Omega:=\Omega(x, u, u',\ldots, y^{({\it od}-1)})$ +% where {\it od} must be less than the order of the ODE. + \end{itemize} + + If {\it lp} is not $nil$ then {\it lp} is the ansatz for + $\xi^i, \eta^\alpha$ and must have the form + \begin{itemize} + \item for point symmetries + {\tt \{xi\_\mbox{$x1$} = ..., ..., eta\_\mbox{$u1$} = ..., ...\}} + where {\tt xi\_, eta\_ } + are fixed and $x1, \ldots, u1$ are to be replaced by the actual names + of the variables and functions. + \item otherwise {\tt spot\_ = ...} where the expression on the right hand + side is the ansatz for the Symmetry-POTential $\Omega.$ + \end{itemize} + +\item {\it fl} is the list of free functions in the ansatz +in case {\it lp} is not $nil.$ +\end{itemize} + + +The result of {\tt LIEPDE} is a list with 3 elements, each of which +is a list: +\[ \{\{{\it con}_1,{\it con}_2,\ldots\}, + \{{\tt xi}\__{\ldots}=\ldots, \ldots, + {\tt eta}\__{\ldots}=\ldots, \ldots\}, + \{{\it flist}\}\}. \] +The first list contains remaining unsolved symmetry conditions {\it con}$_i$. It +is the empty list \{\} if all conditions have been solved. The second list +gives the symmetry generators, i.e.\ expressions for $\xi_i$ and $\eta_j$. The +last list contains all free constants and functions occuring in the first +and second list. + +%That the automatic calculation of symmetries run in most practical cases +%is shown with the following example. It is insofar difficult, as many +%symmetries exist and the solution consequently more difficult is to deriv. +% +%--------------------------------------- +%\subsection{Example} +%For the following PDE-system, which takes its simplest form in the +%formalism of exterior forms: +% +%\begin{eqnarray*} +%0 & = & 3k_t,_{tt}-2k_t,_{xx}-2k_t,_{yy}-2k_t,_{zz}-k_x,_{tx}-2k_zk_x,_y \\ +% & & +2k_yk_x,_z-k_y,_{ty}+2k_zk_y,_x-2k_xk_y,_z-k_z,_{tz}-2k_yk_z,_x+2k_xk_z,_y \\ +%0 & = & k_t,_{tx}-2k_zk_t,_y+2k_yk_t,_z+2k_x,_{tt}-3k_x,_{xx}-2k_x,_{yy} \\ +% & & -2k_x,_{zz}+2k_zk_y,_t-k_y,_{xy}-2k_tk_y,_z-2k_yk_z,_t-k_z,_{xz}+2k_tk_z,_y \\ +%0 & = & k_t,_{ty}+2k_zk_t,_x-2k_xk_t,_z-2k_zk_x,_t-k_x,_{xy}+2k_tk_x,_z \\ +% & & +2k_y,_{tt}-2k_y,_{xx}-3k_y,_{yy}-2k_y,_{zz}+2k_xk_z,_t-2k_tk_z,_x-k_z,_{yz} \\ +%0 & = & k_t,_{tz}-2k_yk_t,_x+2k_xk_t,_y+2k_yk_x,_t-k_x,_{xz}-2k_tk_x,_y \\ +% & & -2k_xk_y,_t+2k_tk_y,_x-k_y,_{yz}+2k_z,_{tt}-2k_z,_{xx}-2k_z,_{yy}-3k_z,_{zz} +%\end{eqnarray*} +%--------------------------------------- +\subsection{The third step: Application of infinitesimal symmetries} +If infinitesimal symmetries have been found then +the program {\tt APPLYSYM} can use them for the following purposes: +\begin{enumerate} +\item Calculation of one symmetry variable and further similarity variables. +After transforming +the DE(-system) to these variables, the symmetry variable will not occur +explicitly any more. For ODEs this has the consequence that their order has +effectively been reduced. +\item Generalization of a special solution by one or more constants of +integration. +\end{enumerate} +Both methods are described in the following section. +%------------------------------------------------------------------------- +\section{Applying symmetries with {\tt APPLYSYM}} +%--------------------------------------- +\subsection{The first mode: Calculation of similarity and symmetry variables} +In the following we assume that a symmetry generator $X$, given +in (\ref{sbed2}), is known such that ODE(s)/PDE(s) $H_A=0$ +satisfy the symmetry condition (\ref{sbed1}). The aim is to +find new dependent functions $u^\alpha = u^\alpha(x^j,y^\beta)$ and +new independent variables $v^i = v^i(x^j,y^\beta),\;\; +1\leq\alpha,\beta\leq p,\;1\leq i,j \leq q$ +such that the symmetry generator +$X = \xi^i(x^j,y^\beta)\partial_{x^i} + + \eta^\alpha(x^j,y^\beta)\partial_{y^\alpha}$ +transforms to +\begin{equation} +X = \partial_{v^1}. \label{sbed3} +\end{equation} + +Inverting the above transformation to $x^i=x^i(v^j,u^\beta), +y^\alpha=y^\alpha(v^j,u^\beta)$ and setting +$H_A(x^i(v^j,u^\beta), y^\alpha(v^j,u^\beta),\ldots) = +h_A(v^j, u^\beta,\ldots)$ +this means that +\begin{eqnarray*} + 0 & = & X H_A(x^i,y^\alpha,y^\beta_j,\ldots)\;\;\; \mbox{mod} \;\;\; H_A=0 \\ + & = & X h_A(v^i,u^\alpha,u^\beta_j,\ldots)\;\;\; \mbox{mod} \;\;\; h_A=0 \\ + & = & \partial_{v^1}h_A(v^i,u^\alpha,u^\beta_j,\ldots)\;\;\; \mbox{mod} + \;\;\; h_A=0. +\end{eqnarray*} +Consequently, the variable $v^1$ does not occur explicitly in $h_A$. +In the case of an ODE(-system) $(v^1=v)$ +the new equations $0=h_A(v,u^\alpha,du^\beta/dv,\ldots)$ +are then of lower total order +after the transformation $z = z(u^1) = du^1/dv$ with now $z, u^2,\ldots u^p$ +as unknown functions and $u^1$ as independent variable. + +The new form (\ref{sbed3}) of $X$ leads directly to conditions for the +symmetry variable $v^1$ and the similarity variables +$v^i|_{i\neq 1}, u^\alpha$ (all functions of $x^k,y^\gamma$): +\begin{eqnarray} + X v^1 = 1 & = & \xi^i(x^k,y^\gamma)\partial_{x^i}v^1 + + \eta^\alpha(x^k,y^\gamma)\partial_{y^\alpha}v^1 \label{ql1} \\ + X v^j|_{j\neq 1} = X u^\beta = 0 & = & + \xi^i(x^k,y^\gamma)\partial_{x^i}u^\beta + + \eta^\alpha(x^k,y^\gamma)\partial_{y^\alpha}u^\beta \label{ql2} +\end{eqnarray} +The general solutions of (\ref{ql1}), (\ref{ql2}) involve free functions +of $p+q-1$ arguments. From the general solution of equation (\ref{ql2}), +$p+q-1$ functionally independent special solutions have to be selected +($v^2,\ldots,v^p$ and $u^1,\ldots,u^q$), +whereas from (\ref{ql1}) only one solution $v^1$ is needed. +Together, the expressions for the symmetry and similarity variables must +define a non-singular transformation $x,y \rightarrow u,v$. + +Different special solutions selected at this stage +will result in different +resulting DEs which are equivalent under point transformations but may +look quite differently. A transformation that is more difficult than another +one will in general +only complicate the new DE(s) compared with the simpler transformation. +We therefore seek the simplest possible special +solutions of (\ref{ql1}), (\ref{ql2}). They also +have to be simple because the transformation has to be inverted to solve for +the old variables in order to do the transformations. + +The following steps are performed in the corresponding mode of the +program {\tt APPLYSYM}: +\begin{itemize} +\item The user is asked to specify a symmetry by selecting one symmetry +from all the known symmetries or by specifying a linear combination of them. +\item Through a call of the procedure {\tt QUASILINPDE} (described in a later +section) the two linear first order PDEs (\ref{ql1}), (\ref{ql2}) are +investigated and, if possible, solved. +\item From the general solution of (\ref{ql1}) 1 special solution +is selected and from (\ref{ql2}) $p+q-1$ special +solutions are selected which should be as simple as possible. +\item The user is asked whether the symmetry variable should be one of the +independent variables (as it has been assumed so far) or one of the new +functions (then only derivatives of this function and not the function itself +turn up in the new DE(s)). +\item Through a call of the procedure {\tt DETRAFO} the transformation +$x^i,y^\alpha \rightarrow v^j,u^\beta$ of the DE(s) $H_A=0$ is finally done. +\item The program returns to the starting menu. +\end{itemize} +%--------------------------------------- +\subsection{The second mode: Generalization of special solutions} +A second application of infinitesimal symmetries is the generalization +of a known special solution given in implicit form through +$0 = F(x^i,y^\alpha)$. If one knows a symmetry variable $v^1$ and +similarity variables $v^r, u^\alpha,\;\;2\leq r\leq p$ then +$v^1$ can be shifted by a constant $c$ because of +$\partial_{v^1}H_A = 0$ and +therefore the DEs $0 = H_A(v^r,u^\alpha,u^\beta_j,\ldots)$ +are unaffected by the shift. Hence from +\[0 = F(x^i, y^\alpha) = F(x^i(v^j,u^\beta), y^\alpha(v^j,u^\beta)) = +\bar{F}(v^j,u^\beta)\] follows that +\[ 0 = \bar{F}(v^1+c,v^r,u^\beta) = +\bar{F}(v^1(x^i,y^\alpha)+c, v^r(x^i,y^\alpha), u^\beta(x^i,y^\alpha))\] +defines implicitly a generalized solution $y^\alpha=y^\alpha(x^i,c)$. + +This generalization works only if $\partial_{v^1}\bar{F} \neq 0$ and +if $\bar{F}$ does not already have +a constant additive to $v^1$. + +The method above needs to know $x^i=x^i(u^\beta,v^j),\; +y^\alpha=y^\alpha(u^\beta,v^j)$ \underline{and} +$u^\alpha = u^\alpha(x^j,y^\beta), v^\alpha = v^\alpha(x^j,y^\beta)$ +which may be practically impossible. +Better is, to integrate $x^i,y^\alpha$ along $X$: +\begin{equation} +\frac{d\bar{x}^i}{d\varepsilon} = \xi^i(\bar{x}^j(\varepsilon), + \bar{y}^\beta(\varepsilon)), \;\;\;\;\; +\frac{d\bar{y}^\alpha}{d\varepsilon} = \eta^\alpha(\bar{x}^j(\varepsilon), + \bar{y}^\beta(\varepsilon)) +\label{ODEsys} +\end{equation} +with initial values $\bar{x}^i = x^i, \bar{y}^\alpha = y^\alpha$ +for $\varepsilon = 0.$ +(This ODE-system is the characteristic system of (\ref{ql2}).) + +Knowing only the finite transformations +\begin{equation} +\bar{x}^i = \bar{x}^i(x^j,y^\beta,\varepsilon),\;\; +\bar{y}^\alpha = \bar{y}^\alpha(x^j,y^\beta,\varepsilon) \label{ODEsol} +\end{equation} +gives immediately the inverse transformation +$\bar{x}^i = \bar{x}^i(x^j,y^\beta,\varepsilon),\;\; +\bar{y}^\alpha = \bar{y}^\alpha(x^j,y^\beta,\varepsilon)$ +just by $\varepsilon \rightarrow -\varepsilon$ and renaming +$x^i,y^\alpha \leftrightarrow \bar{x}^i,\bar{y}^\alpha.$ + +The special solution $0 = F(x^i,y^\alpha)$ +is generalized by the new constant +$\varepsilon$ through +\[ 0 = F(x^i,y^\alpha) = F(x^i(\bar{x}^j,\bar{y}^\beta,\varepsilon), + y^\alpha(\bar{x}^j,\bar{y}^\beta,\varepsilon)) \] +after dropping the $\bar{ }$. + +The steps performed in the corresponding mode of the +program {\tt APPLYSYM} show features of both techniques: +\begin{itemize} +\item The user is asked to specify a symmetry by selecting one symmetry +from all the known symmetries or by specifying a linear combination of them. +\item The special solution to be generalized and the name of the new +constant have to be put in. +\item Through a call of the procedure {\tt QUASILINPDE}, the PDE (\ref{ql1}) +is solved which amounts to a solution of its characteristic ODE system +(\ref{ODEsys}) where $v^1=\varepsilon$. +\item {\tt QUASILINPDE} returns a list of constant expressions +\begin{equation} +c_i = c_i(x^k, y^\beta, \varepsilon),\;\;1\leq i\leq p+q +\end{equation} +which are solved for +$x^j=x^j(c_i,\varepsilon),\;\; y^\alpha=y^\alpha(c_i,\varepsilon)$ +to obtain the generalized solution through +\[ 0 = F(x^j, y^\alpha) + = F( x^j(c_i(x^k, y^\beta, 0), \varepsilon)), + y^\alpha(c_i(x^k, y^\beta, 0), \varepsilon))). \] +\item The new solution is availabe for further generalizations w.r.t.\ other +symmetries. +\end{itemize} +If one would like to generalize a given special solution with $m$ new +constants because $m$ symmetries are known, then one could run the whole +program $m$ times, each time with a different symmetry or one could run the +program once with a linear combination of $m$ symmetry generators which +again is a symmetry generator. Running the program once adds one constant +but we have in addition $m-1$ arbitrary constants in the linear combination +of the symmetries, so $m$ new constants are added. +Usually one will generalize the solution gradually to make solving +(\ref{ODEsys}) gradually more difficult. +%--------------------------------------- +\subsection{Syntax} +The call of {\tt APPLYSYM} is +{\tt APPLYSYM}(\{{\it de}, {\it fun}, {\it var}\}, \{{\it sym}, {\it cons}\}); +\begin{itemize} +\item {\it de} is a single DE or a list of DEs in the form of a vanishing + expression or in the form $\ldots=\ldots\;\;$. +\item {\it fun} is the single function or the list of functions occuring + in {\it de}. +\item {\it var} is the single variable or the list of variables in {\it de}. +\item {\it sym} is a linear combination of all symmetries, each with a + different constant coefficient, in form of a list of the $\xi^i$ and + $\eta^\alpha$: \{xi\_\ldots=\ldots,\ldots,eta\_\ldots=\ldots,\ldots\}, + where the indices after `xi\_' are the variable names and after `eta\_' + the function names. +\item {\it cons} is the list of constants in {\it sym}, one constant for each + symmetry. +\end{itemize} +The list that is the first argument of {\tt APPLYSYM} is the same as the +first argument of {\tt LIEPDE} and the +second argument is the list that {\tt LIEPDE} returns without its first +element (the unsolved conditions). An example is given below. + +What {\tt APPLYSYM} returns depends on the last performed modus. +After modus 1 the return is \\ +\{\{{\it newde}, {\it newfun}, {\it newvar}\}, {\it trafo}\} \\ +where +\begin{itemize} +\item {\it newde} lists the transformed equation(s) +\item {\it newfun} lists the new function name(s) +\item {\it newvar} lists the new variable name(s) +\item {\it trafo} lists the transformations $x^i=x^i(v^j,u^\beta), + y^\alpha=y^\alpha(v^j,u^\beta)$ +\end{itemize} +After modus 2, {\tt APPLYSYM} returns the generalized special solution. +%--------------------------------------- +\subsection{Example: A second order ODE} +Weyl's class of solutions of Einsteins field equations consists of +axialsymmetric time independent metrics of the form +\begin{equation} +{\rm{d}} s^2 = e^{-2 U} \left[ e^{2 k} \left( \rm{d} \rho^2 + \rm{d} +z^2 \right)+\rho^2 \rm{d} \varphi^2 \right] - e^{2 U} \rm{d} t^2, +\end{equation} +where $U$ and $k$ are functions of $\rho$ and $z$. If one is interested in +generalizing these solutions to have a time dependence then the resulting +DEs can be transformed such that one longer third order ODE for $U$ results +which contains only $\rho$ derivatives \cite{Markus}. Because $U$ appears +not alone but only as derivative, a substitution +\begin{equation} +g = dU/d\rho \label{g1dgl} +\end{equation} +lowers the order and the introduction of a function +\begin{equation} +h = \rho g - 1 \label{g2dgl} +\end{equation} +simplifies the ODE to +\begin{equation} +0 = 3\rho^2h\,h'' +-5\rho^2\,h'^2+5\rho\,h\,h'-20\rho\,h^3h'-20\,h^4+16\,h^6+4\,h^2. \label{hdgl} +\end{equation} +where $'= d/d\rho$. +Calling {\tt LIEPDE} through +\small \begin{verbatim} +depend h,r; +prob:={{-20*h**4+16*h**6+3*r**2*h*df(h,r,2)+5*r*h*df(h,r) + -20*h**3*r*df(h,r)+4*h**2-5*r**2*df(h,r)**2}, + {h}, {r}}; +sym:=liepde(prob,{0,nil,nil}); +end; \end{verbatim} \normalsize +gives \small \begin{verbatim} + 3 2 +sym := {{}, {xi_r= - c10*r - c11*r, eta_h=c10*h*r }, {c10,c11}}. +\end{verbatim} \normalsize +All conditions have been solved because the first element of {\tt sym} +is $\{\}$. The two existing symmetries are therefore +\begin{equation} + - \rho^3 \partial_{\rho} + h \rho^2 \,\partial_{h} \;\;\;\;\;\;\mbox{and} + \;\;\;\;\;\;\rho \partial_{\rho}. +\end{equation} +Corresponding finite +transformations can be calculated with {\tt APPLYSYM} through +\small \begin{verbatim} +newde:=applysym(de,rest sym); +\end{verbatim} \normalsize +The interactive session is given below with the user input following +the prompt `{\tt Input:3:}' or following `?'. (Empty lines have been deleted.) +\small \begin{verbatim} +Do you want to find similarity and symmetry variables (enter `1;') +or generalize a special solution with new parameters (enter `2;') +or exit the program (enter `;') +Input:3: 1; +\end{verbatim} \normalsize +We enter `1;' because we want to reduce dependencies by finding similarity +variables and one symmetry variable and then doing the transformation such +that the symmetry variable does not explicitly occur in the DE. +\small \begin{verbatim} +---------------------- The 1. symmetry is: + 3 +xi_r= - r + 2 +eta_h=h*r +---------------------- The 2. symmetry is: +xi_r= - r +---------------------- +Which single symmetry or linear combination of symmetries +do you want to apply? "$ +Enter an expression with `sy_(i)' for the i'th symmetry. +sy_(1); +\end{verbatim} \normalsize +We could have entered `sy\_(2);' or a combination of both +as well with the calculation running then +differently. +\small \begin{verbatim} +The symmetry to be applied in the following is + 3 2 +{xi_r= - r ,eta_h=h*r } +Enter the name of the new dependent variables: +Input:3: u; +Enter the name of the new independent variables: +Input:3: v; +\end{verbatim} \normalsize +This was the input part, now the real calculation starts. +\small \begin{verbatim} +The ODE/PDE (-system) under investigation is : + 2 2 2 3 +0 = 3*df(h,r,2)*h*r - 5*df(h,r) *r - 20*df(h,r)*h *r + 6 4 2 + + 5*df(h,r)*h*r + 16*h - 20*h + 4*h +for the function(s) : h. +It will be looked for a new dependent variable u +and an independent variable v such that the transformed +de(-system) does not depend on u or v. +1. Determination of the similarity variable + 2 +The quasilinear PDE: 0 = r *(df(u_,h)*h - df(u_,r)*r). +The equivalent characteristic system: + 3 +0= - df(u_,r)*r + 2 +0= - r *(df(h,r)*r + h) +for the functions: h(r) u_(r). +\end{verbatim} \normalsize +The PDE is equation (\ref{ql2}). +\small \begin{verbatim} +The general solution of the PDE is given through +0 = ff(u_,h*r) +with arbitrary function ff(..). +A suggestion for this function ff provides: +0 = - h*r + u_ +Do you like this choice? (Y or N) +?y +\end{verbatim} \normalsize +For the following calculation only a single special solution of the PDE is +necessary +and this has to be specified from the general solution by choosing a special +function {\tt ff}. (This function is called {\tt ff} to prevent a clash with +names of user variables/functions.) In principle any choice of {\tt ff} would +work, if it defines a non-singular coordinate transformation, i.e.\ here $r$ +must be a function of $u\_$. If we have $q$ independent variables and +$p$ functions of them then {\tt ff} has $p+q$ arguments. Because of the +condition $0 = ${\tt ff} one has essentially the freedom of choosing a function +of $p+q-1$ arguments freely. This freedom is also necessary to select $p+q-1$ +different functions {\tt ff} and to find as many functionally independent +solutions $u\_$ which all become the new similarity variables. $q$ of them +become the new functions $u^\alpha$ and $p-1$ of them the new variables +$v^2,\ldots,v^p$. Here we have $p=q=1$ (one single ODE). + +Though the program could have done that alone, once the general solution +{\tt ff(..)} is known, the user can interfere here to enter a simpler solution, +if possible. +\small \begin{verbatim} +2. Determination of the symmetry variable + 2 3 +The quasilinear PDE: 0 = df(u_,h)*h*r - df(u_,r)*r - 1. +The equivalent characteristic system: + 3 +0=df(r,u_) + r + 2 +0=df(h,u_) - h*r +for the functions: r(u_) h(u_) . +New attempt with a different independent variable +The equivalent characteristic system: + 2 +0=df(u_,h)*h*r - 1 + 2 +0=r *(df(r,h)*h + r) +for the functions: r(h) u_(h) . +The general solution of the PDE is given through + 2 2 2 + - 2*h *r *u_ + h +0 = ff(h*r,--------------------) + 2 +with arbitrary function ff(..). +A suggestion for this function ff(..) yields: + 2 2 + h *( - 2*r *u_ + 1) +0 = --------------------- + 2 +Do you like this choice? (Y or N) +?y +\end{verbatim} \normalsize +Similar to above. +\small \begin{verbatim} +The suggested solution of the algebraic system which will +do the transformation is: + sqrt(v)*sqrt(2) +{h=sqrt(v)*sqrt(2)*u,r=-----------------} + 2*v +Is the solution ok? (Y or N) +?y +In the intended transformation shown above the dependent +variable is u and the independent variable is v. +The symmetry variable is v, i.e. the transformed expression +will be free of v. +Is this selection of dependent and independent variables ok? (Y or N) +?n +\end{verbatim} \normalsize +We so far assumed that the symmetry variable is one of the new variables, but, +of course we also could choose it to be one of the new functions. +If it is one of the functions then only derivatives of this function occur +in the new DE, not the function itself. If it is one of the variables then +this variable will not occur explicitly. + +In our case we prefer (without strong reason) to have the function as +symmetry variable. We therefore answered with `no'. As a consequence, $u$ and +$v$ will exchange names such that still all new functions have the name $u$ +and the new variables have name $v$: +\small \begin{verbatim} +Please enter a list of substitutions. For example, to +make the variable, which is so far call u1, to an +independent variable v2 and the variable, which is +so far called v2, to an dependent variable u1, +enter: `{u1=v2, v2=u1};' +Input:3: {u=v,v=u}; + +The transformed equation which should be free of u: + 3 6 2 3 +0=3*df(u,v,2)*v - 16*df(u,v) *v - 20*df(u,v) *v + 5*df(u,v) +Do you want to find similarity and symmetry variables (enter `1;') +or generalize a special solution with new parameters (enter `2;') +or exit the program (enter `;') +Input:3: ; +\end{verbatim} +We stop here. The following is returned from our {\tt APPLYSYM} call: +\small \begin{verbatim} + 3 6 2 3 +{{{3*df(u,v,2)*v - 16*df(u,v) *v - 20*df(u,v) *v + 5*df(u,v)}, + {u}, + {v}}, + sqrt(u)*sqrt(2) + {r=-----------------, h=sqrt(u)*sqrt(2)*v }} + 2*u +\end{verbatim} \normalsize +The use of {\tt APPLYSYM} effectively provided us the finite +transformation +\begin{equation} + \rho=(2\,u)^{-1/2},\;\;\;\;\;h=(2\,u)^{1/2}\,v \label{trafo1}. +\end{equation} +and the new ODE +\begin{equation} +0 = 3u''v - 16u'^3v^6 - 20u'^2v^3 + 5u' \label{udgl} +\end{equation} +where $u=u(v)$ and $'=d/dv.$ +Using one symmetry we reduced the 2.\,order ODE (\ref{hdgl}) +to a first order ODE (\ref{udgl}) for $u'$ plus one +integration. The second symmetry can be used to reduce the remaining ODE +to an integration too by introducing a variable $w$ through $v^3d/dv = d/dw$, +i.e. $w = -1/(2v^2)$. With +\begin{equation} +p=du/dw \label{udot} +\end{equation} +the remaining ODE is +\[0 = 3\,w\,\frac{dp}{dw} + 2\,p\,(p+1)(4\,p+1) \] +with solution +\[ \tilde{c}w^{-2}/4 = \tilde{c}v^4 = \frac{p^3(p+1)}{(4\,p+1)^4},\;\;\; + \tilde{c}=const. \] +Writing (\ref{udot}) as $p = v^3(du/dp)/(dv/dp)$ we get $u$ by integration +and with (\ref{trafo1}) further a parametric solution for $\rho,h$: +\begin{eqnarray} +\rho & = & \left(\frac{3c_1^2(2p-1)}{p^{1/2}(p+1)^{1/2}}+c_2\right)^{-1/2} \\ +h & = & \frac{(c_2p^{1/2}(p+1)^{1/2}+6c_1^2p-3c_1^2)^{1/2}p^{1/2}}{c_1(4p+1)} +\end{eqnarray} +where $c_1, c_2 = const.$ and $c_1=\tilde{c}^{1/4}.$ Finally, the metric +function $U(p)$ is obtained as an integral from (\ref{g1dgl}),(\ref{g2dgl}). +%--------------------------------------- +\subsection{Limitations of {\tt APPLYSYM}} +Restrictions of the applicability of the program {\tt APPLYSYM} result +from limitations of the program {\tt QUASILINPDE} described in a section below. +Essentially this means that symmetry generators may only be polynomially +non-linear in $x^i, y^\alpha$. +Though even then the solvability can not be guaranteed, the +generators of Lie-symmetries are mostly very simple such that the +resulting PDE (\ref{PDE}) and the corresponding characteristic +ODE-system have good chances to be solvable. + +Apart from these limitations implied through the solution of differential +equations with {\tt CRACK} and algebraic equations with {\tt SOLVE} +the program {\tt APPLYSYM} itself is free of restrictions, +i.e.\ if once new versions of {\tt CRACK, SOLVE} +would be available then {\tt APPLYSYM} would not have to be changed. + +Currently, whenever a computational step could not be performed +the user is informed and has the possibility of entering interactively +the solution of the unsolved algebraic system or the unsolved linear PDE. +%------------------------------------------------------------------------- +\section{Solving quasilinear PDEs} +%--------------------------------------- +\subsection{The content of {\tt QUASILINPDE}} +The generalization of special solutions of DEs as well as the computation of +similarity and symmetry variables involve the general solution of single +first order linear PDEs. +The procedure {\tt QUASILINPDE} is a general procedure +aiming at the general solution of +PDEs +\begin{equation} + a_1(w_i,\phi)\phi_{w_1} + a_2(w_i,\phi)\phi_{w_2} + \ldots + + a_n(w_i,\phi)\phi_{w_n} = b(w_i,\phi) \label{PDE} +\end{equation} +in $n$ independent variables $w_i, i=1\ldots n$ for one unknown function +$\phi=\phi(w_i)$. +\begin{enumerate} +\item +The first step in solving a quasilinear PDE (\ref{PDE}) +is the formulation of the corresponding characteristic ODE-system +\begin{eqnarray} +\frac{dw_i}{d\varepsilon} & = & a_i(w_j,\phi) \label{char1} \\ +\frac{d\phi}{d\varepsilon} & = & b(w_j,\phi) \label{char2} +\end{eqnarray} +for $\phi, w_i$ regarded now as functions of one variable $\varepsilon$. + +Because the $a_i$ and $b$ do not depend explicitly on $\varepsilon$, one of the +equations (\ref{char1}),(\ref{char2}) with non-vanishing right hand side +can be used to divide all others through it and by that having a system +with one less ODE to solve. +If the equation to divide through is one of +(\ref{char1}) then the remaining system would be +\begin{eqnarray} +\frac{dw_i}{dw_k} & = & \frac{a_i}{a_k} , \;\;\;i=1,2,\ldots k-1,k+1,\ldots n + \label{char3} \\ +\frac{d\phi}{dw_k} & = & \frac{b}{a_k} \label{char4} +\end{eqnarray} +with the independent variable $w_k$ instead of $\varepsilon$. +If instead we divide through equation +(\ref{char2}) then the remaining system would be +\begin{eqnarray} +\frac{dw_i}{d\phi} & = & \frac{a_i}{b} , \;\;\;i=1,2,\ldots n + \label{char3a} +\end{eqnarray} +with the independent variable $\phi$ instead of $\varepsilon$. + +The equation to divide through is chosen by a +subroutine with a heuristic to find the ``simplest'' non-zero +right hand side ($a_k$ or $b$), i.e.\ one which +\begin{itemize} +\item is constant or +\item depends only on one variable or +\item is a product of factors, each of which depends only on +one variable. +\end{itemize} + +One purpose of this division is to reduce the number of ODEs by one. +Secondly, the general solution of (\ref{char1}), (\ref{char2}) involves +an additive constant to $\varepsilon$ which is not relevant and would +have to be set to zero. By dividing through one ODE we eliminate +$\varepsilon$ and lose the problem of identifying this constant in the +general solution before we would have to set it to zero. + +\item % from enumerate +To solve the system (\ref{char3}), (\ref{char4}) or (\ref{char3a}), +the procedure {\tt CRACK} is called. +Although being designed primarily for the solution of overdetermined +PDE-systems, {\tt CRACK} can also be used to solve simple not +overdetermined ODE-systems. This solution +process is not completely algorithmic. Improved versions of {\tt CRACK} +could be used, without making any changes of {\tt QUASILINPDE} +necessary. + +If the characteristic ODE-system can not be solved in the form +(\ref{char3}), (\ref{char4}) or (\ref{char3a}) +then successively all other ODEs of (\ref{char1}), (\ref{char2}) +with non-vanishing right hand side are used for division until +one is found +such that the resulting ODE-system can be solved completely. +Otherwise the PDE can not be solved by {\tt QUASILINPDE}. + +\item % from enumerate +If the characteristic ODE-system (\ref{char1}), (\ref{char2}) has been +integrated completely and in full generality to the implicit solution +\begin{equation} +0 = G_i(\phi, w_j, c_k, \varepsilon),\;\; +i,k=1,\ldots,n+1,\;\;j=1,\ldots,n \label{charsol1} +\end{equation} +then according to the general theory for solving first order PDEs, +$\varepsilon$ has +to be eliminated from one of the equations and to be substituted in the +others to have left $n$ equations. +Also the constant that turns up additively to $\varepsilon$ +is to be set to zero. Both tasks are automatically +fulfilled, if, as described above, $\varepsilon$ is already eliminated +from the beginning by dividing all equations of (\ref{char1}), +(\ref{char2}) +through one of them. + +On either way one ends up with $n$ equations +\begin{equation} +0=g_i(\phi,w_j,c_k),\;\;i,j,k=1\ldots n \label{charsol2} +\end{equation} +involving $n$ constants $c_k$. + +The final step is to solve (\ref{charsol2}) for the $c_i$ to obtain +\begin{equation} +c_i = c_i(\phi, w_1,\ldots ,w_n) \;\;\;\;\;i=1,\ldots n . \label{cons} +\end{equation} +The final solution $\phi = \phi(w_i)$ of the PDE (\ref{PDE}) is then +given implicitly through +\[ 0 = F(c_1(\phi,w_i),c_2(\phi,w_i),\ldots,c_n(\phi,w_i)) \] +where $F$ is an arbitrary function with $n$ arguments. +\end{enumerate} +%--------------------------------------- +\subsection{Syntax} +The call of {\tt QUASILINPDE} is \\ +{\tt QUASILINPDE}({\it de}, {\it fun}, {\it varlist}); +\begin{itemize} +\item +{\it de} is the differential expression which vanishes due to the PDE +{\it de}$\; = 0$ or, {\it de} may be the differential equation itself in the +form $\;\;\ldots = \ldots\;\;$. +\item +{\it fun} is the unknown function. +\item +{\it varlist} is the list of variables of {\it fun}. +\end{itemize} +The result of {\tt QUASILINPDE} is a list of general solutions +\[ \{{\it sol}_1, {\it sol}_2, \ldots \}. \] +If {\tt QUASILINPDE} can not solve the PDE then it returns $\{\}$. +Each solution ${\it sol}_i$ is a list of expressions +\[ \{{\it ex}_1, {\it ex}_2, \ldots \} \] +such that the dependent function ($\phi$ in (\ref{PDE})) is determined +implicitly through an arbitrary function $F$ and the algebraic +equation \[ 0 = F({\it ex}_1, {\it ex}_2, \ldots). \] +%--------------------------------------- +\subsection{Examples} +{\em Example 1:}\\ +To solve the quasilinear first order PDE \[1 = xu,_x + uu,_y - zu,_z\] +for the function $u = u(x,y,z),$ the input would be +\small \begin{verbatim} +depend u,x,y,z; +de:=x*df(u,x)+u*df(u,y)-z*df(u,z) - 1; +varlist:={x,y,z}; +QUASILINPDE(de,u,varlist); +\end{verbatim} \normalsize +In this example the procedure returns +\[\{ \{ x/e^u, ze^u, u^2 - 2y \} \},\] +i.e. there is one general solution (because the outer list has only one +element which itself is a list) and $u$ is given implicitly through +the algebraic equation +\[ 0 = F(x/e^u, ze^u, u^2 - 2y)\] +with arbitrary function $F.$ \\ +{\em Example 2:}\\ +For the linear inhomogeneous PDE +\[ 0 = y z,_x + x z,_y - 1, \;\;\;\;\mbox{for}\;\;\;\;z=z(x,y)\] +{\tt QUASILINPDE} returns the result that for an arbitrary function $F,$ the +equation +\[ 0 = F\left(\frac{x+y}{e^z},e^z(x-y)\right) \] +defines the general solution for $z$. \\ +{\em Example 3:}\\ +For the linear inhomogeneous PDE (3.8) from \cite{KamkePDE} +\[ 0 = x w,_x + (y+z)(w,_y - w,_z), \;\;\;\;\mbox{for}\;\;\;\;w=w(x,y,z)\] +{\tt QUASILINPDE} returns the result +that for an arbitrary function $F,$ the equation +\[ 0 = F\left(w, \;y+z, \;\ln(x)(y+z)-y\right) \] +defines the general solution for $w$, i.e.\ for any function $f$ +\[ w = f\left(y+z, \;\ln(x)(y+z)-y\right) \] +solves the PDE. +%--------------------------------------- +\subsection{Limitations of {\tt QUASILINPDE}} +One restriction on the applicability of {\tt QUASILINPDE} results from +the program {\tt CRACK} which tries to solve the +characteristic ODE-system of the PDE. So far {\tt CRACK} can be +applied only to polynomially non-linear DE's, i.e.\ the characteristic +ODE-system (\ref{char3}),(\ref{char4}) or (\ref{char3a}) may +only be polynomially non-linear, i.e.\ in the PDE (\ref{PDE}) +the expressions $a_i$ and $b$ may only be rational in $w_j,\phi$. + +The task of {\tt CRACK} is simplified as (\ref{charsol1}) does not have to +be solved for $w_j, \phi$. On the other hand (\ref{charsol1}) has to be +solved for the $c_i$. This gives a +second restriction coming from the REDUCE function {\tt SOLVE}. +Though {\tt SOLVE} can be applied +to polynomial and transzendential equations, again no guarantee for +solvability can be given. +%------------------------------------------------------------------------- +\section{Transformation of DEs} +%--------------------------------------- +\subsection{The content of {\tt DETRAFO}} +Finally, after having found the finite transformations, +the program {\tt APPLYSYM} calls the procedure +{\tt DETRAFO} to perform the transformations. {\tt DETRAFO} +can also be used alone to do point- or higher order transformations +which involve a considerable computational effort if the +differential order of the expression to be transformed is high and +if many dependent and independent variables are involved. +This might be especially useful if one wants to experiment +and try out different coordinate transformations interactively, +using {\tt DETRAFO} as standalone procedure. + +To run {\tt DETRAFO}, the old functions $y^{\alpha}$ and old +variables $x^i$ must be +known explicitly in terms of algebraic or +differential expressions of the new functions $u^{\beta}$ +and new variables $v^j$. Then for point transformations the identity +\begin{eqnarray} +dy^{\alpha} & = & \left(y^{\alpha},_{v^i} + + y^{\alpha},_{u^{\beta}}u^{\beta},_{v^i}\right) dv^i \\ + & = & y^{\alpha},_{x^j}dx^j \\ + & = & y^{\alpha},_{x^j}\left(x^j,_{v^i} + + x^j,_{u^{\beta}}u^{\beta},_{v^i}\right) dv^i +\end{eqnarray} +provides the transformation +\begin{equation} +y^{\alpha},_{x^j} = \frac{dy^\alpha}{dv^i}\cdot + \left(\frac{dx^j}{dv^i}\right)^{-1} \label{trafo} +\end{equation} +with {\it det}$\left(dx^j/dv^i\right) \neq 0$ because of the regularity +of the transformation which is checked by {\tt DETRAFO}. Non-regular +transformations are not performed. + +{\tt DETRAFO} is not restricted to point transformations. +In the case of +contact- or higher order transformations, the total +derivatives $dy^{\alpha}/dv^i$ and $dx^j/dv^i$ then only include all +$v^i-$ derivatives of $u^{\beta}$ which occur in +\begin{eqnarray*} +y^{\alpha} & = & y^{\alpha}(v^i,u^{\beta},u^{\beta},_{v^j},\ldots) \\ +x^k & = & x^k(v^i,u^{\beta},u^{\beta},_{v^j},\ldots). +\end{eqnarray*} +%--------------------------------------- +\subsection{Syntax} +The call of {\tt DETRAFO} is +\begin{tabbing} +{\tt DETRAFO}(\=\{{\it ex}$_1$, {\it ex}$_2$, \ldots , {\it ex}$_m$\}, \\ + \>\{{\it ofun}$_1=${\it fex}$_1$, {\it ofun}$_2=${\it fex}$_2$, + \ldots ,{\it ofun}$_p=${\it fex}$_p$\}, \\ + \>\{{\it ovar}$_1=${\it vex}$_1$, {\it ovar}$_2=${\it vex}$_2$, \ldots , + {\it ovar}$_q=${\it vex}$_q$\}, \\ + \>\{{\it nfun}$_1$, {\it nfun}$_2$, \ldots , {\it nfun}$_p$\},\\ + \>\{{\it nvar}$_1$, {\it nvar}$_2$, \ldots , {\it nvar}$_q$\}); +\end{tabbing} +where $m,p,q$ are arbitrary. +\begin{itemize} +\item +The {\it ex}$_i$ are differential expressions to be transformed. +\item +The second list is the list of old functions {\it ofun} expressed +as expressions {\it fex} in terms +of new functions {\it nfun} and new independent variables {\it nvar}. +\item +Similarly the third list expresses the old independent variables {\it ovar} +as expressions {\it vex} in terms of new functions +{\it nfun} and new independent variables {\it nvar}. +\item +The last two lists include the new functions {\it nfun} +and new independent variables {\it nvar}. +\end{itemize} +Names for {\it ofun, ovar, nfun} and {\it nvar} can be arbitrarily +chosen. + +As the result {\tt DETRAFO} returns the first argument of its input, +i.e.\ the list +\[\{{\it ex}_1, {\it ex}_2, \ldots , {\it ex}_m\}\] +where all ${\it ex}_i$ are transformed. +%--------------------------------------- +\subsection{Limitations of {\tt DETRAFO}} +The only requirement is that +the old independent variables $x^i$ and old functions $y^\alpha$ must be +given explicitly in terms of new variables $v^j$ and new functions $u^\beta$ +as indicated in the syntax. +Then all calculations involve only differentiations and basic algebra. +%------------------------------------------------------------------------- +\section{Availability} +The programs run under {\tt REDUCE 3.4.1} or later versions and are available +by anonymous ftp from 138.37.80.15, directory {\tt ~ftp/pub/crack}. +%The manual file {\tt APPLYSYM.TEX} gives more details on the syntax. + +\begin{thebibliography}{99} +\bibitem{WHer} W.\,Hereman, Chapter 13 in vol 3 of the CRC Handbook of +Lie Group Analysis of Differential Equations, Ed.: N.H.\,Ibragimov, +CRC Press, Boca Raton, Florida (1995). +Systems described in this paper are among others: \\ +DELiA (Alexei Bocharov et.al.) Pascal \\ +DIFFGROB2 (Liz Mansfield) Maple \\ +DIMSYM (James Sherring and Geoff Prince) REDUCE \\ +HSYM (Vladimir Gerdt) Reduce \\ +LIE (V. Eliseev, R.N. Fedorova and V.V. Kornyak) Reduce \\ +LIE (Alan Head) muMath \\ +Lie (Gerd Baumann) Mathematica \\ +LIEDF/INFSYM (Peter Gragert and Paul Kersten) Reduce \\ +Liesymm (John Carminati, John Devitt and Greg Fee) Maple \\ +MathSym (Scott Herod) Mathematica \\ +NUSY (Clara Nucci) Reduce \\ +PDELIE (Peter Vafeades) Macsyma \\ +SPDE (Fritz Schwarz) Reduce and Axiom \\ +SYM\_DE (Stanly Steinberg) Macsyma \\ +Symmgroup.c (Dominique Berube and Marc de Montigny) Mathematica \\ +STANDARD FORM (Gregory Reid and Alan Wittkopf) Maple \\ +SYMCAL (Gregory Reid) Macsyma and Maple \\ +SYMMGRP.MAX (Benoit Champagne, Willy Hereman and Pavel Winternitz) Macsyma \\ +LIE package (Khai Vu) Maple \\ +Toolbox for symmetries (Mark Hickman) Maple \\ +Lie symmetries (Jeffrey Ondich and Nick Coult) Mathematica. + +\bibitem{lie1} S.\,Lie, Sophus Lie's 1880 Transformation Group Paper, +Translated by M.\,Ackerman, comments by R.\,Hermann, Mathematical Sciences +Press, Brookline, (1975). + +\bibitem{lie2} S.\,Lie, Differentialgleichungen, Chelsea Publishing Company, +New York, (1967). + +\bibitem{LIEPDE} T.\,Wolf, An efficiency improved program {\tt LIEPDE} +for determining Lie - symmetries of PDEs, Proceedings of the workshop on +Modern group theory methods in Acireale (Sicily) Nov.\,(1992) + +\bibitem{Riq} C.\,Riquier, Les syst\`{e}mes d'\'{e}quations +aux d\'{e}riv\'{e}es partielles, Gauthier--Villars, Paris (1910). + +\bibitem{Th} J.\,Thomas, Differential Systems, AMS, Colloquium +publications, v.\,21, N.Y.\,(1937). + +\bibitem{Ja} M.\,Janet, Le\c{c}ons sur les syst\`{e}mes d'\'{e}quations aux +d\'{e}riv\'{e}es, Gauthier--Villars, Paris (1929). + +\bibitem{Topu} V.L.\,Topunov, Reducing Systems of Linear Differential +Equations to a Passive Form, Acta Appl.\,Math.\,16 (1989) 191--206. + +\bibitem{Alex} A.V.\,Bocharov and M.L.\,Bronstein, Efficiently +Implementing Two Methods of the Geometrical Theory of Differential +Equations: An Experience in Algorithm and Software Design, Acta.\,Appl. +Math.\,16 (1989) 143--166. + +\bibitem{Olv} P.J. Olver, Applications of Lie Groups to Differential +Equations, Springer-Verlag New York (1986). + +\bibitem{Reid1} G.J.\,Reid, A triangularization algorithm which +determines the Lie symmetry algebra of any system of PDEs, J.Phys.\,A: +Math.\,Gen.\,23 (1990) L853-L859. + +\bibitem{FS} F.\,Schwarz, Automatically Determining Symmetries of Partial +Differential Equations, Computing 34, (1985) 91-106. + +\bibitem{Fush} W.I.\,Fushchich and V.V.\,Kornyak, Computer Algebra +Application for Determining Lie and Lie--B\"{a}cklund Symmetries of +Differential Equations, J.\,Symb.\,Comp.\,7 (1989) 611--619. + +\bibitem{Ka} E.\,Kamke, Differentialgleichungen, L\"{o}sungsmethoden +und L\"{o}sungen, Band 1, Gew\"{o}hnliche Differentialgleichungen, +Chelsea Publishing Company, New York, 1959. + +\bibitem{KamkePDE} E.\,Kamke, Differentialgleichungen, L\"{o}sungsmethoden +und L\"{o}sungen, Band 2, Partielle Differentialgleichungen, 6.Aufl., +Teubner, Stuttgart:Teubner, 1979. + +\bibitem{Wo} T.\,Wolf, An Analytic Algorithm for Decoupling and Integrating +systems of Nonlinear Partial Differential Equations, J.\,Comp.\,Phys., +no.\,3, 60 (1985) 437-446 and, Zur analytischen Untersuchung und exakten +L\"{o}sung von Differentialgleichungen mit Computeralgebrasystemen, +Dissertation B, Jena (1989). + +\bibitem{WoBra} T.\,Wolf, A. Brand, The Computer Algebra Package {\tt CRACK} + for Investigating PDEs, Manual for the package {\tt CRACK} in the REDUCE + network library and in Proceedings of ERCIM School on Partial + Differential Equations and Group Theory, April 1992 in Bonn, GMD Bonn. + +\bibitem{WM} M.A.H.\,MacCallum, F.J.\,Wright, Algebraic Computing with REDUCE, +Clarendon Press, Oxford (1991). + +\bibitem{Mal} M.A.H.\,MacCallum, An Ordinary Differential Equation +Solver for REDUCE, Proc.\,ISAAC'88, Springer Lect.\,Notes in Comp Sci. +358, 196--205. + +\bibitem{Step} H.\,Stephani, Differential equations, Their solution using +symmetries, Cambridge University Press (1989). + +\bibitem{Karp} V.I.\,Karpman, Phys.\,Lett.\,A 136, 216 (1989) + +\bibitem{Cham} B.\,Champagne, W.\,Hereman and P.\,Winternitz, The computer + calculation of Lie point symmetries of large systems of differential + equations, Comp.\,Phys.\,Comm.\,66, 319-340 (1991) + +\bibitem{Markus} M.\,Kubitza, private communication + +\end{thebibliography} + +\end{document} + + Index: r36/doc/ARNUM.BIB ================================================================== --- r36/doc/ARNUM.BIB +++ r36/doc/ARNUM.BIB @@ -1,21 +1,21 @@ -% Bibliography entry for arnum.tex. - -@INPROCEEDINGS{Bradford:86, - AUTHOR = "R. J. Bradford and A. C. Hearn and J. A. Padget and E. - Schr{\"u}fer", - TITLE = "Enlarging the {REDUCE} Domain of Computation", - BOOKTITLE = "Proceedings of {SYMSAC} '86", YEAR = 1986, - PAGES = "100-106"} - -@INPROCEEDINGS{Trager:76, - AUTHOR = "B. M. Trager", - TITLE = "Algebraic Factoring and Rational Function Integration", - BOOKTITLE = "Proceedings of {SYMSAC} '76", - YEAR = 1976, PAGES = "196-208"} - -@INCOLLECTION{Davenport:81, - AUTHOR = "James Harold Davenport", - TITLE = "On the Integration of Algebraic Functions", - BOOKTITLE = "Lecture Notes in Computer Science", - PUBLISHER = "Springer Verlag", - VOLUME = 102, YEAR = 1981} +% Bibliography entry for arnum.tex. + +@INPROCEEDINGS{Bradford:86, + AUTHOR = "R. J. Bradford and A. C. Hearn and J. A. Padget and E. + Schr{\"u}fer", + TITLE = "Enlarging the {REDUCE} Domain of Computation", + BOOKTITLE = "Proceedings of {SYMSAC} '86", YEAR = 1986, + PAGES = "100-106"} + +@INPROCEEDINGS{Trager:76, + AUTHOR = "B. M. Trager", + TITLE = "Algebraic Factoring and Rational Function Integration", + BOOKTITLE = "Proceedings of {SYMSAC} '76", + YEAR = 1976, PAGES = "196-208"} + +@INCOLLECTION{Davenport:81, + AUTHOR = "James Harold Davenport", + TITLE = "On the Integration of Algebraic Functions", + BOOKTITLE = "Lecture Notes in Computer Science", + PUBLISHER = "Springer Verlag", + VOLUME = 102, YEAR = 1981} Index: r36/doc/ARNUM.TEX ================================================================== --- r36/doc/ARNUM.TEX +++ r36/doc/ARNUM.TEX @@ -1,244 +1,244 @@ -\documentstyle[11pt,reduce]{article} -\title{Algebraic Number Fields} -\date{} -\author{Eberhard Schr\"{u}fer \\ -Institute SCAI.Alg \\ -German National Research Center for Information Technology (GMD) \\ -Schloss Birlinghoven \\ -D-53754 Sankt Augustin \\ -Germany \\[0.05in] -Email: schruefer@gmd.de} -\begin{document} -\maketitle - -\index{algebraic number fields} -\index{algebraic numbers} -\index{ARNUM package} -Algebraic numbers are the solutions of an irreducible polynomial over -some ground domain. \index{i} The algebraic number $i$ (imaginary -unit), \index{imaginary unit} for example, would be defined by the -polynomial $i^2 + 1$. The arithmetic of algebraic number $s$ can be -viewed as a polynomial arithmetic modulo the defining polynomial. - -Given a defining polynomial for an algebraic number $a$ -\begin{eqnarray*} -a^n ~ + ~ {p _{n-1}} {a ^ {n -1}} ~ + ~ ... ~ + ~ {p_0} -\end{eqnarray*} - -All algebraic numbers which can be built up from $a$ are then of the form: -\begin{eqnarray*} -{r_{n-1}} {a ^{n-1}} ~+~ {r_{n-2}} {a ^{n-2}} ~+~ ... ~+~ {r_0} -\end{eqnarray*} -where the $r_j$'s are rational numbers. - -\index{+ ! algebraic numbers} -The operation of addition is defined by -\begin{eqnarray*} -({r_{n-1}} {a ^{n-1}} ~+~ {r_{n-2}} {a ^{n-2}} ~+~ ...) ~ + ~ -({s_{n-1}} {a ^{n-1}} ~+~ {s_{n-2}} {a ^{n-2}} ~+~ ...) ~ = \\ -({r_{n-1}+s_{n-1}}) {a ^{n-1}} ~+~ ({r_{n-2}+s_{n-2}}) {a ^{n-2}} ~+~ ... -\end{eqnarray*} - -\index{* ! algebraic numbers} -Multiplication of two algebraic numbers can be performed by normal -polynomial multiplication followed by a reduction of the result with the -help of the defining polynomial. - -\begin{eqnarray*} -({r_{n-1}} {a ^{n-1}} + {r_{n-2}} {a ^{n-2}} + ...) ~ \times ~ -({s_{n-1}} {a ^{n-1}} + {s_{n-2}} {a ^{n-2}} + ...) = \\ - {r_{n-1}} {s ^{n-1}}{a^{2n-2}} + ... ~ {\bf modulo} ~ -a^n ~ + ~ {p _{n-1}} {a ^ {n -1}} ~ + ~ ... ~ + ~ {p_0} \\ -= ~~~{q_{n-1}} a^{n-1} ~ + ~ {q _{n-2}} {a ^ {n -2}} ~ + ~ ... -\end{eqnarray*} - -\index{/ ! algebraic numbers} -Division of two algebraic numbers r and s yields another algebraic number q. - -$ \frac{r}{s} = q$ or $ r = q s $. - -The last equation written out explicitly reads - -\begin{eqnarray*} -\lefteqn{({r_{n-1}} {a^{n-1}} + {r_{n-2}} {a^{n-2}} + \ldots)} \\ -& = & ({q_{n-1}} {a^{n-1}} + {q_{n-2}} {a^{n-2}} + \ldots) \times -({s_{n-1}} {a^{n-1}} + {s_{n-2}} {a^{n-2}} + \ldots) \\ -& & {\bf modulo} (a^n + {p _{n-1}} {a^{n -1}} + \ldots) \\ -& = & ({t_{n-1}} {a^{n-1}} + {t_{n-2}} {a^{n-2}} + \ldots) -\end{eqnarray*} - -The $t_i$ are linear in the $q_j$. Equating equal powers of $a$ yields a -linear system for the quotient coefficients $q_j$. - -With this, all field operations for the algebraic numbers are available. The -translation into algorithms is straightforward. For an implementation we -have to decide on a data structure for an algebraic number. We have chosen -the representation REDUCE normally uses for polynomials, the so-called -standard form. Since our polynomials have in general rational coefficients, -we must allow for a rational number domain inside the algebraic number. - -\begin{tabbing} -\s{algebraic number} ::= \\ -\hspace{.25in} \= {\tt :ar:} . \s{univariate polynomial over the rationals} -\\[0.05in] - -\s{univariate polynomial over the rationals} ::= \\ -\> \s{variable} .** \s{ldeg} .* \s{rational} .+ \s{reductum} \\[0.05in] - -\s{ldeg} ::= integer \\[0.3in] - -\s{rational} ::= \\ -\> {\tt :rn:} . \s{integer numerator} . \s{integer denominator} : -integer \\[0.05in] - -\s{reductum} ::= \s{univariate polynomial} : \s{rational} : nil -\end{tabbing} - -This representation allows us to use the REDUCE functions for adding and -multiplying polynomials on the tail of the tagged algebraic number. Also, -the routines for solving linear equations can easily be used for the -calculation of quotients. We are still left with the problem of -introducing a particular algebraic number. In the current version this is -done by giving the defining polynomial to the statement {\bf defpoly}. The -\index{DEFPOLY statement} -algebraic number sqrt(2), for example, can be introduced by -\begin{verbatim} - defpoly sqrt2**2 - 2; -\end{verbatim} - -This statement associates a simplification function for the -translation of the variable in the defining polynomial into its tagged -internal form and also generates a power reduction rule used by the -operations {\bf times} and {\bf quotient} for the reduction of their -result modulo the defining polynomial. A basis for the representation -of an algebraic number is also set up by the statement. In the -working version, the basis is a list of powers of the indeterminate of -the defining polynomial up to one less then its degree. Experiments -with integral bases, however, have been very encouraging, and these -bases might be available in a later version. If the defining -polynomial is not monic, it will be made so by an appropriate -substitution. - -\example \index{ARNUM package ! example} - -\begin{verbatim} - defpoly sqrt2**2-2; - - 1/(sqrt2+1); - - sqrt2 - 1 - - (x**2+2*sqrt2*x+2)/(x+sqrt2); - - x + sqrt2 - - on gcd; - - (x**3+(sqrt2-2)*x**2-(2*sqrt2+3)*x-3*sqrt2)/(x**2-2); - - 2 - (x - 2*x - 3)/(x - sqrt2) - - off gcd; - - sqrt(x**2-2*sqrt2*x*y+2*y**2); - - abs(x - sqrt2*y) -\end{verbatim} - -Until now we have dealt with only a single algebraic number. In practice -this is not sufficient as very often several algebraic numbers appear in an -expression. There are two possibilities for handling this: one can use -multivariate extensions \cite{Davenport:81} or one can construct a defining -polynomial that contains all specified extensions. This package implements -the latter case (the so called primitive representation). The algorithm we -use for the construction of the primitive element is the same as given by -Trager \cite{Trager:76}. In the implementation, multiple extensions can be -given as a list of equations to the statement {\bf defpoly}, which, among other -things, adds the new extension to the previously defined one. All -algebraic numbers are then expressed in terms of the primitive element. - - -\example\index{ARNUM package ! example} - -\begin{verbatim} - defpoly sqrt2**2-2,cbrt5**3-5; - - *** defining polynomial for primitive element: - - 6 4 3 2 - a1 - 6*a1 - 10*a1 + 12*a1 - 60*a1 + 17 - - sqrt2; - - 5 4 3 2 - 48/1187*a1 + 45/1187*a1 - 320/1187*a1 - 780/1187*a1 + - - - 735/1187*a1 - 1820/1187 - - sqrt2**2; - - 2 -\end{verbatim} -\newpage -We can provide factorization of polynomials over the algebraic number -domain by using Trager's algorithm. The polynomial to be factored is first -mapped to a polynomial over the integers by computing the norm of the -polynomial, which is the resultant with respect to the primitive element of -the polynomial and the defining polynomial. After factoring over the -integers, the factors over the algebraic number field are recovered by GCD -calculations. - -\example\index{ARNUM package ! example} - -\begin{verbatim} - defpoly a**2-5; - - on factor; - - x**2 + x - 1; - - (x + (1/2*a + 1/2))*(x - (1/2*a - 1/2)) -\end{verbatim} -\index{SPLIT\_FIELD function} -We have also incorporated a function {\bf split\_field} for the calculation -of a primitive element of minimal degree for which a given polynomial splits -into linear factors. The algorithm as described in Trager's article is -essentially a repeated primitive element calculation. - -\example\index{ARNUM package ! example} - -\begin{verbatim} - split_field(x**3-3*x+7); - - *** Splitting field is generated by: - - 6 4 2 - a2 - 18*a2 + 81*a2 + 1215 - - - - 4 2 - {1/126*a2 - 5/42*a2 - 1/2*a2 + 2/7, - - - 4 2 - - (1/63*a2 - 5/21*a2 + 4/7), - - - 4 2 - 1/126*a2 - 5/42*a2 + 1/2*a2 + 2/7} - - - for each j in ws product (x-j); - - 3 - x - 3*x + 7 -\end{verbatim} - -A more complete description can be found in \cite{Bradford:86}. -\bibliography{arnum} -\bibliographystyle{plain} -\end{document} - +\documentstyle[11pt,reduce]{article} +\title{Algebraic Number Fields} +\date{} +\author{Eberhard Schr\"{u}fer \\ +Institute SCAI.Alg \\ +German National Research Center for Information Technology (GMD) \\ +Schloss Birlinghoven \\ +D-53754 Sankt Augustin \\ +Germany \\[0.05in] +Email: schruefer@gmd.de} +\begin{document} +\maketitle + +\index{algebraic number fields} +\index{algebraic numbers} +\index{ARNUM package} +Algebraic numbers are the solutions of an irreducible polynomial over +some ground domain. \index{i} The algebraic number $i$ (imaginary +unit), \index{imaginary unit} for example, would be defined by the +polynomial $i^2 + 1$. The arithmetic of algebraic number $s$ can be +viewed as a polynomial arithmetic modulo the defining polynomial. + +Given a defining polynomial for an algebraic number $a$ +\begin{eqnarray*} +a^n ~ + ~ {p _{n-1}} {a ^ {n -1}} ~ + ~ ... ~ + ~ {p_0} +\end{eqnarray*} + +All algebraic numbers which can be built up from $a$ are then of the form: +\begin{eqnarray*} +{r_{n-1}} {a ^{n-1}} ~+~ {r_{n-2}} {a ^{n-2}} ~+~ ... ~+~ {r_0} +\end{eqnarray*} +where the $r_j$'s are rational numbers. + +\index{+ ! algebraic numbers} +The operation of addition is defined by +\begin{eqnarray*} +({r_{n-1}} {a ^{n-1}} ~+~ {r_{n-2}} {a ^{n-2}} ~+~ ...) ~ + ~ +({s_{n-1}} {a ^{n-1}} ~+~ {s_{n-2}} {a ^{n-2}} ~+~ ...) ~ = \\ +({r_{n-1}+s_{n-1}}) {a ^{n-1}} ~+~ ({r_{n-2}+s_{n-2}}) {a ^{n-2}} ~+~ ... +\end{eqnarray*} + +\index{* ! algebraic numbers} +Multiplication of two algebraic numbers can be performed by normal +polynomial multiplication followed by a reduction of the result with the +help of the defining polynomial. + +\begin{eqnarray*} +({r_{n-1}} {a ^{n-1}} + {r_{n-2}} {a ^{n-2}} + ...) ~ \times ~ +({s_{n-1}} {a ^{n-1}} + {s_{n-2}} {a ^{n-2}} + ...) = \\ + {r_{n-1}} {s ^{n-1}}{a^{2n-2}} + ... ~ {\bf modulo} ~ +a^n ~ + ~ {p _{n-1}} {a ^ {n -1}} ~ + ~ ... ~ + ~ {p_0} \\ += ~~~{q_{n-1}} a^{n-1} ~ + ~ {q _{n-2}} {a ^ {n -2}} ~ + ~ ... +\end{eqnarray*} + +\index{/ ! algebraic numbers} +Division of two algebraic numbers r and s yields another algebraic number q. + +$ \frac{r}{s} = q$ or $ r = q s $. + +The last equation written out explicitly reads + +\begin{eqnarray*} +\lefteqn{({r_{n-1}} {a^{n-1}} + {r_{n-2}} {a^{n-2}} + \ldots)} \\ +& = & ({q_{n-1}} {a^{n-1}} + {q_{n-2}} {a^{n-2}} + \ldots) \times +({s_{n-1}} {a^{n-1}} + {s_{n-2}} {a^{n-2}} + \ldots) \\ +& & {\bf modulo} (a^n + {p _{n-1}} {a^{n -1}} + \ldots) \\ +& = & ({t_{n-1}} {a^{n-1}} + {t_{n-2}} {a^{n-2}} + \ldots) +\end{eqnarray*} + +The $t_i$ are linear in the $q_j$. Equating equal powers of $a$ yields a +linear system for the quotient coefficients $q_j$. + +With this, all field operations for the algebraic numbers are available. The +translation into algorithms is straightforward. For an implementation we +have to decide on a data structure for an algebraic number. We have chosen +the representation REDUCE normally uses for polynomials, the so-called +standard form. Since our polynomials have in general rational coefficients, +we must allow for a rational number domain inside the algebraic number. + +\begin{tabbing} +\s{algebraic number} ::= \\ +\hspace{.25in} \= {\tt :ar:} . \s{univariate polynomial over the rationals} +\\[0.05in] + +\s{univariate polynomial over the rationals} ::= \\ +\> \s{variable} .** \s{ldeg} .* \s{rational} .+ \s{reductum} \\[0.05in] + +\s{ldeg} ::= integer \\[0.3in] + +\s{rational} ::= \\ +\> {\tt :rn:} . \s{integer numerator} . \s{integer denominator} : +integer \\[0.05in] + +\s{reductum} ::= \s{univariate polynomial} : \s{rational} : nil +\end{tabbing} + +This representation allows us to use the REDUCE functions for adding and +multiplying polynomials on the tail of the tagged algebraic number. Also, +the routines for solving linear equations can easily be used for the +calculation of quotients. We are still left with the problem of +introducing a particular algebraic number. In the current version this is +done by giving the defining polynomial to the statement {\bf defpoly}. The +\index{DEFPOLY statement} +algebraic number sqrt(2), for example, can be introduced by +\begin{verbatim} + defpoly sqrt2**2 - 2; +\end{verbatim} + +This statement associates a simplification function for the +translation of the variable in the defining polynomial into its tagged +internal form and also generates a power reduction rule used by the +operations {\bf times} and {\bf quotient} for the reduction of their +result modulo the defining polynomial. A basis for the representation +of an algebraic number is also set up by the statement. In the +working version, the basis is a list of powers of the indeterminate of +the defining polynomial up to one less then its degree. Experiments +with integral bases, however, have been very encouraging, and these +bases might be available in a later version. If the defining +polynomial is not monic, it will be made so by an appropriate +substitution. + +\example \index{ARNUM package ! example} + +\begin{verbatim} + defpoly sqrt2**2-2; + + 1/(sqrt2+1); + + sqrt2 - 1 + + (x**2+2*sqrt2*x+2)/(x+sqrt2); + + x + sqrt2 + + on gcd; + + (x**3+(sqrt2-2)*x**2-(2*sqrt2+3)*x-3*sqrt2)/(x**2-2); + + 2 + (x - 2*x - 3)/(x - sqrt2) + + off gcd; + + sqrt(x**2-2*sqrt2*x*y+2*y**2); + + abs(x - sqrt2*y) +\end{verbatim} + +Until now we have dealt with only a single algebraic number. In practice +this is not sufficient as very often several algebraic numbers appear in an +expression. There are two possibilities for handling this: one can use +multivariate extensions \cite{Davenport:81} or one can construct a defining +polynomial that contains all specified extensions. This package implements +the latter case (the so called primitive representation). The algorithm we +use for the construction of the primitive element is the same as given by +Trager \cite{Trager:76}. In the implementation, multiple extensions can be +given as a list of equations to the statement {\bf defpoly}, which, among other +things, adds the new extension to the previously defined one. All +algebraic numbers are then expressed in terms of the primitive element. + + +\example\index{ARNUM package ! example} + +\begin{verbatim} + defpoly sqrt2**2-2,cbrt5**3-5; + + *** defining polynomial for primitive element: + + 6 4 3 2 + a1 - 6*a1 - 10*a1 + 12*a1 - 60*a1 + 17 + + sqrt2; + + 5 4 3 2 + 48/1187*a1 + 45/1187*a1 - 320/1187*a1 - 780/1187*a1 + + + + 735/1187*a1 - 1820/1187 + + sqrt2**2; + + 2 +\end{verbatim} +\newpage +We can provide factorization of polynomials over the algebraic number +domain by using Trager's algorithm. The polynomial to be factored is first +mapped to a polynomial over the integers by computing the norm of the +polynomial, which is the resultant with respect to the primitive element of +the polynomial and the defining polynomial. After factoring over the +integers, the factors over the algebraic number field are recovered by GCD +calculations. + +\example\index{ARNUM package ! example} + +\begin{verbatim} + defpoly a**2-5; + + on factor; + + x**2 + x - 1; + + (x + (1/2*a + 1/2))*(x - (1/2*a - 1/2)) +\end{verbatim} +\index{SPLIT\_FIELD function} +We have also incorporated a function {\bf split\_field} for the calculation +of a primitive element of minimal degree for which a given polynomial splits +into linear factors. The algorithm as described in Trager's article is +essentially a repeated primitive element calculation. + +\example\index{ARNUM package ! example} + +\begin{verbatim} + split_field(x**3-3*x+7); + + *** Splitting field is generated by: + + 6 4 2 + a2 - 18*a2 + 81*a2 + 1215 + + + + 4 2 + {1/126*a2 - 5/42*a2 - 1/2*a2 + 2/7, + + + 4 2 + - (1/63*a2 - 5/21*a2 + 4/7), + + + 4 2 + 1/126*a2 - 5/42*a2 + 1/2*a2 + 2/7} + + + for each j in ws product (x-j); + + 3 + x - 3*x + 7 +\end{verbatim} + +A more complete description can be found in \cite{Bradford:86}. +\bibliography{arnum} +\bibliographystyle{plain} +\end{document} + Index: r36/doc/ASSIST.TEX ================================================================== --- r36/doc/ASSIST.TEX +++ r36/doc/ASSIST.TEX @@ -1,1406 +1,1406 @@ -\documentstyle[11pt,reduce]{article} -\newcommand{\nl}{\hfill\newline} -\newcommand{\bq}{\begin{quotation}} -\newcommand{\eq}{\end{quotation}} -\newcommand{\bi}{\begin{itemize}} -\newcommand{\ei}{\end{itemize}} -\date{} -\title{{\bf ASSIST}\ :\\[2pt] - A General Purpose Facility~for~\REDUCE \\[5pt] - \mbox{\hfill Version 2.2\hfil}} -\author{Hubert Caprasse \\ -D\'epartement d'Astronomie et d'Astrophysique \\ -Institut de Physique, B--5, Sart Tilman \\ -B--4000 LIEGE 1 -Belgium\\[3pt] -E--mail: caprasse@vm1.ulg.ac.be} -\begin{document} -\maketitle -\index{ASSIST package} -\section{Introduction} - ASSIST contains -an appreciable number of additional general purpose functions which allow -to better adapt \REDUCE\ to various calculational strategies, -to make the programming task more straightforward and more efficient. - -Contrary to all other packages, ASSIST does not aim to provide neither a new -facility to compute a definite class of mathematical objects nor to extend -the base of mathematical knowledge of \REDUCE\ . -The functions it contains should be -useful independently of the nature of the application which is considered. -They were initially written while doing specific applications of -\REDUCE\ to problems in theoretical physics. Most them were designed -in such a way that their applicability range is broad. Though it was not -the primary goal, efficiency has been sought whenever possible. - -The source code in ASSIST contains many comments concerning -the meaaning and the use of the supplementary functions available -in the algebraic mode. These comments, hopefully, makes the code transparent -and allow a thorough exploitation of the package. The present documentation -contains a non--technical description of it and describes the -various new facilities it provides. -\section{ Survey of the Available New Facilities} -An elementary help facility is available both in -the MS-DOS\ and Windows environments. It is made independent of the -help facility of \REDUCE\ itself. It includes only one function: - -\f{HELPASSIST} which takes one argument. -\begin{itemize} -\item[i.] The argument is the identifier \f{assist}. Then the function -gives the informations necessary to retrieve the names of the functions. -\item[ii.] The argument is an integer equal to one of the section number -of the present documentation. Then the names of the functions described -in that section are obtained.\nl -There is, presently, no way to retrieve the number and the nature of the -arguments. -\end{itemize} -The package contains several modules. Their content reflects closely -the various categories of facilities quoted below. Some functions do -already exist inside the KERNEL of \REDUCE\ . However, their range -of applicability is {\em extended}.\nl -\begin{itemize} -\item{Control of Switches:} -\begin{quotation} -\noindent -\f{SWITCHES SWITCHORG} -\end{quotation} -\item{Operations on Lists and Bags:} -\begin{quotation} -\noindent -\f{MKLIST KERNLIST ALGNLIST LENGTH \nl -FREQUENCY SEQUENCES \nl -INSERT INSERT\_KEEP\_ORDER MERGE\_LIST \nl -FIRST SECOND THIRD REST REVERSE LAST \nl -BELAST CONS ( . ) APPEND APPENDN \nl -REMOVE DELETE DELETE\_ALL DELPAIR \nl -MEMBER ELMULT PAIR DEPTH POSITION \nl -REPFIRST REPREST ASFIRST ASLAST ASREST \nl -ASFLIST ASSLIST RESTASLIST SUBSTITUTE \nl -BAGPROP PUTBAG CLEARBAG BAGP BAGLISTP \nl -ALISTP ABAGLISTP LISTBAG } -\end{quotation} -\item{Operations on Sets:} -\begin{quotation} -\noindent -\f{MKSET SETP UNION INTERSECT DIFFSET SYMDIFF} -\end{quotation} -\newpage -\item{General Purpose Utility Functions:} -\begin{quotation} -\noindent -\f{LIST\_TO\_IDS MKIDN MKIDNEW DELLASTDIGIT DETIDNUM \\ -ODDP FOLLOWLINE == RANDOMLIST MKRANDTABL \\ -PERMUTATIONS CYCLICPERMLIST COMBNUM COMBINATIONS \\ -SYMMETRIZE REMSYM SORTNUMLIST SORTLIST ALGSORT \\ -EXTREMUM DEPATOM FUNCVAR IMPLICIT EXPLICIT \\ -KORDERLIST CHECKPROPLIST EXTRACTLIST} -\end{quotation} -\item{ Properties and Flags:} -\begin{quotation} -\noindent -\f{PUTFLAG PUTPROP DISPLAYPROP DISPLAYFLAG \\ -CLEARFLAG CLEARPROP } -\end{quotation} -\item{ Control Statements, Control of Environment:} -\begin{quotation} -\noindent -\f{NORDP DEPVARP ALATOMP ALKERNP PRECP \\ - SHOW SUPPRESS CLEAROP CLEARFUNCTIONS } -\end{quotation} -\item{Handling of Polynomials:} -\begin{quotation} -\noindent -\f{ALG\_TO\_SYMB SYMB\_TO\_ALG \\ -DISTRIBUTE LEADTERM REDEXPR MONOM\\ -LOWESTDEG DIVPOL SPLITTERMS SPLITPLUSMINUS} -\end{quotation} -\item{Handling of Transcendental Functions:} -\begin{quotation} -\noindent -\f{TRIGEXPAND HYPEXPAND TRIGREDUCE HYPREDUCE} -\end{quotation} -\item{Coercion from lists to arrays and converse:} -\begin{quotation} -\f{LIST\_TO\_ARRAY ARRAY\_TO\_LIST} -\end{quotation} -\item{Handling of n-dimensional Vectors:} -\begin{quotation} -\noindent -\f{SUMVECT MINVECT SCALVECT CROSSVECT MPVECT } -\end{quotation} -{\item Handling of Grassmann Operators:} -\begin{quotation} -\noindent -\f{PUTGRASS REMGRASS GRASSP GRASSPARITY GHOSTFACTOR } -\end{quotation} -\item{Handling of Matrices:} -\begin{quotation} -\noindent -\f{UNITMAT MKIDM BAGLMAT COERCEMAT \\ -SUBMAT MATSUBR MATSUBC RMATEXTR RMATEXTC \\ - HCONCMAT VCONCMAT TPMAT HERMAT \\ -SETELTMAT GETELTMAT} -\end{quotation} -\end{itemize} -In the following each group of functions is, successively, described. -\section{Control of Switches} -The two available functions i.e. \f{SWITCHES, SWITCHORG} have -no argument and are called as if they were mere identifiers. - -\f{SWITCHES} displays the actual status of the most often used switches -when manipulating rational functions. The chosen switches are -\begin{quotation} -\noindent -{\tt EXP, DIV, MCD, GCD, ALLFAC, INTSTR,\\ RAT, RATIONAL, FACTOR } -\end{quotation} -The switch {\tt DISTRIBUTE} which controls the handling -of distributed polynomials is added to them (see below the description of -the new functions for manipulating polynomials ). -The selection is somewhat arbitrary but it may be changed in a trivial -fashion by the user. - -Most of the symbolic variables {\tt !*EXP, !*DIV, $\ldots$} -which have either the value T or the value NIL are made available in the -algebraic mode so that it becomes possible to write conditional -statements of the kind -\begin{verbatim} - - IF !*EXP THEN DO ...... - - IF !*GCD THEN OFF GCD; - -\end{verbatim} -\f{SWITCHORG} resets (almost) {\em all} switches in the status -they have when {\bf entering} into \REDUCE\ . -The new switch {\tt DISTRIBUTE} allows to put polynomials in a -distributed form. -\section{Manipulation of the List Structure} - -Additional functions for list manipulations are provided and some already -defined functions in the kernel of \REDUCE\ are modified to properly -generalize them to the available new structure {\tt BAG}. -\begin{itemize} -\item[i.] -Generation of a list of length n with all its elements initialized to 0 -and possibility to append to a list $l$ a certain number of zero's to -make it of length $n$: -\begin{verbatim} - - MKLIST n ; n is an INTEGER - - MKLIST(l,n); l is List-like, n is an INTEGER - -\end{verbatim} - -\item[ii.] -Generation of a list of sublists of length n containing p elements -equal to 0 and q elements equal to 1 such that $$p+q=n .$$ -The function \f{SEQUENCES} works both in the algebraic and -symbolic modes. Here is an example: -\begin{verbatim} - - SEQUENCES 2 ; ==> {{0,0},{0,1},{1,0},{1,1}} - -\end{verbatim} -The function \f{KERNLIST} transforms any prefix of a kernel into the -{\bf \verb+list+} prefix. The output list is a copy: -\begin{verbatim} - - KERNLIST (); ==> {} - -\end{verbatim} -Four functions to delete elements are \f{DELETE, REMOVE, DELETE\_ALL} and -\f{DELPAIR}. The first two act as in symbolic mode, the third -eliminates from a given list {\em all} -elements equal to its first argument. The fourth act on list of pairs -and eliminates from it the {\em first} pair whose first element is equal to -its first argument : -\begin{verbatim} - - DELETE(x,{a,b,x,f,x}); ==> {a,b,f,x} - - REMOVE({a,b,x,f,x},3); ==> {a,b,f,x} - - DELETE_ALL(x,{a,b,x,f,x}); ==> {a,b,f} - - DELPAIR(a,{{a,1},{b,2},{c,3}}; ==> {{b,2},{c,3}} - -\end{verbatim} -\item[iv.] -The function \f{ELMULT} returns an {\em integer} which is the -{\em multiplicity} of its first argument inside the list which is its -second argument. -The function \f{FREQUENCY} gives a list of pairs -whose second element indicates the number of times the first element -appears inside the original list: -\begin{verbatim} - - ELMULT(x,{a,b,x,f,x}) ==> 2 - - FREQUENCY({a,b,c,a}); ==> {{a,2},{b,1},{c,1}} - -\end{verbatim} -\item[v.] -The function \f{INSERT} allows to insert a given object into a list -at the wanted position. - -The functions \f{INSERT\_KEEP\_ORDER} and \f{MERGE\_LIST} allow to -keep a given ordering when inserting one element inside a list or -when merging two lists. Both have 3 arguments. The last one is -the name of a binary boolean ordering function: -\begin{verbatim} - - ll:={1,2,3}$ - - INSERT(x,ll,3); ==> {1,2,x,3} - - INSERT_KEEP_ORDER(5,ll,lessp); ==> {1,2,3,5} - - MERGE_LIST(ll,ll,lessp); ==> {1,1,2,2,3,3} - -\end{verbatim} -\item[vi.] -Algebraic lists can be read from right to left or left to right. -They {\em look} symmetrical. One would like to dispose of manipulation -functions which reflect this. -So, to the already defined functions \f{FIRST} and \f{REST} are -added the functions \f{LAST} and \f{BELAST}. \f{LAST} gives the last -element of the list while \f{BELAST} gives the list {\em without} its -last element. \\ -Various additional functions are provided. They are: -\bq - -\f{ CONS (.), POSITION, DEPTH, PAIR, \\ -APPENDN, REPFIRST, REPLAST} - -\eq -The token ``dot'' needs a special comment. It corresponds to -several different operations. -\begin{enumerate} -\item If one applies it on the left of a list, it acts as the \f{CONS} -function. Be careful, blank spaces are required around the dot: -\begin{verbatim} - - 4 . {a,b}; ==> {4,a,b} - -\end{verbatim} -\item If one applies it on the right of a list, it has the same -effect as the \f{PART} operator: -\begin{verbatim} - - {a,b,c}.2; ==> b - -\end{verbatim} -\item If one applies it on 4--dimensional vectors, it acts as in the -HEPHYS packge. -\end{enumerate} -\f{POSITION} returns the POSITION of the first occurrence of x in -a list or a message if x is not present in it. - -\f{DEPTH} returns an {\em integer} equal to the number of levels where a - list is found if and only if this number is the {\em same} for each - element of the list otherwise it returns a message telling the user - that list is of {\em unequal depth}. - -\f{PAIR} has two arguments which must be lists. It returns a list -whose elements are {\em lists of two elements.} -The $n^{th}$ sublist contains the $n^{th}$ element of the first list -and the $n^{th}$ element of the second list. These types of lists are called -{\em association lists} or ALISTS in the following. -To test for these type of lists a boolean function \f{ABAGLISTP} -is provided. It will be discussed below.\\ -\f{APPENDN} has {\em any} fixed number of lists as arguments. It -generalizes the already existing function \f{APPEND} which accepts -only two lists as arguments. \\ -\f{REPFIRST} has two arguments. The first one is any object, the second one -is a list. It replaces the first element of the list by tho object. It -works like the symbolic function \f{REPLACA} except that the -original list is not destroyed.\\ -\f{REPREST} has also two arguments. It replaces the rest of the list by -its first argument and returns the new list without destroying the -original list. It is analogous to the symbolic function \f{REPLACD}. -Here are examples: -\begin{verbatim} - - ll:={{a,b}}$ - ll1:=ll.1; ==> {a,b} - ll.0; ==> list - 0 . ll; ==> {0,{a,b}} - - DEPTH ll; ==> 2 - - PAIR(ll1,ll1); ==> {{a,a},{b,b}} - - REPFIRST{new,ll); ==> {new} - - ll3:=APPENDN(ll1,ll1,ll1); ==> {a,b,a,b,a,b} - - POSITION(b,ll3); ==> 2 - - REPREST(new,ll3); ==> {a,new} - -\end{verbatim} -\item[vii.] -The functions \f{ASFIRST, ASLAST, ASREST, ASFLIST, ASSLIST, \\RESTASLIST} -act on ALISTS or on list of lists of well defined depths -and have two arguments. The first is the key object -which one seeks to associate in some way to an element of the association -list which is the second argument.\\ -\f{ASFIRST} returns the pair whose first element is equal to the -first argument.\\ -\f{ASLAST} returns the pair whose last element is equal to the first -argument.\\ -\f{ASREST} needs a {\em list} as its first argument. The function -seeks the first sublist of a list of lists (which is its second argument) -equal to its first argument and returns it.\\ -\f{RESTASLIST} has a {\em list of keys} as its first arguments. It -returns the collection of pairs which meet the criterion of \f{ASREST}.\\ -\f{ASFLIST} returns a list containing {\em all pairs} which -satisfy to the criteria of the function \f{ASFIRST}. So the output -is also an ALIST or a list of lists.\\ -\f{ASSLIST} returns a list which contains {\em all pairs} which have -their second element equal to the first argument.\\ -Here are a few examples: -\begin{verbatim} - - lp:={{a,1},{b,2},{c,3}}$ - - ASFIRST(a,lp); ==> {a,1} - - ASLAST(1,lp); ==> {a,1} - - ASREST({1},lp); ==> {a,1} - - RESTASLIST({a,b},lp); ==> {{1},{2}} - - lpp:=APPEND(lp,lp)$ - - ASFLIST(a,lpp); ==> {{a,1},{a,1}} - - ASSLIST(1,lpp); ==> {{a,1},{a,1}} - -\end{verbatim} -\item[vii.] The function \f{SUBSTITUTE} has three arguments. The first -is the object to substitute, the second is the object which must be -replaced by the first, the third is a list. Substitution is made to -all levels. It is a more elementary function than \f{SUB} but its -capabilities are less. When dealing with algebraic quantities, it is -important to make sure that {\em all} objects involved in the function -have either the prefix lisp or the standard quotient representation -otherwise it will not properly work. -\end{itemize} -\section{ The Bag Structure and its Associated Functions} -The LIST structure of \REDUCE\ is very convenient to manipulate -groups of objects which are, a priori, unknown. This structure is -endowed with other properties such as ``mapping'' i.e. the fact that -if \verb+OP+ is an operator one gets, by default, -\begin{verbatim} - - OP({x,y}); ==> {OP(x),OP(y)} - -\end{verbatim} -It is not permitted to submit lists to the operations valid on rings -so that lists cannot be indeterminates of polynomials.\\ -Very frequently too, procedure arguments cannot be lists. -At the other extreme, so to say, one has the \verb+KERNEL+ -structure associated -to the algebraic declaration \verb+operator+ . This structure behaves as -an ``unbreakable'' one and, for that reason, behaves -like an ordinary identifier. -It may generally be bound to all non-numeric procedure parameters -and it may appear -as an ordinary indeterminate inside polynomials. \\ -The \verb+BAG+ structure is intermediate between a list and an operator. -From the operator it borrows the property to be a \verb+KERNEL+ and, -therefore, may be an indeterminate of a polynomial. From the list structure -it borrows the property to be a {\em composite} object.\\[5pt] -\mbox{\underline{{\bf Definition}:\hfill}}\\[4pt] -A bag is an object endowed with the following properties: -\begin{enumerate} -\item It is a \verb+KERNEL+ composed of an atomic prefix (its -envelope) and -its content (miscellaneous objects). -\item Its content may be changed in an analogous way as the content of a -list. During these manipulations the name of the bag is {\em conserved}. -\item Properties may be given to the envelope. For instance, one may -declare it \verb+NONCOM+ or \verb+SYMMETRIC+ etc.\ $\ldots$ -\end{enumerate} -\vspace{5pt} -\mbox{\underline{{\bf Available Functions}:\hfill}} -\bi -\item[i.] A default bag envelope \verb+BAG+ is defined. -It is a reserved identifier. -An identifier other than \verb+LIST+ or one which is already associated -with a boolean function may be defined as a bag envelope through the -command \f{PUTBAG}. In particular, any operator may also be declared -to be a bag. {\bf When and only when} the identifier is not an already defined -function does \f{PUTBAG} puts on it the property of an OPERATOR PREFIX. -The command: -\begin{verbatim} - - PUTBAG id1,id2,....idn; - -\end{verbatim} -declares \verb+id1,.....,idn+ as bag envelopes. -Analoguously, the command -\begin{verbatim} - - CLEARBAG id1,...idn; - -\end{verbatim} -eliminates the bag property on \verb+id1,...,idn+. -\item[ii.] The boolean function \f{BAGP} detects the bag property. -Here is an example: -\begin{verbatim} - - aa:=bag(x,y,z)$ - - if BAGP aa then "ok"; ==> ok - -\end{verbatim} -\item[iii.] Almost all functions defined above for lists -do also work for bags. -Moreover, functions subsequently defined for SETS do also work. -Here is a list of the main ones: -\begin{quotation} -\f{FIRST, SECOND, LAST, REST, BELAST, DEPTH,\\ -LENGTH, APPEND, CONS (.), REPFIRST, REPREST} $\ldots$ -\end{quotation} - -However, because of the conservation of the envelope, they act -somewhat differently. Here are a few examples (more examples are -given inside the test file): -\begin{verbatim} - - PUTBAG op; ==> T - - aa:=op(x,y,z)$ - - FIRST op(x,y,z); ==> op(x) - - REST op(x,y,z); ==> op(y,z) - - BELAST op(x,y,z); ==> op(x,y) - - APPEND(aa,aa); ==> op(x,y,z,x,y,z) - - LENGTH aa; ==> 3 - - DEPTH aa; ==> 1 - -\end{verbatim} -When ``appending'' two bags with {\em different} envelopes, the resulting bag -gets the name of the one bound to the first parameter of \f{APPEND}.\\ -The function \f{LENGTH} gives the actual number of variables on which -the operator (or the function) depends. -\vspace{5pt} -\begin{center} -The NAME of the ENVELOPE is KEPT by the functions \\[3pt] -\f{FIRST, SECOND, LAST, BELAST }. -\end{center} -\vspace{5pt} -\item[iv.] -The connection between the list and the bag structures is made easy -thanks to \f{KERNLIST} which transforms a bag into a list and thanks to -the coercion function \f{LISTBAG}. This function has 2 arguments -and is used as follows: -\begin{verbatim} - - LISTBAG(,); ==> () - -\end{verbatim} -The identifier \verb++, if allowed, is automatically declared as a bag -envelope or an error message is generated. \\[3pt] -Finally, two boolean functions which work both for bags and lists are -provided. They are \f{BAGLISTP} and \f{ABAGLISTP}. -They return t or nil (in a conditional statement) if their argument -is a bag or a list for the first one, if their argument is a list of -sublists or a bag containing bags for the second one . -\end{itemize} -\section{Sets and their Manipulation Functions} -Functions for sets do exist on the level of the symbolic mode. The -package make them available in the algebraic mode but also {\em generalizes} -them so that they can be applied on bag--like objects as well. -\bi -\item[i.] -The constructor \f{MKSET} transforms a list or bag into a set by eliminating -duplicates. -\begin{verbatim} - - MKSET({1,a,a1}); ==> {1,a} - MKSET bag(1,a,a1); ==> bag(1,a) - -\end{verbatim} - -\f{SETP} is a boolean function which recognizes set--like objects. -\begin{verbatim} - - if SETP {1,2,3} then ... ; - -\end{verbatim} -\item[ii.] -The available functions are -\begin{center} -\f{UNION, INTERSECT, DIFFSET, SYMDIFF}. -\end{center} -They have two arguments which must be sets otherwise an error message -is issued. -Their meaning is transparent from their name. They respectively give the -union, the intersection, the difference and the symmetric difference of two -sets. -\ei -\section{General Purpose Utility Functions} -Functions in this sections have various purposes. They have all been used -many times in applications under some form or another. The form given -to them in this package is adjusted to maximize their range of applications. -\bi -\item[i.] -The functions \f{MKIDNEW DELLASTDIGIT DETIDNUM LIST\_TO\_IDS} -handle identifiers. \f{MKIDNEW} is a variant of \f{MKID}. - -\f{MKIDNEW} has either 0 or 1 argument. It generates an identifier which -has not yet been used before. -\begin{verbatim} - - MKIDNEW(); ==> g0001 - - MKIDNEW(a); ==> ag0002 - -\end{verbatim} -\f{DELLASTDIGIT} takes an integer as argument, it strips it from its last -digit. -\begin{verbatim} - - DELLASTDIGIT 45; ==> 4 - -\end{verbatim} -\f{DETIDNUM}, extracts the last digit from an -identifier. It is a very convenient when one wants to make a do loop -starting from a set of indices $ a_1, \ldots , a_{n} $. -\begin{verbatim} - - DETIDNUM a23; ==> 23 - -\end{verbatim} - -\f{LIST\_to\_IDS} generalizes the function \f{MKID} to a list of -atoms. It creates and intern an identifier from the concatenation of -the atoms. The first atom cannot be an integer. -\begin{verbatim} - - LIST_TO_IDS {a,1,id,10}; ==> a1id10 - -\end{verbatim} -The function \f{ODDP} detects odd integers. - -The function \f{FOLLOWLINE} is convenient when using the function \f{PRIN2}. -It allows to format an output text in a much more flexible way than with -the function \f{WRITE}. \\ -Try the following examples : -\begin{verbatim} - - <>$ ==> ? - - <>; ==> ? - -\end{verbatim} -The function \f{==} is a short and convenient notation for the \f{SET} -function. In fact it is a {\em generalization} of it to allow to -deal also with KERNELS: -\begin{verbatim} - - operator op; - - op(x):=abs(x)$ - - op(x) == x; ==> x - - op(x); ==> x - abs(x); ==> x - -\end{verbatim} -The function \f{RANDOMLIST} generates a list of random numbers. It takes -two arguments which are both integers. The first one indicates the range -inside which the random numbers are chosen. The second one indicates how -many numbers are to be generated. It is also the length of the list which -is generated. -\begin{verbatim} - - RANDOMLIST(10,5); ==> {2,1,3,9,6} - -\end{verbatim} -\f{MKRANDTABL} generates a table of random numbers. This table is either -a one or two dimensional array. The base of random numbers may be either -an integer or a floating point number. In this last case, to work properly, -the switch \f{rounded} must be ON. It has three arguments. The first is -either a one integer or a two integer list. The second is the base chosen -to generate the random numbers. The third is the chosen name for the -generated array. In the example below a two-dimensional table of integer -random numbers is generated as array elements of the identifier {\f ar}. -\begin{verbatim} - - MKRANDTABL({3,4},10,ar); ==> - - *** array ar redefined - - {3,4} - -\end{verbatim} -The output is the array dimension. - -\f{COMBNUM} gives the number of combinations of $n$ objects -taken $p$ to $p$. It has the two integer arguments $n$ and $p$. - -\f{PERMUTATIONS} gives the list of permutations on $n$ objects. -Each permutation is itself a list. \f{CYCLICPERMLIST} gives the list of -{\em cyclic} permutations. For both functions, the argument may -also be a {\tt bag}. -\begin{verbatim} - - PERMUTATIONS {1,2} ==> {{1,2},{2,1}} - - CYCLICPERMLIST {1,2,3} ==> - - {{1,2,3},{2,3,1},{3,1,2}} - -\end{verbatim} -\f{COMBINATIONS} gives a list of combinations on $n$ objects taken $p$ -to $p$. It has two arguments. The first one is a list (or a bag) and -the second one is the integer $p$. -\begin{verbatim} - - COMBINATIONS({1,2,3},2) ==> {{2,3},{1,3},{1,2}} - -\end{verbatim} -\f{REMSYM} is a command that erases the \REDUCE\ commands -\verb+symmetric+ or \verb+antisymmetric+ . - -\f{SYMMETRIZE} is a powerful function which generate a symmetric expression. -It has 3 arguments. The first is a list (or a list of list) containing -the expressions which will appear as variables for a kernel. The second -argument is the kernel-name and the third is a permutation function -which either exist in the algebraic or in the symbolic mode. This -function may have been constructed by the user. Within this package -the two functions \f{PERMUTATIONS} and \f{CYCLICPERMLIST} may be used. -Here are two examples: -\begin{verbatim} - - ll:={a,b,c}$ - - SYMMETRIZE(ll,op,cyclicpermlist); ==> - - OP(A,B,C) + OP(B,C,A) + OP(C,A,B) - - SYMMETRIZE(list ll,op,cyclicpermlist); ==> - - OP({A,B,C}) + OP({B,C,A}) + OP({C,A,B}) - -\end{verbatim} -Notice that, taking for the first argument a list of list gives rise to -an expression where each kernel has a {\em list as argument}. Another -peculiarity of this function is the fact that, unless a pattern maching is -made on the operator \verb+OP+, it needs to be reevaluated. This peculiarity -is induced by the need to maximize efficiency when \verb+OP+ is an abstract -operator. Here is an illustration: -\begin{verbatim} - - op(a,b,c):=a*b*c$ - - SYMMETRIZE(ll,op,cyclicpermlist); ==> - - OP(A,B,C) + OP(B,C,A) + OP(C,A,B) - - for all x let op(x,a,b)=sin(x*a*b); - - SYMMETRIZE(ll,op,cyclicpermlist); ==> - - OP(B,C,A) + SIN(A*B*C) + OP(A,B,C) - -\end{verbatim} -The functions \f{SORTNUMLIST} and \f{SORTLIST} are functions which sort -lists. They use {\em bubblesort} and {\em quicksort} algorithms. - -\f{SORTNUMLIST} takes as argument a list of numbers. It sorts it in -increasing order. - -\f{SORTLIST} is a generalization of the above function. -It sorts the list according -to any well defined ordering. Its first argument is the list and its -second argument is the ordering function. The content of the list -is not necessary numbers but must be such that the ordering function has -a meaning. -\f{ALGSORT} exploits the PSL \f{SORT} function. It is intended to replace -the two functions above. -\begin{verbatim} - - l:={1,3,4,0}$ SORTNUMLIST l; ==> {0,1,3,4} - - ll:={1,a,tt,z}$ SORTLIST(ll,ordp); ==> {a,z,tt,1} - - l:={-1,3,4,0}$ ALGSORT(l,>); ==> {4,3,0,-1} - -\end{verbatim} -One must know that using these functions for kernels or bags may be -dangerous since they are destructive. If it is needed, it is recommended -to first apply \f{KERNLIST} on them. - -The function \f{EXTREMUM} is a generalization of the already defined functions -\f{MIN, MAX} to include general orderings. It is a 2 arguments function. -The first is the list and the second is the ordering function. -With the list \verb+ll+ defined in the last example, one gets -\begin{verbatim} - - EXTREMUM(ll,ordp); ==> 1 - -\end{verbatim} -\item[iii.] There are four functions to identify dependencies. -\f{FUNCVAR} takes any expression as argument and returns the set of -variables on which it depends. Constants are eliminated. -\begin{verbatim} - FUNCVAR(e+pi+sin(log(y)); ==> {y} -\end{verbatim} -\f{DEPATOM} has an {\bf atom} as argument. It returns it if it is -a number or if no dependency has previously been declared. Otherwise, -it returns the list of variables on which it depends as declared in various -{\tt DEPEND} declarations. -\begin{verbatim} - - depend a,x,y; - - DEPATOM a; ==> {x,y} - -\end{verbatim} -The functions \f{EXPLICIT} and \f{IMPLICIT} make explicit or -implicit the dependencies. This example show how they work: -\begin{verbatim} - - depend a,x; depend x,y,z; - - EXPLICIT a; ==> a(x(y,z)) - - IMPLICIT ws; ==> a - -\end{verbatim} -These are useful when one does not know the names of the variables - and (or) the nature of the dependencies. - -\f{KORDERLIST} is a zero argument function which display the actual -ordering. -\begin{verbatim} - - korder x,y,z; - - KORDERLIST; ==> (x,y,z) - -\end{verbatim} -\item[iv.] The function \f{REVAL} which takes an arbitrary expression -is available which {\em forces} down-to-the-botttom simplification of -an expression. It is useful with \f{SYMMETRIZE}.\nl -Here is an example: -\begin{verbatim} - - l:=op(x,y,z)$ - - op(x,y,z):=x*y*z$ - - SYMMETRIZE(l,op,cyclicpermlist); ==> - - op(x,y,z)+op(y,z,x)+op(z,x,y) - - REVAL ws; ==> op(y,z,x)+op(z,x,y)+x*y*z - -\end{verbatim} -\item[v.] Filtering functions for lists. - -\f{CHECKPROLIST} is a boolean function which checks if the -elements of a list have a definite property. Its first argument -is the list, its second argument is a boolean function -(\f{FIXP NUMBERP $\ldots$}) or an ordering function (as \f{ORDP}). - -\f{EXTRACTLIST} extracts from the list given as its first argument -the elements which satisfy the boolean function given as its second -argument. For example: -\begin{verbatim} - - l:={1,a,b,"st")$ - - EXTRACTLIST(l,fixp); ==> {1} - - EXTRACTLIST(l,stringp); ==> {st} - -\end{verbatim} -\ei -\section{Properties and Flags} -In spite of the fact that many facets of the handling of -property lists is easily accessible in the algebraic mode, it is useful to -provide analogous functions {\em genuine} to the algebraic mode. The reason is -that, altering property lists of objects, may easily destroy the integrity -of the system. The functions, which are here described, {\bf do ignore} -the property list and flags already defined by the system itself. They -generate and track the {\em additional properties and flags} that the user -issues using them. They offer him -the possibility to work on property lists so -that he can design a programming style of the ``conceptual'' type. -\bi -\item[i.] We first consider ``flags''. \\ -To a given identifier, one may -associates another one linked to it ``in the background''. The three -functions \f{PUTFLAG, DISPLAYFLAG} and \f{CLEARFLAG} handle them. - -\f{PUTFLAG} has 3 arguments. The first is the identifier or a list -of identifiers, the second is the name of the flag, -the third is T (true) or 0 (zero). -When the third argument is T, it creates the flag, when it is 0 it -destroys it. -\begin{verbatim} - - PUTFLAG(z1,flag_name,t); ==> flag_name - - PUTFLAG({z1,z2},flag1_name,t); ==> t - - PUTFLAG(z2,flag1_name,0) ==> - -\end{verbatim} -\f{DISPLAYFLAG} allows to extract flags. The previous actions give: -\begin{verbatim} - - DISPLAYFLAG z1; ==>{flag_name,flag1_name} - - DISPLAYFLAG z2 ; ==> {} - -\end{verbatim} -\f{CLEARFLAG} is a command which clears {\em all} flags associated to -the identifiers $id_1, \ldots , id_n .$ -\item[ii.] Properties are handled by similar functions. -\f{PUTPROP} has four arguments. The second argument is, here, the -{\em indicator} of the property. The third argument may be {\em any -valid expression}. The fourth can be T or 0. If it is 0, the property -is removed. -\begin{verbatim} - - PUTPROP(z1,property,x^2,t); ==> z1 - -\end{verbatim} -In general, one enter -\begin{verbatim} - - PUTPROP(LIST(idp1,idp2,..),,,T); - -\end{verbatim} -To display a specific property, one uses -\f{DISPLAYPROP} which takes two arguments. The first is the name of the -identifier, the second is the indicator of the property. -\begin{verbatim} - - 2 - DISPLAYPROP(z1,property); ==> {property,x } - -\end{verbatim} -Finally, \f{CLEARPROP} is a nary commmand which clears {\em all} -properties of the identifiers which appear as arguments. -\ei -\section{Control Functions} -Here we describe additional functions which -improve the user control on the environment. -\bi -\item[i.] -The first set of functions is composed of unary and binary boolean functions. -They are: -\begin{verbatim} - - ALATOMP x; x is anything. - ALKERNP x; x is anything. - DEPVARP(x,v); x is anything. - - (v is an atom or a kernel) - -\end{verbatim} -\f{ALATOMP} has the value T iff x is an integer or an identifier -{\em after} it has been evaluated down to the bottom. - -\f{ALKERNP} has the value T iff x is a kernel {\em after} -it has been evaluated down to the bottom. - -\f{DEPVARP} returns T iff the expression x depends on v at -{\bf any level}. - -The above functions together with \f{PRECP} have - been declared operator functions to ease the verification of -their value. - -\f{NORDP} is essentially equivalent to \verb+not+\f{ ORDP} - when inside a conditional statement. Otherwise, it can be used -while \verb+not+\f{ ORDP} cannot. -\item[ii.] -The next functions allow one to {\em analyze} and to -{\em clean} the environment -of \REDUCE\ which is created by the user while he is working -{\bf interactively}. Two functions are provided:\\ -\f{SHOW} allows to get the various identifiers already -assigned and to see their type. \f{SUPPRESS} selectively clears the -used identifiers or clears them all. It is to be stressed that identifiers -assigned from the input of files are {\bf ignored}. -Both functions have one argument and the same options for this -argument: -\begin{verbatim} - - SHOW (SUPPRESS) all - SHOW (SUPPRESS) scalars - SHOW (SUPPRESS) lists - SHOW (SUPPRESS) saveids (for saved expressions) - SHOW (SUPPRESS) matrices - SHOW (SUPPRESS) arrays - SHOW (SUPPRESS) vectors - (contains vector, index and tvector) - SHOW (SUPPRESS) forms - -\end{verbatim} -The option \verb+all+ is the most convenient for \f{SHOW} but, -with it, it may -takes time to get the answer after one has worked several hours. -When entering \REDUCE\ the option \verb+all+ for \f{SHOW} gives: -\begin{verbatim} - - SHOW all; ==> - - scalars are: NIL - arrays are: NIL - lists are: NIL - matrices are: NIL - vectors are: NIL - forms are: NIL - -\end{verbatim} -It is a convenient way to remember the various options. Here an example -which is valid when one starts from a fresh environment: -\begin{verbatim} - - a:=b:=1$ - - SHOW scalars; ==> scalars are: (A B) - - SUPPRESS scalars; ==> t - - SHOW scalars; ==> scalars are: NIL - -\end{verbatim} -\item[iii.] -The \f{CLEAR} function of the system does not do a complete cleaning of -\verb+OPERATORS+ and \verb+FUNCTIONS+ . The following two functions do a more -complete cleaning and, also, takes automatically into account the -{\em user} flag and properties that the functions -\f{PUTFLAG} and \f{PUTPROP} may have introduced. - - -Their names are \f{CLEAROP} and \f{CLEARFUNCTIONS}. -\f{CLEAROP} takes one operator as its argument.\\ - \f{CLEARFUNCTIONS} is a nary command. If one issues - - -\begin{verbatim} - - - CLEARFUNCTIONS a1,a2, ... , an $ - -\end{verbatim} -The functions with names \verb+ a1,a2, ... ,an+ are cleared. -One should be careful when using this facility since the -only functions which cannot be erased are those which are -protected with the \verb+lose+ flag. -\ei -\section{Handling of Polynomials} -The module contains some utility functions to handle -standard quotients and several new facilities to manipulate polynomials. -\bi -\item[i.] Two functions \f{ALG\_TO\_SYMB} and \f{SYMB\_TO\_ALG} -allow to change an expression which is in the algebraic standard -quotient form into a prefix lisp form and vice-versa. This is made -in such a way that the symbol \verb+list+ which appears in the -algebraic mode disappear in the symbolic form (there it becomes -a parenthesis ``()'' ) and it is reintroduced in the translation -from a symbolic prefix lisp expression to an algebraic one. -Here, is an example, showing how the wellknown lisp function -\f{FLATTENS} can be trivially transposed inside the algebraic mode: -\begin{verbatim} - - algebraic procedure ecrase x; - lisp symb_to_alg flattens1 alg_to_symb algebraic x; - - symbolic procedure flattens1 x; - % ll; ==> ((A B) ((C D) E)) - % flattens1 ll; (A B C D E) - if atom x then list x else - if cdr x then - append(flattens1 car x, flattens1 cdr x) - else flattens1 car x; - -\end{verbatim} - - -gives, for instance, -\begin{verbatim} - - ll:={a,{b,{c},d,e},{{{z}}}}$ - - - ECRASE ll; ==> {A, B, C, D, E, Z} - - - -\end{verbatim} -\item[ii.] -\f{LEADTERM} and \f{REDEXPR} are the algebraic equivalent of the -symbolic functions \f{LT} and \f{RED}. They give, respectively, the -{\em leading term} and the {\em reductum} of a polynomial. They also work -for rational functions. Their interest lies in the fact that they do not -require to extract the main variable. They work according to the current -ordering of the system: -\begin{verbatim} - - pol:=x+y+z$ - - LEADTERM pol; ==> x - - korder y,x,z; - - LEADTERM pol; ==> y - - REDEXPR pol; ==> x + z - -\end{verbatim} -By default, the representation of multivariate polynomials is recursive. -% It is justified since it is the one which takes the least of memory. -With such a representation, the function \f{LEADTERM} does not necessarily -extract a true monom. It extracts a monom in the leading indeterminate -multiplied by a polynomial in the other indeterminates. However, very often, - one needs to handle true monoms separately. In that case, one needs a -polynomial in {\em distributive} form. Such a form is provided by the -package GROEBNER (H. Melenk et al.). The facility there is, however, -% much too involved and the necessity to load the package makes interesting -quite complicated, so it makes sense to have -an elementary facility for writing polynomials in a distributive form. So, -a new switch is created to handle {\em distributed} polynomials. It is -called {\tt DISTRIBUTE} and a new function \f{DISTRIBUTE} puts a -polynomial in distributive form. With the switch put to {\bf on}, -\f{LEADTERM} gives {\bf true} monoms. - -\f{MONOM} transforms a polynomial into a list of monoms. It works -{\em whatever the position of the switch} {\tt DISTRIBUTE}. - -\f{SPLITTERMS} is analogous to \f{MONOM} except that it gives -a list of two lists. The first sublist contains the positive terms -while the second sublist contains the negative terms. - -\f{SPLITPLUSMINUS} gives a list whose first element is the positive -part of the polynomial and its second element is its negative part. -\item[iii.] -Two complementary functions \f{LOWESTDEG} and \f{DIVPOL} are provided. -The first takes a polynomial as its first argument and the name of an -indeterminate as its second argument. It returns the {\em lowest degree} - in that indeterminate. The second function takes two polynomials and -returns both the quotient and its remainder. -\ei -\section{Handling of Transcendental Functions} -%\item[i.] -The functions \f{TRIGREDUCE} and \f{TRIGEXPAND} and the equivalent -ones for hyperbolic functions \f{HYPREDUCE} and \f{HYPEXPAND} -make the transformations to multiple arguments and from -multiple arguments to elementary arguments. Here, a simple example: -\begin{verbatim} - - aa:=sin(x+y)$ - - TRIGEXPAND aa; ==> SIN(X)*COS(Y) + SIN(Y)*COS(X) - - TRIGREDUCE ws; ==> SIN(Y + X) - -\end{verbatim} -When a trigonometric or hyperbolic expression is symmetric with -respect to the interchange of {\tt SIN (SINH)} and {\tt COS (COSH)}, -the application of\nl \f{TRIG(HYP)-REDUCE} may often lead to great -simplifications. However, if it is highly asymmetric, the repeated -application of \f{TRIG(HYP)-REDUCE} followed by the use of -\f{TRIG(HYP)-EXPAND} will lead to {\em more} complicated -but more symmetric expressions: -\begin{verbatim} - - aa:=(sin(x)^2+cos(x)^2)^3$ - - TRIGREDUCE aa; ==> 1 - -\end{verbatim} -\pagebreak -\begin{verbatim} - - bb:=1+sin(x)^3$ - - TRIGREDUCE bb; ==> - - - SIN(3*X) + 3*SIN(X) + 4 - --------------------------- - 4 - - TRIGEXPAND ws; ==> - - - 3 2 - SIN(X) - 3*SIN(X)*COS(X) + 3*SIN(X) + 4 - ------------------------------------------- - 4 - -\end{verbatim} -%\ei -\section{Coercion from lists to arrays and converse} -Sometimes when a list is very long and, - especially if frequent access to its elements are needed, -it is advantageous to (temporarily) transform it into an array.\nl -\f{LIST\_TO\_ARRAY} has three arguments. The first is the list. The -second is an integer which indicates the array dimension required. The -third is the name of an identifier which will play the role of the array -name generated by it. If the chosen dimension is not compatible with the -list depth and structure an error message is issued.\nl -\f{ARRAY\_TO\_LIST} does the opposite coercion. It takes the array -name as its sole argument. -\section{Handling of n--dimensional Vectors} -Explicit vectors in {\tt EUCLIDEAN} space may be represented by -list-like or bag-like objects of depth 1. -The components may be bags but may {\bf not} be lists. -Functions are provided to do the sum, the difference and the -scalar product. When, space-dimension is three, there are also functions -for the cross and mixed products. -\f{SUMVECT, MINVECT, SCALVECT, CROSSVECT} have two arguments. -\f{MPVECT} has three arguments. The following example -is sufficient to explain how they work: -\begin{verbatim} - - l:={1,2,3}$ - - ll:=list(a,b,c)$ - - SUMVECT(l,ll); ==> {A + 1,B + 2,C + 3} - - MINVECT(l,ll); ==> { - A + 1, - B + 2, - C + 3} - - SCALVECT(l,ll); ==> A + 2*B + 3*C - - CROSSVECT(l,ll); ==> { - 3*B + 2*C,3*A - C, - 2*A + B} - - MPVECT(l,ll,l); ==> 0 - -\end{verbatim} -\section{Handling of Grassmann Operators} -Grassman variables are often used in physics. For them the multiplication -operation is associative, distributive but anticommutative. The -{\tt KERNEL} of \REDUCE\ does not provide it. However, implementing -it in full generality would almost -certainly decrease the overall efficiency of the system. This small -module together with the declaration of antisymmetry for operators is -enough to deal with most calculations. The reason is, that a -product of similar anticommuting kernels can easily be transformed -into an antisymmetric operator with as many indices as the number of -these kernels. Moreover, one may also issue pattern matching rules -to implement the anticommutativity of the product. -The functions in this module represent the minimum functionality -required to identify them and to handle their specific features. - -\f{PUTGRASS} is a (nary) command which give identifiers the property -to be the names of Grassmann kernels. \f{REMGRASS} removes this property. - -\f{GRASSP} is a boolean function which detects grassmann kernels. - -\f{GRASSPARITY} takes a {\bf monom} as argument and gives its parity. -If the monom is a simple grassmann kernel it returns 1. - -\f{GHOSTFACTOR} has two arguments. Each one is a monom. It is equal to -\begin{verbatim} - - (-1)**(GRASSPARITY u * GRASSPARITY v) - -\end{verbatim} -Here is an illustration to show how the above functions work: -\begin{verbatim} - - PUTGRASS eta; ==> t - - if GRASSP eta(1) then "grassmann kernel"; ==> - - grassmann kernel - - aa:=eta(1)*eta(2)-eta(2)*eta(1); ==> - - AA := - ETA(2)*ETA(1) + ETA(1)*ETA(2) - - GRASSPARITY eta(1); ==> 1 - - GRASSPARITY (eta(1)*eta(2)); ==> 0 - - GHOSTFACTOR(eta(1),eta(2)); ==> -1 - - grasskernel:= - {eta(~x)*eta(~y) => -eta y * eta x when nordp(x,y), - (~x)*(~x) => 0 when grassp x}; - - exp:=eta(1)^2$ - - exp where grasskernel; ==> 0 - - aa where grasskernel; ==> - 2*ETA(2)*ETA(1) - -\end{verbatim} -\section{Handling of Matrices} -This module provides functions for handling matrices more comfortably. -\bi -\item[i.] -Often, one needs to construct some {\tt UNIT} matrix of -a given dimension. This construction is done by the system thanks -to the function \f{UNITMAT}. It is a nary function. The command is -\begin{verbatim} - - UNITMAT M1(n1), M2(n2), .....Mi(ni) ; - -\end{verbatim} -where \verb+M1,...Mi+ are names of matrices and -\verb+ n1, n2, ..., ni+ are integers . - -\f{MKIDM} is a generalization of \f{MKID}. It allows to create a matrix name -from an identifier and a number. For example, if \verb+u+ and \verb+u1+ -are two matrices, one can go from one to the other: -\begin{verbatim} - - matrix u(2,2);$ unitmat u1(2)$ - - u1; ==> - - [1 0] - [ ] - [0 1] - - mkidm(u,1); ==> - - [1 0] - [ ] - [0 1] -\end{verbatim} -This function allows one to make loops on matrices as in the following. -If \verb+U, U1, U2,.., U5+ are matrices, -\begin{verbatim} - FOR I:=1:5 DO U:=U-MKIDM(U,I); -\end{verbatim} -can be issued. -\item[ii.] -The next functions map matrices on bag-like or list-like objects -and conversely they generate matrices from bags or lists. - -\f{COERCEMAT} transforms the matrix \verb+U+ into a list of lists. -The entry is -\begin{verbatim} - - COERCEMAT(U,id) - -\end{verbatim} -where \verb+id+ is equal to \verb+list+ otherwise it transforms it into -a bag of bags whose envelope is equal to \verb+id+. - -\f{BAGLMAT} does the opposite job. The {\bf first} argument is the -bag-like or list-like object while the second argument is the matrix -identifier. The entry is -\begin{verbatim} - - BAGLMAT(bgl,U) - -\end{verbatim} -\verb+bgl+ becomes the matrix \verb+U+ . The transformation is -{\bf not} done if \verb+U+ is {\em already} the name of a -previously defined matrix. This is to avoid ACCIDENTAL redefinition -of that matrix. -\item[ii.] -The functions \f{SUBMAT, MATEXTR, MATEXTC} take parts of a given matrix. - -\f{SUBMAT} has three arguments. The entry is -\begin{verbatim} - - SUBMAT(U,nr,nc) - -\end{verbatim} -The first is the matrix name, and the other two are the row and column -numbers . It gives the -submatrix obtained from \verb+U+ deleting the row \verb+nr+ and -the column \verb+nc+. -When one of them is equal to zero only column \verb+nc+ -or row \verb+nr+ is deleted. - -\f{MATEXTR} and \f{MATEXTC} extract a row or a column and place it into -a list-like or bag-like object. -The entry are -\begin{verbatim} - - MATEXTR(U,VN,nr) - - MATEXTC(U,VN,nc) - -\end{verbatim} -where \verb+U+ is the matrix, \verb+VN+ is the ``vector name'', -\verb+nr+ and \verb+nc+ are integers. If \verb+VN+ is equal -to {\tt list} the vector is given as a list otherwise it is -given as a bag. -\item[iii.] -Functions which manipulate matrices. They are -\f{MATSUBR, MATSUBC, HCONCMAT, VCONCMAT, TPMAT, HERMAT} - -\f{MATSUBR MATSUBC} substitute rows and columns. They have three arguments. -Entries are: -\begin{verbatim} - - MATSUBR(U,bgl,nr) - - MATSUBC(U,bgl,nc) - -\end{verbatim} -The meaning of the variables \verb+U, nr, nc+ is the same as above -while \verb+bgl+ is a list-like or bag-like vector. -Its length should be compatible with the dimensions of the matrix. - -\f{HCONCMAT VCONCMAT} concatenate two matrices. The entries are -\begin{verbatim} - - HCONCMAT(U,V) - - VCONCMAT(U,V) - -\end{verbatim} -The first function concatenates horizontally, the second one -concatenates vertically. The dimensions must match. - -\f{TPMAT} makes the tensor product of two matrices. It is also an -{\em infix} function. The entry is -\begin{verbatim} - - TPMAT(U,V) or U TPMAT V - -\end{verbatim} -\f{HERMAT} takes the hermitian conjugate of a matrix -The entry is -\begin{verbatim} - - HERMAT(U,HU) - -\end{verbatim} -where \verb+HU+ is the identifier for the hermitian matrix of \verb+U+. -It should {\bf unassigned} for this function to work successfully. -This is done on purpose to prevent accidental redefinition of an already -used identifier . -\item[iv.] -\f{SETELMAT GETELMAT} are functions of two integers. The first one -reset the element \verb+(i,j)+ while the second one extract an -element identified by \verb+(i,j)+. They may be useful when -dealing with matrices {\em inside procedures}. -\ei -%\input assist1 -%\input assist2 -%\input assist3 -%\input assist4 -%\input assist5 -%\input assist6 -%\input assist7 -%\input assist8 -\end{document} +\documentstyle[11pt,reduce]{article} +\newcommand{\nl}{\hfill\newline} +\newcommand{\bq}{\begin{quotation}} +\newcommand{\eq}{\end{quotation}} +\newcommand{\bi}{\begin{itemize}} +\newcommand{\ei}{\end{itemize}} +\date{} +\title{{\bf ASSIST}\ :\\[2pt] + A General Purpose Facility~for~\REDUCE \\[5pt] + \mbox{\hfill Version 2.2\hfil}} +\author{Hubert Caprasse \\ +D\'epartement d'Astronomie et d'Astrophysique \\ +Institut de Physique, B--5, Sart Tilman \\ +B--4000 LIEGE 1 +Belgium\\[3pt] +E--mail: caprasse@vm1.ulg.ac.be} +\begin{document} +\maketitle +\index{ASSIST package} +\section{Introduction} + ASSIST contains +an appreciable number of additional general purpose functions which allow +to better adapt \REDUCE\ to various calculational strategies, +to make the programming task more straightforward and more efficient. + +Contrary to all other packages, ASSIST does not aim to provide neither a new +facility to compute a definite class of mathematical objects nor to extend +the base of mathematical knowledge of \REDUCE\ . +The functions it contains should be +useful independently of the nature of the application which is considered. +They were initially written while doing specific applications of +\REDUCE\ to problems in theoretical physics. Most them were designed +in such a way that their applicability range is broad. Though it was not +the primary goal, efficiency has been sought whenever possible. + +The source code in ASSIST contains many comments concerning +the meaaning and the use of the supplementary functions available +in the algebraic mode. These comments, hopefully, makes the code transparent +and allow a thorough exploitation of the package. The present documentation +contains a non--technical description of it and describes the +various new facilities it provides. +\section{ Survey of the Available New Facilities} +An elementary help facility is available both in +the MS-DOS\ and Windows environments. It is made independent of the +help facility of \REDUCE\ itself. It includes only one function: + +\f{HELPASSIST} which takes one argument. +\begin{itemize} +\item[i.] The argument is the identifier \f{assist}. Then the function +gives the informations necessary to retrieve the names of the functions. +\item[ii.] The argument is an integer equal to one of the section number +of the present documentation. Then the names of the functions described +in that section are obtained.\nl +There is, presently, no way to retrieve the number and the nature of the +arguments. +\end{itemize} +The package contains several modules. Their content reflects closely +the various categories of facilities quoted below. Some functions do +already exist inside the KERNEL of \REDUCE\ . However, their range +of applicability is {\em extended}.\nl +\begin{itemize} +\item{Control of Switches:} +\begin{quotation} +\noindent +\f{SWITCHES SWITCHORG} +\end{quotation} +\item{Operations on Lists and Bags:} +\begin{quotation} +\noindent +\f{MKLIST KERNLIST ALGNLIST LENGTH \nl +FREQUENCY SEQUENCES \nl +INSERT INSERT\_KEEP\_ORDER MERGE\_LIST \nl +FIRST SECOND THIRD REST REVERSE LAST \nl +BELAST CONS ( . ) APPEND APPENDN \nl +REMOVE DELETE DELETE\_ALL DELPAIR \nl +MEMBER ELMULT PAIR DEPTH POSITION \nl +REPFIRST REPREST ASFIRST ASLAST ASREST \nl +ASFLIST ASSLIST RESTASLIST SUBSTITUTE \nl +BAGPROP PUTBAG CLEARBAG BAGP BAGLISTP \nl +ALISTP ABAGLISTP LISTBAG } +\end{quotation} +\item{Operations on Sets:} +\begin{quotation} +\noindent +\f{MKSET SETP UNION INTERSECT DIFFSET SYMDIFF} +\end{quotation} +\newpage +\item{General Purpose Utility Functions:} +\begin{quotation} +\noindent +\f{LIST\_TO\_IDS MKIDN MKIDNEW DELLASTDIGIT DETIDNUM \\ +ODDP FOLLOWLINE == RANDOMLIST MKRANDTABL \\ +PERMUTATIONS CYCLICPERMLIST COMBNUM COMBINATIONS \\ +SYMMETRIZE REMSYM SORTNUMLIST SORTLIST ALGSORT \\ +EXTREMUM DEPATOM FUNCVAR IMPLICIT EXPLICIT \\ +KORDERLIST CHECKPROPLIST EXTRACTLIST} +\end{quotation} +\item{ Properties and Flags:} +\begin{quotation} +\noindent +\f{PUTFLAG PUTPROP DISPLAYPROP DISPLAYFLAG \\ +CLEARFLAG CLEARPROP } +\end{quotation} +\item{ Control Statements, Control of Environment:} +\begin{quotation} +\noindent +\f{NORDP DEPVARP ALATOMP ALKERNP PRECP \\ + SHOW SUPPRESS CLEAROP CLEARFUNCTIONS } +\end{quotation} +\item{Handling of Polynomials:} +\begin{quotation} +\noindent +\f{ALG\_TO\_SYMB SYMB\_TO\_ALG \\ +DISTRIBUTE LEADTERM REDEXPR MONOM\\ +LOWESTDEG DIVPOL SPLITTERMS SPLITPLUSMINUS} +\end{quotation} +\item{Handling of Transcendental Functions:} +\begin{quotation} +\noindent +\f{TRIGEXPAND HYPEXPAND TRIGREDUCE HYPREDUCE} +\end{quotation} +\item{Coercion from lists to arrays and converse:} +\begin{quotation} +\f{LIST\_TO\_ARRAY ARRAY\_TO\_LIST} +\end{quotation} +\item{Handling of n-dimensional Vectors:} +\begin{quotation} +\noindent +\f{SUMVECT MINVECT SCALVECT CROSSVECT MPVECT } +\end{quotation} +{\item Handling of Grassmann Operators:} +\begin{quotation} +\noindent +\f{PUTGRASS REMGRASS GRASSP GRASSPARITY GHOSTFACTOR } +\end{quotation} +\item{Handling of Matrices:} +\begin{quotation} +\noindent +\f{UNITMAT MKIDM BAGLMAT COERCEMAT \\ +SUBMAT MATSUBR MATSUBC RMATEXTR RMATEXTC \\ + HCONCMAT VCONCMAT TPMAT HERMAT \\ +SETELTMAT GETELTMAT} +\end{quotation} +\end{itemize} +In the following each group of functions is, successively, described. +\section{Control of Switches} +The two available functions i.e. \f{SWITCHES, SWITCHORG} have +no argument and are called as if they were mere identifiers. + +\f{SWITCHES} displays the actual status of the most often used switches +when manipulating rational functions. The chosen switches are +\begin{quotation} +\noindent +{\tt EXP, DIV, MCD, GCD, ALLFAC, INTSTR,\\ RAT, RATIONAL, FACTOR } +\end{quotation} +The switch {\tt DISTRIBUTE} which controls the handling +of distributed polynomials is added to them (see below the description of +the new functions for manipulating polynomials ). +The selection is somewhat arbitrary but it may be changed in a trivial +fashion by the user. + +Most of the symbolic variables {\tt !*EXP, !*DIV, $\ldots$} +which have either the value T or the value NIL are made available in the +algebraic mode so that it becomes possible to write conditional +statements of the kind +\begin{verbatim} + + IF !*EXP THEN DO ...... + + IF !*GCD THEN OFF GCD; + +\end{verbatim} +\f{SWITCHORG} resets (almost) {\em all} switches in the status +they have when {\bf entering} into \REDUCE\ . +The new switch {\tt DISTRIBUTE} allows to put polynomials in a +distributed form. +\section{Manipulation of the List Structure} + +Additional functions for list manipulations are provided and some already +defined functions in the kernel of \REDUCE\ are modified to properly +generalize them to the available new structure {\tt BAG}. +\begin{itemize} +\item[i.] +Generation of a list of length n with all its elements initialized to 0 +and possibility to append to a list $l$ a certain number of zero's to +make it of length $n$: +\begin{verbatim} + + MKLIST n ; n is an INTEGER + + MKLIST(l,n); l is List-like, n is an INTEGER + +\end{verbatim} + +\item[ii.] +Generation of a list of sublists of length n containing p elements +equal to 0 and q elements equal to 1 such that $$p+q=n .$$ +The function \f{SEQUENCES} works both in the algebraic and +symbolic modes. Here is an example: +\begin{verbatim} + + SEQUENCES 2 ; ==> {{0,0},{0,1},{1,0},{1,1}} + +\end{verbatim} +The function \f{KERNLIST} transforms any prefix of a kernel into the +{\bf \verb+list+} prefix. The output list is a copy: +\begin{verbatim} + + KERNLIST (); ==> {} + +\end{verbatim} +Four functions to delete elements are \f{DELETE, REMOVE, DELETE\_ALL} and +\f{DELPAIR}. The first two act as in symbolic mode, the third +eliminates from a given list {\em all} +elements equal to its first argument. The fourth act on list of pairs +and eliminates from it the {\em first} pair whose first element is equal to +its first argument : +\begin{verbatim} + + DELETE(x,{a,b,x,f,x}); ==> {a,b,f,x} + + REMOVE({a,b,x,f,x},3); ==> {a,b,f,x} + + DELETE_ALL(x,{a,b,x,f,x}); ==> {a,b,f} + + DELPAIR(a,{{a,1},{b,2},{c,3}}; ==> {{b,2},{c,3}} + +\end{verbatim} +\item[iv.] +The function \f{ELMULT} returns an {\em integer} which is the +{\em multiplicity} of its first argument inside the list which is its +second argument. +The function \f{FREQUENCY} gives a list of pairs +whose second element indicates the number of times the first element +appears inside the original list: +\begin{verbatim} + + ELMULT(x,{a,b,x,f,x}) ==> 2 + + FREQUENCY({a,b,c,a}); ==> {{a,2},{b,1},{c,1}} + +\end{verbatim} +\item[v.] +The function \f{INSERT} allows to insert a given object into a list +at the wanted position. + +The functions \f{INSERT\_KEEP\_ORDER} and \f{MERGE\_LIST} allow to +keep a given ordering when inserting one element inside a list or +when merging two lists. Both have 3 arguments. The last one is +the name of a binary boolean ordering function: +\begin{verbatim} + + ll:={1,2,3}$ + + INSERT(x,ll,3); ==> {1,2,x,3} + + INSERT_KEEP_ORDER(5,ll,lessp); ==> {1,2,3,5} + + MERGE_LIST(ll,ll,lessp); ==> {1,1,2,2,3,3} + +\end{verbatim} +\item[vi.] +Algebraic lists can be read from right to left or left to right. +They {\em look} symmetrical. One would like to dispose of manipulation +functions which reflect this. +So, to the already defined functions \f{FIRST} and \f{REST} are +added the functions \f{LAST} and \f{BELAST}. \f{LAST} gives the last +element of the list while \f{BELAST} gives the list {\em without} its +last element. \\ +Various additional functions are provided. They are: +\bq + +\f{ CONS (.), POSITION, DEPTH, PAIR, \\ +APPENDN, REPFIRST, REPLAST} + +\eq +The token ``dot'' needs a special comment. It corresponds to +several different operations. +\begin{enumerate} +\item If one applies it on the left of a list, it acts as the \f{CONS} +function. Be careful, blank spaces are required around the dot: +\begin{verbatim} + + 4 . {a,b}; ==> {4,a,b} + +\end{verbatim} +\item If one applies it on the right of a list, it has the same +effect as the \f{PART} operator: +\begin{verbatim} + + {a,b,c}.2; ==> b + +\end{verbatim} +\item If one applies it on 4--dimensional vectors, it acts as in the +HEPHYS packge. +\end{enumerate} +\f{POSITION} returns the POSITION of the first occurrence of x in +a list or a message if x is not present in it. + +\f{DEPTH} returns an {\em integer} equal to the number of levels where a + list is found if and only if this number is the {\em same} for each + element of the list otherwise it returns a message telling the user + that list is of {\em unequal depth}. + +\f{PAIR} has two arguments which must be lists. It returns a list +whose elements are {\em lists of two elements.} +The $n^{th}$ sublist contains the $n^{th}$ element of the first list +and the $n^{th}$ element of the second list. These types of lists are called +{\em association lists} or ALISTS in the following. +To test for these type of lists a boolean function \f{ABAGLISTP} +is provided. It will be discussed below.\\ +\f{APPENDN} has {\em any} fixed number of lists as arguments. It +generalizes the already existing function \f{APPEND} which accepts +only two lists as arguments. \\ +\f{REPFIRST} has two arguments. The first one is any object, the second one +is a list. It replaces the first element of the list by tho object. It +works like the symbolic function \f{REPLACA} except that the +original list is not destroyed.\\ +\f{REPREST} has also two arguments. It replaces the rest of the list by +its first argument and returns the new list without destroying the +original list. It is analogous to the symbolic function \f{REPLACD}. +Here are examples: +\begin{verbatim} + + ll:={{a,b}}$ + ll1:=ll.1; ==> {a,b} + ll.0; ==> list + 0 . ll; ==> {0,{a,b}} + + DEPTH ll; ==> 2 + + PAIR(ll1,ll1); ==> {{a,a},{b,b}} + + REPFIRST{new,ll); ==> {new} + + ll3:=APPENDN(ll1,ll1,ll1); ==> {a,b,a,b,a,b} + + POSITION(b,ll3); ==> 2 + + REPREST(new,ll3); ==> {a,new} + +\end{verbatim} +\item[vii.] +The functions \f{ASFIRST, ASLAST, ASREST, ASFLIST, ASSLIST, \\RESTASLIST} +act on ALISTS or on list of lists of well defined depths +and have two arguments. The first is the key object +which one seeks to associate in some way to an element of the association +list which is the second argument.\\ +\f{ASFIRST} returns the pair whose first element is equal to the +first argument.\\ +\f{ASLAST} returns the pair whose last element is equal to the first +argument.\\ +\f{ASREST} needs a {\em list} as its first argument. The function +seeks the first sublist of a list of lists (which is its second argument) +equal to its first argument and returns it.\\ +\f{RESTASLIST} has a {\em list of keys} as its first arguments. It +returns the collection of pairs which meet the criterion of \f{ASREST}.\\ +\f{ASFLIST} returns a list containing {\em all pairs} which +satisfy to the criteria of the function \f{ASFIRST}. So the output +is also an ALIST or a list of lists.\\ +\f{ASSLIST} returns a list which contains {\em all pairs} which have +their second element equal to the first argument.\\ +Here are a few examples: +\begin{verbatim} + + lp:={{a,1},{b,2},{c,3}}$ + + ASFIRST(a,lp); ==> {a,1} + + ASLAST(1,lp); ==> {a,1} + + ASREST({1},lp); ==> {a,1} + + RESTASLIST({a,b},lp); ==> {{1},{2}} + + lpp:=APPEND(lp,lp)$ + + ASFLIST(a,lpp); ==> {{a,1},{a,1}} + + ASSLIST(1,lpp); ==> {{a,1},{a,1}} + +\end{verbatim} +\item[vii.] The function \f{SUBSTITUTE} has three arguments. The first +is the object to substitute, the second is the object which must be +replaced by the first, the third is a list. Substitution is made to +all levels. It is a more elementary function than \f{SUB} but its +capabilities are less. When dealing with algebraic quantities, it is +important to make sure that {\em all} objects involved in the function +have either the prefix lisp or the standard quotient representation +otherwise it will not properly work. +\end{itemize} +\section{ The Bag Structure and its Associated Functions} +The LIST structure of \REDUCE\ is very convenient to manipulate +groups of objects which are, a priori, unknown. This structure is +endowed with other properties such as ``mapping'' i.e. the fact that +if \verb+OP+ is an operator one gets, by default, +\begin{verbatim} + + OP({x,y}); ==> {OP(x),OP(y)} + +\end{verbatim} +It is not permitted to submit lists to the operations valid on rings +so that lists cannot be indeterminates of polynomials.\\ +Very frequently too, procedure arguments cannot be lists. +At the other extreme, so to say, one has the \verb+KERNEL+ +structure associated +to the algebraic declaration \verb+operator+ . This structure behaves as +an ``unbreakable'' one and, for that reason, behaves +like an ordinary identifier. +It may generally be bound to all non-numeric procedure parameters +and it may appear +as an ordinary indeterminate inside polynomials. \\ +The \verb+BAG+ structure is intermediate between a list and an operator. +From the operator it borrows the property to be a \verb+KERNEL+ and, +therefore, may be an indeterminate of a polynomial. From the list structure +it borrows the property to be a {\em composite} object.\\[5pt] +\mbox{\underline{{\bf Definition}:\hfill}}\\[4pt] +A bag is an object endowed with the following properties: +\begin{enumerate} +\item It is a \verb+KERNEL+ composed of an atomic prefix (its +envelope) and +its content (miscellaneous objects). +\item Its content may be changed in an analogous way as the content of a +list. During these manipulations the name of the bag is {\em conserved}. +\item Properties may be given to the envelope. For instance, one may +declare it \verb+NONCOM+ or \verb+SYMMETRIC+ etc.\ $\ldots$ +\end{enumerate} +\vspace{5pt} +\mbox{\underline{{\bf Available Functions}:\hfill}} +\bi +\item[i.] A default bag envelope \verb+BAG+ is defined. +It is a reserved identifier. +An identifier other than \verb+LIST+ or one which is already associated +with a boolean function may be defined as a bag envelope through the +command \f{PUTBAG}. In particular, any operator may also be declared +to be a bag. {\bf When and only when} the identifier is not an already defined +function does \f{PUTBAG} puts on it the property of an OPERATOR PREFIX. +The command: +\begin{verbatim} + + PUTBAG id1,id2,....idn; + +\end{verbatim} +declares \verb+id1,.....,idn+ as bag envelopes. +Analoguously, the command +\begin{verbatim} + + CLEARBAG id1,...idn; + +\end{verbatim} +eliminates the bag property on \verb+id1,...,idn+. +\item[ii.] The boolean function \f{BAGP} detects the bag property. +Here is an example: +\begin{verbatim} + + aa:=bag(x,y,z)$ + + if BAGP aa then "ok"; ==> ok + +\end{verbatim} +\item[iii.] Almost all functions defined above for lists +do also work for bags. +Moreover, functions subsequently defined for SETS do also work. +Here is a list of the main ones: +\begin{quotation} +\f{FIRST, SECOND, LAST, REST, BELAST, DEPTH,\\ +LENGTH, APPEND, CONS (.), REPFIRST, REPREST} $\ldots$ +\end{quotation} + +However, because of the conservation of the envelope, they act +somewhat differently. Here are a few examples (more examples are +given inside the test file): +\begin{verbatim} + + PUTBAG op; ==> T + + aa:=op(x,y,z)$ + + FIRST op(x,y,z); ==> op(x) + + REST op(x,y,z); ==> op(y,z) + + BELAST op(x,y,z); ==> op(x,y) + + APPEND(aa,aa); ==> op(x,y,z,x,y,z) + + LENGTH aa; ==> 3 + + DEPTH aa; ==> 1 + +\end{verbatim} +When ``appending'' two bags with {\em different} envelopes, the resulting bag +gets the name of the one bound to the first parameter of \f{APPEND}.\\ +The function \f{LENGTH} gives the actual number of variables on which +the operator (or the function) depends. +\vspace{5pt} +\begin{center} +The NAME of the ENVELOPE is KEPT by the functions \\[3pt] +\f{FIRST, SECOND, LAST, BELAST }. +\end{center} +\vspace{5pt} +\item[iv.] +The connection between the list and the bag structures is made easy +thanks to \f{KERNLIST} which transforms a bag into a list and thanks to +the coercion function \f{LISTBAG}. This function has 2 arguments +and is used as follows: +\begin{verbatim} + + LISTBAG(,); ==> () + +\end{verbatim} +The identifier \verb++, if allowed, is automatically declared as a bag +envelope or an error message is generated. \\[3pt] +Finally, two boolean functions which work both for bags and lists are +provided. They are \f{BAGLISTP} and \f{ABAGLISTP}. +They return t or nil (in a conditional statement) if their argument +is a bag or a list for the first one, if their argument is a list of +sublists or a bag containing bags for the second one . +\end{itemize} +\section{Sets and their Manipulation Functions} +Functions for sets do exist on the level of the symbolic mode. The +package make them available in the algebraic mode but also {\em generalizes} +them so that they can be applied on bag--like objects as well. +\bi +\item[i.] +The constructor \f{MKSET} transforms a list or bag into a set by eliminating +duplicates. +\begin{verbatim} + + MKSET({1,a,a1}); ==> {1,a} + MKSET bag(1,a,a1); ==> bag(1,a) + +\end{verbatim} + +\f{SETP} is a boolean function which recognizes set--like objects. +\begin{verbatim} + + if SETP {1,2,3} then ... ; + +\end{verbatim} +\item[ii.] +The available functions are +\begin{center} +\f{UNION, INTERSECT, DIFFSET, SYMDIFF}. +\end{center} +They have two arguments which must be sets otherwise an error message +is issued. +Their meaning is transparent from their name. They respectively give the +union, the intersection, the difference and the symmetric difference of two +sets. +\ei +\section{General Purpose Utility Functions} +Functions in this sections have various purposes. They have all been used +many times in applications under some form or another. The form given +to them in this package is adjusted to maximize their range of applications. +\bi +\item[i.] +The functions \f{MKIDNEW DELLASTDIGIT DETIDNUM LIST\_TO\_IDS} +handle identifiers. \f{MKIDNEW} is a variant of \f{MKID}. + +\f{MKIDNEW} has either 0 or 1 argument. It generates an identifier which +has not yet been used before. +\begin{verbatim} + + MKIDNEW(); ==> g0001 + + MKIDNEW(a); ==> ag0002 + +\end{verbatim} +\f{DELLASTDIGIT} takes an integer as argument, it strips it from its last +digit. +\begin{verbatim} + + DELLASTDIGIT 45; ==> 4 + +\end{verbatim} +\f{DETIDNUM}, extracts the last digit from an +identifier. It is a very convenient when one wants to make a do loop +starting from a set of indices $ a_1, \ldots , a_{n} $. +\begin{verbatim} + + DETIDNUM a23; ==> 23 + +\end{verbatim} + +\f{LIST\_to\_IDS} generalizes the function \f{MKID} to a list of +atoms. It creates and intern an identifier from the concatenation of +the atoms. The first atom cannot be an integer. +\begin{verbatim} + + LIST_TO_IDS {a,1,id,10}; ==> a1id10 + +\end{verbatim} +The function \f{ODDP} detects odd integers. + +The function \f{FOLLOWLINE} is convenient when using the function \f{PRIN2}. +It allows to format an output text in a much more flexible way than with +the function \f{WRITE}. \\ +Try the following examples : +\begin{verbatim} + + <>$ ==> ? + + <>; ==> ? + +\end{verbatim} +The function \f{==} is a short and convenient notation for the \f{SET} +function. In fact it is a {\em generalization} of it to allow to +deal also with KERNELS: +\begin{verbatim} + + operator op; + + op(x):=abs(x)$ + + op(x) == x; ==> x + + op(x); ==> x + abs(x); ==> x + +\end{verbatim} +The function \f{RANDOMLIST} generates a list of random numbers. It takes +two arguments which are both integers. The first one indicates the range +inside which the random numbers are chosen. The second one indicates how +many numbers are to be generated. It is also the length of the list which +is generated. +\begin{verbatim} + + RANDOMLIST(10,5); ==> {2,1,3,9,6} + +\end{verbatim} +\f{MKRANDTABL} generates a table of random numbers. This table is either +a one or two dimensional array. The base of random numbers may be either +an integer or a floating point number. In this last case, to work properly, +the switch \f{rounded} must be ON. It has three arguments. The first is +either a one integer or a two integer list. The second is the base chosen +to generate the random numbers. The third is the chosen name for the +generated array. In the example below a two-dimensional table of integer +random numbers is generated as array elements of the identifier {\f ar}. +\begin{verbatim} + + MKRANDTABL({3,4},10,ar); ==> + + *** array ar redefined + + {3,4} + +\end{verbatim} +The output is the array dimension. + +\f{COMBNUM} gives the number of combinations of $n$ objects +taken $p$ to $p$. It has the two integer arguments $n$ and $p$. + +\f{PERMUTATIONS} gives the list of permutations on $n$ objects. +Each permutation is itself a list. \f{CYCLICPERMLIST} gives the list of +{\em cyclic} permutations. For both functions, the argument may +also be a {\tt bag}. +\begin{verbatim} + + PERMUTATIONS {1,2} ==> {{1,2},{2,1}} + + CYCLICPERMLIST {1,2,3} ==> + + {{1,2,3},{2,3,1},{3,1,2}} + +\end{verbatim} +\f{COMBINATIONS} gives a list of combinations on $n$ objects taken $p$ +to $p$. It has two arguments. The first one is a list (or a bag) and +the second one is the integer $p$. +\begin{verbatim} + + COMBINATIONS({1,2,3},2) ==> {{2,3},{1,3},{1,2}} + +\end{verbatim} +\f{REMSYM} is a command that erases the \REDUCE\ commands +\verb+symmetric+ or \verb+antisymmetric+ . + +\f{SYMMETRIZE} is a powerful function which generate a symmetric expression. +It has 3 arguments. The first is a list (or a list of list) containing +the expressions which will appear as variables for a kernel. The second +argument is the kernel-name and the third is a permutation function +which either exist in the algebraic or in the symbolic mode. This +function may have been constructed by the user. Within this package +the two functions \f{PERMUTATIONS} and \f{CYCLICPERMLIST} may be used. +Here are two examples: +\begin{verbatim} + + ll:={a,b,c}$ + + SYMMETRIZE(ll,op,cyclicpermlist); ==> + + OP(A,B,C) + OP(B,C,A) + OP(C,A,B) + + SYMMETRIZE(list ll,op,cyclicpermlist); ==> + + OP({A,B,C}) + OP({B,C,A}) + OP({C,A,B}) + +\end{verbatim} +Notice that, taking for the first argument a list of list gives rise to +an expression where each kernel has a {\em list as argument}. Another +peculiarity of this function is the fact that, unless a pattern maching is +made on the operator \verb+OP+, it needs to be reevaluated. This peculiarity +is induced by the need to maximize efficiency when \verb+OP+ is an abstract +operator. Here is an illustration: +\begin{verbatim} + + op(a,b,c):=a*b*c$ + + SYMMETRIZE(ll,op,cyclicpermlist); ==> + + OP(A,B,C) + OP(B,C,A) + OP(C,A,B) + + for all x let op(x,a,b)=sin(x*a*b); + + SYMMETRIZE(ll,op,cyclicpermlist); ==> + + OP(B,C,A) + SIN(A*B*C) + OP(A,B,C) + +\end{verbatim} +The functions \f{SORTNUMLIST} and \f{SORTLIST} are functions which sort +lists. They use {\em bubblesort} and {\em quicksort} algorithms. + +\f{SORTNUMLIST} takes as argument a list of numbers. It sorts it in +increasing order. + +\f{SORTLIST} is a generalization of the above function. +It sorts the list according +to any well defined ordering. Its first argument is the list and its +second argument is the ordering function. The content of the list +is not necessary numbers but must be such that the ordering function has +a meaning. +\f{ALGSORT} exploits the PSL \f{SORT} function. It is intended to replace +the two functions above. +\begin{verbatim} + + l:={1,3,4,0}$ SORTNUMLIST l; ==> {0,1,3,4} + + ll:={1,a,tt,z}$ SORTLIST(ll,ordp); ==> {a,z,tt,1} + + l:={-1,3,4,0}$ ALGSORT(l,>); ==> {4,3,0,-1} + +\end{verbatim} +One must know that using these functions for kernels or bags may be +dangerous since they are destructive. If it is needed, it is recommended +to first apply \f{KERNLIST} on them. + +The function \f{EXTREMUM} is a generalization of the already defined functions +\f{MIN, MAX} to include general orderings. It is a 2 arguments function. +The first is the list and the second is the ordering function. +With the list \verb+ll+ defined in the last example, one gets +\begin{verbatim} + + EXTREMUM(ll,ordp); ==> 1 + +\end{verbatim} +\item[iii.] There are four functions to identify dependencies. +\f{FUNCVAR} takes any expression as argument and returns the set of +variables on which it depends. Constants are eliminated. +\begin{verbatim} + FUNCVAR(e+pi+sin(log(y)); ==> {y} +\end{verbatim} +\f{DEPATOM} has an {\bf atom} as argument. It returns it if it is +a number or if no dependency has previously been declared. Otherwise, +it returns the list of variables on which it depends as declared in various +{\tt DEPEND} declarations. +\begin{verbatim} + + depend a,x,y; + + DEPATOM a; ==> {x,y} + +\end{verbatim} +The functions \f{EXPLICIT} and \f{IMPLICIT} make explicit or +implicit the dependencies. This example show how they work: +\begin{verbatim} + + depend a,x; depend x,y,z; + + EXPLICIT a; ==> a(x(y,z)) + + IMPLICIT ws; ==> a + +\end{verbatim} +These are useful when one does not know the names of the variables + and (or) the nature of the dependencies. + +\f{KORDERLIST} is a zero argument function which display the actual +ordering. +\begin{verbatim} + + korder x,y,z; + + KORDERLIST; ==> (x,y,z) + +\end{verbatim} +\item[iv.] The function \f{REVAL} which takes an arbitrary expression +is available which {\em forces} down-to-the-botttom simplification of +an expression. It is useful with \f{SYMMETRIZE}.\nl +Here is an example: +\begin{verbatim} + + l:=op(x,y,z)$ + + op(x,y,z):=x*y*z$ + + SYMMETRIZE(l,op,cyclicpermlist); ==> + + op(x,y,z)+op(y,z,x)+op(z,x,y) + + REVAL ws; ==> op(y,z,x)+op(z,x,y)+x*y*z + +\end{verbatim} +\item[v.] Filtering functions for lists. + +\f{CHECKPROLIST} is a boolean function which checks if the +elements of a list have a definite property. Its first argument +is the list, its second argument is a boolean function +(\f{FIXP NUMBERP $\ldots$}) or an ordering function (as \f{ORDP}). + +\f{EXTRACTLIST} extracts from the list given as its first argument +the elements which satisfy the boolean function given as its second +argument. For example: +\begin{verbatim} + + l:={1,a,b,"st")$ + + EXTRACTLIST(l,fixp); ==> {1} + + EXTRACTLIST(l,stringp); ==> {st} + +\end{verbatim} +\ei +\section{Properties and Flags} +In spite of the fact that many facets of the handling of +property lists is easily accessible in the algebraic mode, it is useful to +provide analogous functions {\em genuine} to the algebraic mode. The reason is +that, altering property lists of objects, may easily destroy the integrity +of the system. The functions, which are here described, {\bf do ignore} +the property list and flags already defined by the system itself. They +generate and track the {\em additional properties and flags} that the user +issues using them. They offer him +the possibility to work on property lists so +that he can design a programming style of the ``conceptual'' type. +\bi +\item[i.] We first consider ``flags''. \\ +To a given identifier, one may +associates another one linked to it ``in the background''. The three +functions \f{PUTFLAG, DISPLAYFLAG} and \f{CLEARFLAG} handle them. + +\f{PUTFLAG} has 3 arguments. The first is the identifier or a list +of identifiers, the second is the name of the flag, +the third is T (true) or 0 (zero). +When the third argument is T, it creates the flag, when it is 0 it +destroys it. +\begin{verbatim} + + PUTFLAG(z1,flag_name,t); ==> flag_name + + PUTFLAG({z1,z2},flag1_name,t); ==> t + + PUTFLAG(z2,flag1_name,0) ==> + +\end{verbatim} +\f{DISPLAYFLAG} allows to extract flags. The previous actions give: +\begin{verbatim} + + DISPLAYFLAG z1; ==>{flag_name,flag1_name} + + DISPLAYFLAG z2 ; ==> {} + +\end{verbatim} +\f{CLEARFLAG} is a command which clears {\em all} flags associated to +the identifiers $id_1, \ldots , id_n .$ +\item[ii.] Properties are handled by similar functions. +\f{PUTPROP} has four arguments. The second argument is, here, the +{\em indicator} of the property. The third argument may be {\em any +valid expression}. The fourth can be T or 0. If it is 0, the property +is removed. +\begin{verbatim} + + PUTPROP(z1,property,x^2,t); ==> z1 + +\end{verbatim} +In general, one enter +\begin{verbatim} + + PUTPROP(LIST(idp1,idp2,..),,,T); + +\end{verbatim} +To display a specific property, one uses +\f{DISPLAYPROP} which takes two arguments. The first is the name of the +identifier, the second is the indicator of the property. +\begin{verbatim} + + 2 + DISPLAYPROP(z1,property); ==> {property,x } + +\end{verbatim} +Finally, \f{CLEARPROP} is a nary commmand which clears {\em all} +properties of the identifiers which appear as arguments. +\ei +\section{Control Functions} +Here we describe additional functions which +improve the user control on the environment. +\bi +\item[i.] +The first set of functions is composed of unary and binary boolean functions. +They are: +\begin{verbatim} + + ALATOMP x; x is anything. + ALKERNP x; x is anything. + DEPVARP(x,v); x is anything. + + (v is an atom or a kernel) + +\end{verbatim} +\f{ALATOMP} has the value T iff x is an integer or an identifier +{\em after} it has been evaluated down to the bottom. + +\f{ALKERNP} has the value T iff x is a kernel {\em after} +it has been evaluated down to the bottom. + +\f{DEPVARP} returns T iff the expression x depends on v at +{\bf any level}. + +The above functions together with \f{PRECP} have + been declared operator functions to ease the verification of +their value. + +\f{NORDP} is essentially equivalent to \verb+not+\f{ ORDP} + when inside a conditional statement. Otherwise, it can be used +while \verb+not+\f{ ORDP} cannot. +\item[ii.] +The next functions allow one to {\em analyze} and to +{\em clean} the environment +of \REDUCE\ which is created by the user while he is working +{\bf interactively}. Two functions are provided:\\ +\f{SHOW} allows to get the various identifiers already +assigned and to see their type. \f{SUPPRESS} selectively clears the +used identifiers or clears them all. It is to be stressed that identifiers +assigned from the input of files are {\bf ignored}. +Both functions have one argument and the same options for this +argument: +\begin{verbatim} + + SHOW (SUPPRESS) all + SHOW (SUPPRESS) scalars + SHOW (SUPPRESS) lists + SHOW (SUPPRESS) saveids (for saved expressions) + SHOW (SUPPRESS) matrices + SHOW (SUPPRESS) arrays + SHOW (SUPPRESS) vectors + (contains vector, index and tvector) + SHOW (SUPPRESS) forms + +\end{verbatim} +The option \verb+all+ is the most convenient for \f{SHOW} but, +with it, it may +takes time to get the answer after one has worked several hours. +When entering \REDUCE\ the option \verb+all+ for \f{SHOW} gives: +\begin{verbatim} + + SHOW all; ==> + + scalars are: NIL + arrays are: NIL + lists are: NIL + matrices are: NIL + vectors are: NIL + forms are: NIL + +\end{verbatim} +It is a convenient way to remember the various options. Here an example +which is valid when one starts from a fresh environment: +\begin{verbatim} + + a:=b:=1$ + + SHOW scalars; ==> scalars are: (A B) + + SUPPRESS scalars; ==> t + + SHOW scalars; ==> scalars are: NIL + +\end{verbatim} +\item[iii.] +The \f{CLEAR} function of the system does not do a complete cleaning of +\verb+OPERATORS+ and \verb+FUNCTIONS+ . The following two functions do a more +complete cleaning and, also, takes automatically into account the +{\em user} flag and properties that the functions +\f{PUTFLAG} and \f{PUTPROP} may have introduced. + + +Their names are \f{CLEAROP} and \f{CLEARFUNCTIONS}. +\f{CLEAROP} takes one operator as its argument.\\ + \f{CLEARFUNCTIONS} is a nary command. If one issues + + +\begin{verbatim} + + + CLEARFUNCTIONS a1,a2, ... , an $ + +\end{verbatim} +The functions with names \verb+ a1,a2, ... ,an+ are cleared. +One should be careful when using this facility since the +only functions which cannot be erased are those which are +protected with the \verb+lose+ flag. +\ei +\section{Handling of Polynomials} +The module contains some utility functions to handle +standard quotients and several new facilities to manipulate polynomials. +\bi +\item[i.] Two functions \f{ALG\_TO\_SYMB} and \f{SYMB\_TO\_ALG} +allow to change an expression which is in the algebraic standard +quotient form into a prefix lisp form and vice-versa. This is made +in such a way that the symbol \verb+list+ which appears in the +algebraic mode disappear in the symbolic form (there it becomes +a parenthesis ``()'' ) and it is reintroduced in the translation +from a symbolic prefix lisp expression to an algebraic one. +Here, is an example, showing how the wellknown lisp function +\f{FLATTENS} can be trivially transposed inside the algebraic mode: +\begin{verbatim} + + algebraic procedure ecrase x; + lisp symb_to_alg flattens1 alg_to_symb algebraic x; + + symbolic procedure flattens1 x; + % ll; ==> ((A B) ((C D) E)) + % flattens1 ll; (A B C D E) + if atom x then list x else + if cdr x then + append(flattens1 car x, flattens1 cdr x) + else flattens1 car x; + +\end{verbatim} + + +gives, for instance, +\begin{verbatim} + + ll:={a,{b,{c},d,e},{{{z}}}}$ + + + ECRASE ll; ==> {A, B, C, D, E, Z} + + + +\end{verbatim} +\item[ii.] +\f{LEADTERM} and \f{REDEXPR} are the algebraic equivalent of the +symbolic functions \f{LT} and \f{RED}. They give, respectively, the +{\em leading term} and the {\em reductum} of a polynomial. They also work +for rational functions. Their interest lies in the fact that they do not +require to extract the main variable. They work according to the current +ordering of the system: +\begin{verbatim} + + pol:=x+y+z$ + + LEADTERM pol; ==> x + + korder y,x,z; + + LEADTERM pol; ==> y + + REDEXPR pol; ==> x + z + +\end{verbatim} +By default, the representation of multivariate polynomials is recursive. +% It is justified since it is the one which takes the least of memory. +With such a representation, the function \f{LEADTERM} does not necessarily +extract a true monom. It extracts a monom in the leading indeterminate +multiplied by a polynomial in the other indeterminates. However, very often, + one needs to handle true monoms separately. In that case, one needs a +polynomial in {\em distributive} form. Such a form is provided by the +package GROEBNER (H. Melenk et al.). The facility there is, however, +% much too involved and the necessity to load the package makes interesting +quite complicated, so it makes sense to have +an elementary facility for writing polynomials in a distributive form. So, +a new switch is created to handle {\em distributed} polynomials. It is +called {\tt DISTRIBUTE} and a new function \f{DISTRIBUTE} puts a +polynomial in distributive form. With the switch put to {\bf on}, +\f{LEADTERM} gives {\bf true} monoms. + +\f{MONOM} transforms a polynomial into a list of monoms. It works +{\em whatever the position of the switch} {\tt DISTRIBUTE}. + +\f{SPLITTERMS} is analogous to \f{MONOM} except that it gives +a list of two lists. The first sublist contains the positive terms +while the second sublist contains the negative terms. + +\f{SPLITPLUSMINUS} gives a list whose first element is the positive +part of the polynomial and its second element is its negative part. +\item[iii.] +Two complementary functions \f{LOWESTDEG} and \f{DIVPOL} are provided. +The first takes a polynomial as its first argument and the name of an +indeterminate as its second argument. It returns the {\em lowest degree} + in that indeterminate. The second function takes two polynomials and +returns both the quotient and its remainder. +\ei +\section{Handling of Transcendental Functions} +%\item[i.] +The functions \f{TRIGREDUCE} and \f{TRIGEXPAND} and the equivalent +ones for hyperbolic functions \f{HYPREDUCE} and \f{HYPEXPAND} +make the transformations to multiple arguments and from +multiple arguments to elementary arguments. Here, a simple example: +\begin{verbatim} + + aa:=sin(x+y)$ + + TRIGEXPAND aa; ==> SIN(X)*COS(Y) + SIN(Y)*COS(X) + + TRIGREDUCE ws; ==> SIN(Y + X) + +\end{verbatim} +When a trigonometric or hyperbolic expression is symmetric with +respect to the interchange of {\tt SIN (SINH)} and {\tt COS (COSH)}, +the application of\nl \f{TRIG(HYP)-REDUCE} may often lead to great +simplifications. However, if it is highly asymmetric, the repeated +application of \f{TRIG(HYP)-REDUCE} followed by the use of +\f{TRIG(HYP)-EXPAND} will lead to {\em more} complicated +but more symmetric expressions: +\begin{verbatim} + + aa:=(sin(x)^2+cos(x)^2)^3$ + + TRIGREDUCE aa; ==> 1 + +\end{verbatim} +\pagebreak +\begin{verbatim} + + bb:=1+sin(x)^3$ + + TRIGREDUCE bb; ==> + + - SIN(3*X) + 3*SIN(X) + 4 + --------------------------- + 4 + + TRIGEXPAND ws; ==> + + + 3 2 + SIN(X) - 3*SIN(X)*COS(X) + 3*SIN(X) + 4 + ------------------------------------------- + 4 + +\end{verbatim} +%\ei +\section{Coercion from lists to arrays and converse} +Sometimes when a list is very long and, + especially if frequent access to its elements are needed, +it is advantageous to (temporarily) transform it into an array.\nl +\f{LIST\_TO\_ARRAY} has three arguments. The first is the list. The +second is an integer which indicates the array dimension required. The +third is the name of an identifier which will play the role of the array +name generated by it. If the chosen dimension is not compatible with the +list depth and structure an error message is issued.\nl +\f{ARRAY\_TO\_LIST} does the opposite coercion. It takes the array +name as its sole argument. +\section{Handling of n--dimensional Vectors} +Explicit vectors in {\tt EUCLIDEAN} space may be represented by +list-like or bag-like objects of depth 1. +The components may be bags but may {\bf not} be lists. +Functions are provided to do the sum, the difference and the +scalar product. When, space-dimension is three, there are also functions +for the cross and mixed products. +\f{SUMVECT, MINVECT, SCALVECT, CROSSVECT} have two arguments. +\f{MPVECT} has three arguments. The following example +is sufficient to explain how they work: +\begin{verbatim} + + l:={1,2,3}$ + + ll:=list(a,b,c)$ + + SUMVECT(l,ll); ==> {A + 1,B + 2,C + 3} + + MINVECT(l,ll); ==> { - A + 1, - B + 2, - C + 3} + + SCALVECT(l,ll); ==> A + 2*B + 3*C + + CROSSVECT(l,ll); ==> { - 3*B + 2*C,3*A - C, - 2*A + B} + + MPVECT(l,ll,l); ==> 0 + +\end{verbatim} +\section{Handling of Grassmann Operators} +Grassman variables are often used in physics. For them the multiplication +operation is associative, distributive but anticommutative. The +{\tt KERNEL} of \REDUCE\ does not provide it. However, implementing +it in full generality would almost +certainly decrease the overall efficiency of the system. This small +module together with the declaration of antisymmetry for operators is +enough to deal with most calculations. The reason is, that a +product of similar anticommuting kernels can easily be transformed +into an antisymmetric operator with as many indices as the number of +these kernels. Moreover, one may also issue pattern matching rules +to implement the anticommutativity of the product. +The functions in this module represent the minimum functionality +required to identify them and to handle their specific features. + +\f{PUTGRASS} is a (nary) command which give identifiers the property +to be the names of Grassmann kernels. \f{REMGRASS} removes this property. + +\f{GRASSP} is a boolean function which detects grassmann kernels. + +\f{GRASSPARITY} takes a {\bf monom} as argument and gives its parity. +If the monom is a simple grassmann kernel it returns 1. + +\f{GHOSTFACTOR} has two arguments. Each one is a monom. It is equal to +\begin{verbatim} + + (-1)**(GRASSPARITY u * GRASSPARITY v) + +\end{verbatim} +Here is an illustration to show how the above functions work: +\begin{verbatim} + + PUTGRASS eta; ==> t + + if GRASSP eta(1) then "grassmann kernel"; ==> + + grassmann kernel + + aa:=eta(1)*eta(2)-eta(2)*eta(1); ==> + + AA := - ETA(2)*ETA(1) + ETA(1)*ETA(2) + + GRASSPARITY eta(1); ==> 1 + + GRASSPARITY (eta(1)*eta(2)); ==> 0 + + GHOSTFACTOR(eta(1),eta(2)); ==> -1 + + grasskernel:= + {eta(~x)*eta(~y) => -eta y * eta x when nordp(x,y), + (~x)*(~x) => 0 when grassp x}; + + exp:=eta(1)^2$ + + exp where grasskernel; ==> 0 + + aa where grasskernel; ==> - 2*ETA(2)*ETA(1) + +\end{verbatim} +\section{Handling of Matrices} +This module provides functions for handling matrices more comfortably. +\bi +\item[i.] +Often, one needs to construct some {\tt UNIT} matrix of +a given dimension. This construction is done by the system thanks +to the function \f{UNITMAT}. It is a nary function. The command is +\begin{verbatim} + + UNITMAT M1(n1), M2(n2), .....Mi(ni) ; + +\end{verbatim} +where \verb+M1,...Mi+ are names of matrices and +\verb+ n1, n2, ..., ni+ are integers . + +\f{MKIDM} is a generalization of \f{MKID}. It allows to create a matrix name +from an identifier and a number. For example, if \verb+u+ and \verb+u1+ +are two matrices, one can go from one to the other: +\begin{verbatim} + + matrix u(2,2);$ unitmat u1(2)$ + + u1; ==> + + [1 0] + [ ] + [0 1] + + mkidm(u,1); ==> + + [1 0] + [ ] + [0 1] +\end{verbatim} +This function allows one to make loops on matrices as in the following. +If \verb+U, U1, U2,.., U5+ are matrices, +\begin{verbatim} + FOR I:=1:5 DO U:=U-MKIDM(U,I); +\end{verbatim} +can be issued. +\item[ii.] +The next functions map matrices on bag-like or list-like objects +and conversely they generate matrices from bags or lists. + +\f{COERCEMAT} transforms the matrix \verb+U+ into a list of lists. +The entry is +\begin{verbatim} + + COERCEMAT(U,id) + +\end{verbatim} +where \verb+id+ is equal to \verb+list+ otherwise it transforms it into +a bag of bags whose envelope is equal to \verb+id+. + +\f{BAGLMAT} does the opposite job. The {\bf first} argument is the +bag-like or list-like object while the second argument is the matrix +identifier. The entry is +\begin{verbatim} + + BAGLMAT(bgl,U) + +\end{verbatim} +\verb+bgl+ becomes the matrix \verb+U+ . The transformation is +{\bf not} done if \verb+U+ is {\em already} the name of a +previously defined matrix. This is to avoid ACCIDENTAL redefinition +of that matrix. +\item[ii.] +The functions \f{SUBMAT, MATEXTR, MATEXTC} take parts of a given matrix. + +\f{SUBMAT} has three arguments. The entry is +\begin{verbatim} + + SUBMAT(U,nr,nc) + +\end{verbatim} +The first is the matrix name, and the other two are the row and column +numbers . It gives the +submatrix obtained from \verb+U+ deleting the row \verb+nr+ and +the column \verb+nc+. +When one of them is equal to zero only column \verb+nc+ +or row \verb+nr+ is deleted. + +\f{MATEXTR} and \f{MATEXTC} extract a row or a column and place it into +a list-like or bag-like object. +The entry are +\begin{verbatim} + + MATEXTR(U,VN,nr) + + MATEXTC(U,VN,nc) + +\end{verbatim} +where \verb+U+ is the matrix, \verb+VN+ is the ``vector name'', +\verb+nr+ and \verb+nc+ are integers. If \verb+VN+ is equal +to {\tt list} the vector is given as a list otherwise it is +given as a bag. +\item[iii.] +Functions which manipulate matrices. They are +\f{MATSUBR, MATSUBC, HCONCMAT, VCONCMAT, TPMAT, HERMAT} + +\f{MATSUBR MATSUBC} substitute rows and columns. They have three arguments. +Entries are: +\begin{verbatim} + + MATSUBR(U,bgl,nr) + + MATSUBC(U,bgl,nc) + +\end{verbatim} +The meaning of the variables \verb+U, nr, nc+ is the same as above +while \verb+bgl+ is a list-like or bag-like vector. +Its length should be compatible with the dimensions of the matrix. + +\f{HCONCMAT VCONCMAT} concatenate two matrices. The entries are +\begin{verbatim} + + HCONCMAT(U,V) + + VCONCMAT(U,V) + +\end{verbatim} +The first function concatenates horizontally, the second one +concatenates vertically. The dimensions must match. + +\f{TPMAT} makes the tensor product of two matrices. It is also an +{\em infix} function. The entry is +\begin{verbatim} + + TPMAT(U,V) or U TPMAT V + +\end{verbatim} +\f{HERMAT} takes the hermitian conjugate of a matrix +The entry is +\begin{verbatim} + + HERMAT(U,HU) + +\end{verbatim} +where \verb+HU+ is the identifier for the hermitian matrix of \verb+U+. +It should {\bf unassigned} for this function to work successfully. +This is done on purpose to prevent accidental redefinition of an already +used identifier . +\item[iv.] +\f{SETELMAT GETELMAT} are functions of two integers. The first one +reset the element \verb+(i,j)+ while the second one extract an +element identified by \verb+(i,j)+. They may be useful when +dealing with matrices {\em inside procedures}. +\ei +%\input assist1 +%\input assist2 +%\input assist3 +%\input assist4 +%\input assist5 +%\input assist6 +%\input assist7 +%\input assist8 +\end{document} Index: r36/doc/AVECTOR.TEX ================================================================== --- r36/doc/AVECTOR.TEX +++ r36/doc/AVECTOR.TEX @@ -1,422 +1,422 @@ -\documentstyle[11pt,reduce]{article} -\date{} -\title{A Vector Algebra and Calculus Package for REDUCE} -\author{David Harper \\ -Astronomy Unit \\ -Queen Mary and Westfield College \\ -University of London \\ -Mile End Road \\ -London E1 4NS \\ -England \\[0.05in] -Electronic mail: {\it adh@star.qmw.ac.uk}} -\begin{document} -\maketitle - -\index{AVECTOR package} - -\section{Introduction} - -This package \footnote{Reference: Computer Physics Communications, -{\bf 54}, 295-305 (1989)} -is written in RLISP (the LISP meta-language) and is -intended for use with REDUCE 3.4. \index{vector algebra} It provides -REDUCE with the ability to perform vector algebra using the same -notation as scalar algebra. The basic algebraic operations are -supported, as are differentiation and integration of vectors with -respect to scalar variables, cross product and dot product, component -manipulation and application of scalar functions ({\em e.g.} cosine) -to a vector to yield a vector result. - -A set of vector calculus operators are provided for use with any -orthogonal curvilinear coordinate system. These operators are -gradient, divergence, curl and del-squared (Laplacian). The Laplacian -operator can take scalar or vector arguments. - -Several important coordinate systems are pre-defined and can be -invoked by name. It is also possible to create new coordinate systems -by specifying the names of the coordinates and the values of the scale -factors. - -\section{Vector declaration and initialisation} - -Any name may be declared to be a vector, provided that it has -not previously been declared as a matrix or an array. To -declare a list of names to be vectors use the VEC command: -\index{VEC command} -\begin{verbatim} - VEC A,B,C; -\end{verbatim} -declares the variables {\tt A}, {\tt B} and {\tt C} to be vectors. -If they have already been assigned (scalar) values, these will be lost. - -When a vector is declared using the {\tt VEC} command, it does not -have an initial value. - -If a vector value is assigned to a scalar variable, then that -variable will automatically be declared as a vector and the -user will be notified that this has happened. - -\index{AVEC function} -A vector may be initialised using the {\tt AVEC} function which -takes three scalar arguments and returns a vector made up -from those scalars. For example -\begin{verbatim} - A := AVEC(A1, A2, A3); -\end{verbatim} -sets the components of the vector {\tt A} to {\tt A1}, {\tt A2} and {\tt A3}. - -\section{Vector algebra} - -(In the examples which follow, {\tt V}, {\tt V1}, {\tt V2} {\em etc} -are assumed to be vectors while {\tt S}, {\tt S1}, {\tt S2} etc are scalars.) - -\index{+ ! vector} \index{- ! vector} \index{* ! vector} \index{/ ! vector} -The scalar algebra operators +,-,* and / may be used with -vector operands according to the rules of vector algebra. -Thus multiplication and division of a vector by a scalar -are both allowed, but it is an error to multiply or -divide one vector by another. - -\begin{tabular}{l l} -{\tt V := V1 + V2 - V3;} & Addition and subtraction \\ -{\tt V := S1*3*V1;} & Scalar multiplication \\ -{\tt V := V1/S;} & Scalar division \\ -{\tt V := -V1;} & Negation \\ -\end{tabular} - -\index{DOT ! vector} \index{Dot product} \index{CROSS ! vector} -\index{cross product} -\noindent Vector multiplication is carried out using the infix -operators {\tt DOT} and {\tt CROSS}. These are defined to have -higher precedence than scalar multiplication and -division. - -\begin{tabular}{l l} -{\tt V := V1 CROSS V2;} & Cross product \\ -{\tt S := V1 DOT V2;} & Dot product \\ -{\tt V := V1 CROSS V2 + V3;} & \\ -{\tt V := (V1 CROSS V2) + V3;} & \\ -\end{tabular} - -The last two expressions are equivalent due to the precedence of -the {\tt CROSS} operator. - -\index{VMOD operator} -The modulus of a vector may be calculated using the {\tt VMOD} operator. - -\begin{verbatim} - S := VMOD V; -\end{verbatim} - -A unit vector may be generated from any vector using the {\tt VMOD} -operator. - -\begin{verbatim} - V1 := V/(VMOD V); -\end{verbatim} - -Components may be extracted from any vector using index notation -in the same way as an array. - -\begin{tabular}{l l} -{\tt V := AVEC(AX, AY, AZ);} & \\ -{\tt V(0);} & yields AX \\ -{\tt V(1);} & yields AY \\ -{\tt V(2);} & yields AZ \\ -\end{tabular} - -It is also possible to set values of individual components. Following -from above: - -\begin{verbatim} - V(1) := B; -\end{verbatim} - -The vector {\tt V} now has components {\tt AX}, {\tt B}, {\tt AZ}. - -\index{vector ! differentiation} \index{vector ! integration} -\index{differentiation ! vector} \index{differentiation ! vector} -Vectors may be used as arguments in the differentiation and -integration routines in place of the dependent expression. - -\begin{tabular}{l l} -{\tt V := AVEC(X**2, SIN(X), Y);} & \\ -{\tt DF(V,X);} & yields (2*X, COS(X), 0) \\ -{\tt INT(V,X);} & yields (X**3/3, -COS(X), Y*X) \\ -\end{tabular} - -Vectors may be given as arguments to monomial functions such as {\tt -SIN}, {\tt LOG} and {\tt TAN}. The result is a vector obtained by -applying the function component-wise to the argument vector. - -\begin{tabular}{l l} -{\tt V := AVEC(A1, A2, A3);} & \\ -{\tt SIN(V);} & yields (SIN(A1), SIN(A2), SIN(A3)) \\ -\end{tabular} - -\section{ Vector calculus} - -\index{DIV ! operator} \index{divergence ! vector field} -\index{GRAD ! operator} \index{gradient ! vector field} -\index{CURL ! operator} \index{curl ! vector field} -\index{DELSQ ! operator} \index{Laplacian ! vector field} -The vector calculus operators div, grad and curl are recognised. -The Laplacian operator is also available and may be applied to -scalar and vector arguments. - -\begin{tabular}{l l} -{\tt V := GRAD S;} & Gradient of a scalar field \\ -{\tt S := DIV V;} & Divergence of a vector field \\ -{\tt V := CURL V1;} & Curl of a vector field \\ -{\tt S := DELSQ S1;} & Laplacian of a scalar field \\ -{\tt V := DELSQ V1;} & Laplacian of a vector field \\ -\end{tabular} - -These operators may be used in any orthogonal curvilinear coordinate -system. The user may alter the names of the coordinates and the values -of the scale factors. Initially the coordinates are {\tt X}, {\tt Y} -and {\tt Z} and the scale factors are all unity. - -\index{COORDS vector} \index{HFACTORS scale factors} -There are two special vectors : {\tt COORDS} contains the names -of the coordinates in the current system and {\tt HFACTORS} -contains the values of the scale factors. - -\index{COORDINATES operator} -The coordinate names may be changed using the {\tt COORDINATES} -operator. - -\begin{verbatim} - COORDINATES R,THETA,PHI; -\end{verbatim} - -This command changes the coordinate names to {\tt R}, {\tt THETA} and -{\tt PHI}. - -\index{SCALEFACTORS operator} -The scale factors may be altered using the {\tt SCALEFACTORS} operator. - -\begin{verbatim} - SCALEFACTORS(1,R,R*SIN(THETA)); -\end{verbatim} - -This command changes the scale factors to {\tt 1}, {\tt R} and {\tt R -SIN(THETA)}. - -Note that the arguments of {\tt SCALEFACTORS} must be enclosed in -parentheses. This is not necessary with {\tt COORDINATES}. - - -When vector differential operators are applied to an expression, -the current set of coordinates are used as the independent -variables and the scale factors are employed in the calculation. -(See, for example, Batchelor G.K. 'An Introduction to Fluid -Mechanics', Appendix 2.) - - -\index{"!*CSYSTEMS global (AVECTOR)} -Several coordinate systems are pre-defined and may be invoked by -name. To see a list of valid names enter - -\begin{verbatim} - SYMBOLIC !*CSYSTEMS; -\end{verbatim} - -and REDUCE will respond with something like - -\begin{verbatim} - (CARTESIAN SPHERICAL CYLINDRICAL) -\end{verbatim} - -\index{GETCSYSTEM command} -To choose a coordinate system by name, use the command {\tt GETCSYSTEM}. - -To choose the Cartesian coordinate system : -\begin{verbatim} - GETCSYSTEM 'CARTESIAN; -\end{verbatim} -\index{PUTCSYSTEM command} - -Note the quote which prefixes the name of the coordinate system. This -is required because {\tt GETCSYSTEM} (and its complement {\tt -PUTCSYSTEM}) is a {\tt SYMBOLIC} procedure which requires a literal -argument. - -REDUCE responds by typing a list of the coordinate names in that -coordinate system. The example above would produce the response - -\begin{verbatim} - (X Y Z) -\end{verbatim} - -whilst - -\begin{verbatim} - GETCSYSTEM 'SPHERICAL; -\end{verbatim} - -would produce - -\begin{verbatim} - (R THETA PHI) -\end{verbatim} - -Note that any attempt to invoke a coordinate system is subject to the -same restrictions as the implied calls to {\tt COORDINATES} and {\tt -SCALEFACTORS}. In particular, {\tt GETCSYSTEM} fails if any of the -coordinate names has been assigned a value and the previous coordinate -system remains in effect. - -A user-defined coordinate system can be assigned a name using the -command {\tt PUTCSYSTEM}. It may then be re-invoked at a later stage using -{\tt GETCSYSTEM}. - -\example\index{AVECTOR package ! example} - -We define a general coordinate system with coordinate names {\tt -X},{\tt Y},{\tt Z} and scale factors {\tt H1},{\tt H2},{\tt H3} : - -\begin{verbatim} - COORDINATES X,Y,Z; - SCALEFACTORS(H1,H2,H3); - PUTCSYSTEM 'GENERAL; -\end{verbatim} - -This system may later be invoked by entering - -\begin{verbatim} - GETCSYSTEM 'GENERAL; -\end{verbatim} - -\section{Volume and Line Integration} - -Several functions are provided to perform volume and line integrals. -These operate in any orthogonal curvilinear coordinate system and -make use of the scale factors described in the previous section. - - -Definite integrals of scalar and vector expressions may be calculated -using the {\tt DEFINT} function. - -\example\index{AVECTOR package ! example} - -\index{DEFINT function} \index{integration ! definite (simple)} -\index{definite integration (simple)} -\noindent To calculate the definite integral of $\sin(x)^2$ between 0 and -2$\pi$ we enter - -\begin{verbatim} - DEFINT(SIN(X)**2,X,0,2*PI); -\end{verbatim} - -This function is a simple extension of the {\tt INT} function taking -two extra arguments, the lower and upper bounds of integration -respectively. - -\index{VOLINTEGRAL function} \index{integration ! volume} -Definite volume integrals may be calculated using the {\tt -VOLINTEGRAL} function whose syntax is as follows : - -\noindent {\tt VOLINTEGRAL}({\tt integrand}, vector {\tt lower-bound}, -vector {\tt upper-bound}); - -\example\index{AVECTOR package ! example} - -\noindent In spherical polar coordinates we may calculate the volume of a -sphere by integrating unity over the range $r$=0 to {\tt RR}, $\theta$=0 to -{\tt PI}, $\phi$=0 to 2*$\pi$ as follows : - -\begin{tabular}{l l} -{\tt VLB := AVEC(0,0,0);} & Lower bound \\ -{\tt VUB := AVEC(RR,PI,2*PI);} & Upper bound in $r, \theta, \phi$ - respectively \\ -{\tt VOLINTORDER := (0,1,2);} & The order of integration \\ -{\tt VOLINTEGRAL(1,VLB,VUB);} & \\ -\end{tabular} - -\index{VOLINTORDER vector} -Note the use of the special vector {\tt VOLINTORDER} which controls -the order in which the integrations are carried out. This vector -should be set to contain the number 0, 1 and 2 in the required order. -The first component of {\tt VOLINTORDER} contains the index of the -first integration variable, the second component is the index of the -second integration variable and the third component is the index of -the third integration variable. - -\example\index{AVECTOR package ! example} - -Suppose we wish to calculate the volume of a right circular cone. This -is equivalent to integrating unity over a conical region with the -bounds: - -\begin{tabular}{l l} -z = 0 to H & (H = the height of the cone) \\ -r = 0 to pZ & (p = ratio of base diameter to height) \\ -phi = 0 to 2*PI & \\ -\end{tabular} - -We evaluate the volume by integrating a series of infinitesimally thin -circular disks of constant z-value. The integration is thus performed -in the order : d($\phi$) from 0 to $2\pi$, dr from 0 to p*Z, dz from 0 to H. -The order of the indices is thus 2, 0, 1. - -\begin{verbatim} - VOLINTORDER := AVEC(2,0,1); - VLB := AVEC(0,0,0); - VUB := AVEC(P*Z,H,2*PI); - VOLINTEGRAL(1,VLB,VUB); -\end{verbatim} - -(At this stage, we replace {\tt P*H} by {\tt RR}, the base radius of the cone, -to obtain the result in its more familiar form.) - - -\index{LINEINT function} \index{DEFLINEINT function} -\index{integration ! line} \index{line integrals} -Line integrals may be calculated using the {\tt LINEINT} and {\tt DEFLINEINT} -functions. Their general syntax is - -\noindent {\tt LINEINT}({\tt vector-function}, {\tt vector-curve}, -{\tt variable}); - -\noindent{\tt DEFLINENINT}({\tt vector-function}, {\tt vector-curve}, -{\tt variable}, {\tt lower-bound}, {\tt upper-bound}); - -\noindent where -\begin{description} -\item[{\tt vector-function}] is any vector-valued expression; -\item[{\tt vector-curve}] is a vector expression which describes the path of -integration in terms of the independent variable; -\item[{\tt variable}] is the independent variable; -\item[{\tt lower-bound}] -\item[{\tt upper-bound}] are the bounds of integration in terms of the -independent variable. -\end{description} - -\example\index{AVECTOR package ! example} - -In spherical polar coordinates, we may integrate round a line of -constant theta (`latitude') to find the length of such a line. The -vector function is thus the tangent to the `line of latitude', (0,0,1) -and the path is {\tt (0,LAT,PHI)} where {\tt PHI} is the independent -variable. We show how to obtain the definite integral {\em i.e.} from -$\phi=0$ to $2 \pi$ : -\begin{verbatim} -DEFLINEINT(AVEC(0,0,1),AVEC(0,LAT,PHI),PHI,0,2*PI); -\end{verbatim} - -\section{Defining new functions and procedures} - -Most of the procedures in this package are defined in symbolic mode -and are invoked by the REDUCE expression-evaluator when a vector -expression is encountered. It is not generally possible to define -procedures which accept or return vector values in algebraic mode. -This is a consequence of the way in which the REDUCE interpreter -operates and it affects other non-scalar data types as well : arrays -cannot be passed as algebraic procedure arguments, for example. - -\section{Acknowledgements} - -This package was written whilst the author was the U.K. Computer -Algebra Support Officer at the University of Liverpool Computer Laboratory. -\end{document} +\documentstyle[11pt,reduce]{article} +\date{} +\title{A Vector Algebra and Calculus Package for REDUCE} +\author{David Harper \\ +Astronomy Unit \\ +Queen Mary and Westfield College \\ +University of London \\ +Mile End Road \\ +London E1 4NS \\ +England \\[0.05in] +Electronic mail: {\it adh@star.qmw.ac.uk}} +\begin{document} +\maketitle + +\index{AVECTOR package} + +\section{Introduction} + +This package \footnote{Reference: Computer Physics Communications, +{\bf 54}, 295-305 (1989)} +is written in RLISP (the LISP meta-language) and is +intended for use with REDUCE 3.4. \index{vector algebra} It provides +REDUCE with the ability to perform vector algebra using the same +notation as scalar algebra. The basic algebraic operations are +supported, as are differentiation and integration of vectors with +respect to scalar variables, cross product and dot product, component +manipulation and application of scalar functions ({\em e.g.} cosine) +to a vector to yield a vector result. + +A set of vector calculus operators are provided for use with any +orthogonal curvilinear coordinate system. These operators are +gradient, divergence, curl and del-squared (Laplacian). The Laplacian +operator can take scalar or vector arguments. + +Several important coordinate systems are pre-defined and can be +invoked by name. It is also possible to create new coordinate systems +by specifying the names of the coordinates and the values of the scale +factors. + +\section{Vector declaration and initialisation} + +Any name may be declared to be a vector, provided that it has +not previously been declared as a matrix or an array. To +declare a list of names to be vectors use the VEC command: +\index{VEC command} +\begin{verbatim} + VEC A,B,C; +\end{verbatim} +declares the variables {\tt A}, {\tt B} and {\tt C} to be vectors. +If they have already been assigned (scalar) values, these will be lost. + +When a vector is declared using the {\tt VEC} command, it does not +have an initial value. + +If a vector value is assigned to a scalar variable, then that +variable will automatically be declared as a vector and the +user will be notified that this has happened. + +\index{AVEC function} +A vector may be initialised using the {\tt AVEC} function which +takes three scalar arguments and returns a vector made up +from those scalars. For example +\begin{verbatim} + A := AVEC(A1, A2, A3); +\end{verbatim} +sets the components of the vector {\tt A} to {\tt A1}, {\tt A2} and {\tt A3}. + +\section{Vector algebra} + +(In the examples which follow, {\tt V}, {\tt V1}, {\tt V2} {\em etc} +are assumed to be vectors while {\tt S}, {\tt S1}, {\tt S2} etc are scalars.) + +\index{+ ! vector} \index{- ! vector} \index{* ! vector} \index{/ ! vector} +The scalar algebra operators +,-,* and / may be used with +vector operands according to the rules of vector algebra. +Thus multiplication and division of a vector by a scalar +are both allowed, but it is an error to multiply or +divide one vector by another. + +\begin{tabular}{l l} +{\tt V := V1 + V2 - V3;} & Addition and subtraction \\ +{\tt V := S1*3*V1;} & Scalar multiplication \\ +{\tt V := V1/S;} & Scalar division \\ +{\tt V := -V1;} & Negation \\ +\end{tabular} + +\index{DOT ! vector} \index{Dot product} \index{CROSS ! vector} +\index{cross product} +\noindent Vector multiplication is carried out using the infix +operators {\tt DOT} and {\tt CROSS}. These are defined to have +higher precedence than scalar multiplication and +division. + +\begin{tabular}{l l} +{\tt V := V1 CROSS V2;} & Cross product \\ +{\tt S := V1 DOT V2;} & Dot product \\ +{\tt V := V1 CROSS V2 + V3;} & \\ +{\tt V := (V1 CROSS V2) + V3;} & \\ +\end{tabular} + +The last two expressions are equivalent due to the precedence of +the {\tt CROSS} operator. + +\index{VMOD operator} +The modulus of a vector may be calculated using the {\tt VMOD} operator. + +\begin{verbatim} + S := VMOD V; +\end{verbatim} + +A unit vector may be generated from any vector using the {\tt VMOD} +operator. + +\begin{verbatim} + V1 := V/(VMOD V); +\end{verbatim} + +Components may be extracted from any vector using index notation +in the same way as an array. + +\begin{tabular}{l l} +{\tt V := AVEC(AX, AY, AZ);} & \\ +{\tt V(0);} & yields AX \\ +{\tt V(1);} & yields AY \\ +{\tt V(2);} & yields AZ \\ +\end{tabular} + +It is also possible to set values of individual components. Following +from above: + +\begin{verbatim} + V(1) := B; +\end{verbatim} + +The vector {\tt V} now has components {\tt AX}, {\tt B}, {\tt AZ}. + +\index{vector ! differentiation} \index{vector ! integration} +\index{differentiation ! vector} \index{differentiation ! vector} +Vectors may be used as arguments in the differentiation and +integration routines in place of the dependent expression. + +\begin{tabular}{l l} +{\tt V := AVEC(X**2, SIN(X), Y);} & \\ +{\tt DF(V,X);} & yields (2*X, COS(X), 0) \\ +{\tt INT(V,X);} & yields (X**3/3, -COS(X), Y*X) \\ +\end{tabular} + +Vectors may be given as arguments to monomial functions such as {\tt +SIN}, {\tt LOG} and {\tt TAN}. The result is a vector obtained by +applying the function component-wise to the argument vector. + +\begin{tabular}{l l} +{\tt V := AVEC(A1, A2, A3);} & \\ +{\tt SIN(V);} & yields (SIN(A1), SIN(A2), SIN(A3)) \\ +\end{tabular} + +\section{ Vector calculus} + +\index{DIV ! operator} \index{divergence ! vector field} +\index{GRAD ! operator} \index{gradient ! vector field} +\index{CURL ! operator} \index{curl ! vector field} +\index{DELSQ ! operator} \index{Laplacian ! vector field} +The vector calculus operators div, grad and curl are recognised. +The Laplacian operator is also available and may be applied to +scalar and vector arguments. + +\begin{tabular}{l l} +{\tt V := GRAD S;} & Gradient of a scalar field \\ +{\tt S := DIV V;} & Divergence of a vector field \\ +{\tt V := CURL V1;} & Curl of a vector field \\ +{\tt S := DELSQ S1;} & Laplacian of a scalar field \\ +{\tt V := DELSQ V1;} & Laplacian of a vector field \\ +\end{tabular} + +These operators may be used in any orthogonal curvilinear coordinate +system. The user may alter the names of the coordinates and the values +of the scale factors. Initially the coordinates are {\tt X}, {\tt Y} +and {\tt Z} and the scale factors are all unity. + +\index{COORDS vector} \index{HFACTORS scale factors} +There are two special vectors : {\tt COORDS} contains the names +of the coordinates in the current system and {\tt HFACTORS} +contains the values of the scale factors. + +\index{COORDINATES operator} +The coordinate names may be changed using the {\tt COORDINATES} +operator. + +\begin{verbatim} + COORDINATES R,THETA,PHI; +\end{verbatim} + +This command changes the coordinate names to {\tt R}, {\tt THETA} and +{\tt PHI}. + +\index{SCALEFACTORS operator} +The scale factors may be altered using the {\tt SCALEFACTORS} operator. + +\begin{verbatim} + SCALEFACTORS(1,R,R*SIN(THETA)); +\end{verbatim} + +This command changes the scale factors to {\tt 1}, {\tt R} and {\tt R +SIN(THETA)}. + +Note that the arguments of {\tt SCALEFACTORS} must be enclosed in +parentheses. This is not necessary with {\tt COORDINATES}. + + +When vector differential operators are applied to an expression, +the current set of coordinates are used as the independent +variables and the scale factors are employed in the calculation. +(See, for example, Batchelor G.K. 'An Introduction to Fluid +Mechanics', Appendix 2.) + + +\index{"!*CSYSTEMS global (AVECTOR)} +Several coordinate systems are pre-defined and may be invoked by +name. To see a list of valid names enter + +\begin{verbatim} + SYMBOLIC !*CSYSTEMS; +\end{verbatim} + +and REDUCE will respond with something like + +\begin{verbatim} + (CARTESIAN SPHERICAL CYLINDRICAL) +\end{verbatim} + +\index{GETCSYSTEM command} +To choose a coordinate system by name, use the command {\tt GETCSYSTEM}. + +To choose the Cartesian coordinate system : +\begin{verbatim} + GETCSYSTEM 'CARTESIAN; +\end{verbatim} +\index{PUTCSYSTEM command} + +Note the quote which prefixes the name of the coordinate system. This +is required because {\tt GETCSYSTEM} (and its complement {\tt +PUTCSYSTEM}) is a {\tt SYMBOLIC} procedure which requires a literal +argument. + +REDUCE responds by typing a list of the coordinate names in that +coordinate system. The example above would produce the response + +\begin{verbatim} + (X Y Z) +\end{verbatim} + +whilst + +\begin{verbatim} + GETCSYSTEM 'SPHERICAL; +\end{verbatim} + +would produce + +\begin{verbatim} + (R THETA PHI) +\end{verbatim} + +Note that any attempt to invoke a coordinate system is subject to the +same restrictions as the implied calls to {\tt COORDINATES} and {\tt +SCALEFACTORS}. In particular, {\tt GETCSYSTEM} fails if any of the +coordinate names has been assigned a value and the previous coordinate +system remains in effect. + +A user-defined coordinate system can be assigned a name using the +command {\tt PUTCSYSTEM}. It may then be re-invoked at a later stage using +{\tt GETCSYSTEM}. + +\example\index{AVECTOR package ! example} + +We define a general coordinate system with coordinate names {\tt +X},{\tt Y},{\tt Z} and scale factors {\tt H1},{\tt H2},{\tt H3} : + +\begin{verbatim} + COORDINATES X,Y,Z; + SCALEFACTORS(H1,H2,H3); + PUTCSYSTEM 'GENERAL; +\end{verbatim} + +This system may later be invoked by entering + +\begin{verbatim} + GETCSYSTEM 'GENERAL; +\end{verbatim} + +\section{Volume and Line Integration} + +Several functions are provided to perform volume and line integrals. +These operate in any orthogonal curvilinear coordinate system and +make use of the scale factors described in the previous section. + + +Definite integrals of scalar and vector expressions may be calculated +using the {\tt DEFINT} function. + +\example\index{AVECTOR package ! example} + +\index{DEFINT function} \index{integration ! definite (simple)} +\index{definite integration (simple)} +\noindent To calculate the definite integral of $\sin(x)^2$ between 0 and +2$\pi$ we enter + +\begin{verbatim} + DEFINT(SIN(X)**2,X,0,2*PI); +\end{verbatim} + +This function is a simple extension of the {\tt INT} function taking +two extra arguments, the lower and upper bounds of integration +respectively. + +\index{VOLINTEGRAL function} \index{integration ! volume} +Definite volume integrals may be calculated using the {\tt +VOLINTEGRAL} function whose syntax is as follows : + +\noindent {\tt VOLINTEGRAL}({\tt integrand}, vector {\tt lower-bound}, +vector {\tt upper-bound}); + +\example\index{AVECTOR package ! example} + +\noindent In spherical polar coordinates we may calculate the volume of a +sphere by integrating unity over the range $r$=0 to {\tt RR}, $\theta$=0 to +{\tt PI}, $\phi$=0 to 2*$\pi$ as follows : + +\begin{tabular}{l l} +{\tt VLB := AVEC(0,0,0);} & Lower bound \\ +{\tt VUB := AVEC(RR,PI,2*PI);} & Upper bound in $r, \theta, \phi$ + respectively \\ +{\tt VOLINTORDER := (0,1,2);} & The order of integration \\ +{\tt VOLINTEGRAL(1,VLB,VUB);} & \\ +\end{tabular} + +\index{VOLINTORDER vector} +Note the use of the special vector {\tt VOLINTORDER} which controls +the order in which the integrations are carried out. This vector +should be set to contain the number 0, 1 and 2 in the required order. +The first component of {\tt VOLINTORDER} contains the index of the +first integration variable, the second component is the index of the +second integration variable and the third component is the index of +the third integration variable. + +\example\index{AVECTOR package ! example} + +Suppose we wish to calculate the volume of a right circular cone. This +is equivalent to integrating unity over a conical region with the +bounds: + +\begin{tabular}{l l} +z = 0 to H & (H = the height of the cone) \\ +r = 0 to pZ & (p = ratio of base diameter to height) \\ +phi = 0 to 2*PI & \\ +\end{tabular} + +We evaluate the volume by integrating a series of infinitesimally thin +circular disks of constant z-value. The integration is thus performed +in the order : d($\phi$) from 0 to $2\pi$, dr from 0 to p*Z, dz from 0 to H. +The order of the indices is thus 2, 0, 1. + +\begin{verbatim} + VOLINTORDER := AVEC(2,0,1); + VLB := AVEC(0,0,0); + VUB := AVEC(P*Z,H,2*PI); + VOLINTEGRAL(1,VLB,VUB); +\end{verbatim} + +(At this stage, we replace {\tt P*H} by {\tt RR}, the base radius of the cone, +to obtain the result in its more familiar form.) + + +\index{LINEINT function} \index{DEFLINEINT function} +\index{integration ! line} \index{line integrals} +Line integrals may be calculated using the {\tt LINEINT} and {\tt DEFLINEINT} +functions. Their general syntax is + +\noindent {\tt LINEINT}({\tt vector-function}, {\tt vector-curve}, +{\tt variable}); + +\noindent{\tt DEFLINENINT}({\tt vector-function}, {\tt vector-curve}, +{\tt variable}, {\tt lower-bound}, {\tt upper-bound}); + +\noindent where +\begin{description} +\item[{\tt vector-function}] is any vector-valued expression; +\item[{\tt vector-curve}] is a vector expression which describes the path of +integration in terms of the independent variable; +\item[{\tt variable}] is the independent variable; +\item[{\tt lower-bound}] +\item[{\tt upper-bound}] are the bounds of integration in terms of the +independent variable. +\end{description} + +\example\index{AVECTOR package ! example} + +In spherical polar coordinates, we may integrate round a line of +constant theta (`latitude') to find the length of such a line. The +vector function is thus the tangent to the `line of latitude', (0,0,1) +and the path is {\tt (0,LAT,PHI)} where {\tt PHI} is the independent +variable. We show how to obtain the definite integral {\em i.e.} from +$\phi=0$ to $2 \pi$ : +\begin{verbatim} +DEFLINEINT(AVEC(0,0,1),AVEC(0,LAT,PHI),PHI,0,2*PI); +\end{verbatim} + +\section{Defining new functions and procedures} + +Most of the procedures in this package are defined in symbolic mode +and are invoked by the REDUCE expression-evaluator when a vector +expression is encountered. It is not generally possible to define +procedures which accept or return vector values in algebraic mode. +This is a consequence of the way in which the REDUCE interpreter +operates and it affects other non-scalar data types as well : arrays +cannot be passed as algebraic procedure arguments, for example. + +\section{Acknowledgements} + +This package was written whilst the author was the U.K. Computer +Algebra Support Officer at the University of Liverpool Computer Laboratory. +\end{document} Index: r36/doc/BIBL.BIB ================================================================== --- r36/doc/BIBL.BIB +++ r36/doc/BIBL.BIB @@ -1,7273 +1,7273 @@ -% REDUCE BIBLIOGRAPHY - -% Part 1: A-E - -% Copyright (c) 1995 RAND. All Rights Reserved. - -% Additions and corrections are solicited. Please send them, in the -% same format as these entries if possible, to reduce at rand.org. - - -@ARTICLE{Abbott:85, - AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", - TITLE = "A Remark on Factorisation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "31-33", MONTH = "May"} - -@INPROCEEDINGS{Abbott:86, - AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", - TITLE = "The {Bath} Algebraic Number Package", - BOOKTITLE = "Proc. of {SYMSAC} '86", - YEAR = 1986, PAGES = "250-253"} - -@INPROCEEDINGS{Abbott:87, - AUTHOR = "J. A. Abbott and J. H. Davenport", - TITLE = "Polynomial Factorization: An Exploration of {Lenstra's} -Algorithm", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes in Computer Science", - YEAR = 1987, VOLUME = 378, PAGES = "391-402", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Abbott:87a, - AUTHOR = "J. A. Abbott", - TITLE = "Integration: Solving the {Risch} Differential Equation", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "465-467", - PUBLISHER = "Springer-Verlag"} - -@PHDTHESIS{Abbott:88, - AUTHOR = "J. A. Abbott", - TITLE = "Factorisation of Polynomials over Algebraic Number Fields", - SCHOOL = "Univ. of Bath, England", - YEAR = 1988} - -@ARTICLE{Abbott:88a, - AUTHOR = "J. A. Abbott and J. H. Davenport", - TITLE = "A Remark on a Paper by {Wang}: Another Surprising Property of 42", - JOURNAL = "Math. Comp.", - YEAR = 1988, VOLUME = 51, PAGES = "837-839"} - -@INPROCEEDINGS{Abbott:89, - AUTHOR = "J. A. Abbott", - TITLE = "Recovery of Algebraic Numbers from their p-Adic Approximations", - BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", - YEAR = 1989, PAGES = "112-120"} - -@TECHREPORT{Abbott:89a, - AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", - TITLE = "A Remark on the Multiplication of Sparse Polynomials", - NUMBER = "TR 89-21", YEAR = 1989, - INSTITUTION = "School of Mathematical Sciences, University of Bath"} - -@INPROCEEDINGS{Abdali:88, - AUTHOR = "S. K. Abdali and D. S. Wise", - TITLE = "Experiments with Quadtree Representation of Matrices", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "96-108"} - -@ARTICLE{Abiezzi:83, - AUTHOR = "Salim S. {Abi-Ezzi}", - TITLE = "Clarification to the Symbolic Mode in {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = "3 and 4", PAGES = "43-47", - MONTH = "August and November"} - -@INPROCEEDINGS{Abramov:91, - AUTHOR = "S. A. Abramov and K. Yu. Kvansenko", - TITLE = "Fast Algorithms to Search for the Rational Solutions of Linear -Differential Equations with Polynomial Coefficients", - EDITOR = "Stephen M. Watt", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, - PAGES = "267-270"} - -@TECHREPORT{Abramov:91a, - AUTHOR = "S. A. Abramov and K. Yu. Kvashenko", - TITLE = "Fast search of a certain type solutions of linear ordinary -differential equations with polynomial coefficients", - INSTITUTION = "Computer Center of the USSR, Academy of Science, Moscow", - YEAR = 1991} - -@InProceedings{Adamchik90, - author = "V. S. Adamchik and O. I. Marichev", - title = "The Algorithm for calculating Integrals of - Hypergeometric type functions and its realization in - {REDUCE} System", - booktitle = "Proceedings of the 1990 International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "212-224", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Adams:83, - AUTHOR = "K. J. Adams", - TITLE = "Analytic Estimates for the Dynamic Aperture of Nonlinear Lattices", - JOURNAL = "IEEE Trans. Nucl. Sci.", - YEAR = 1983, VOLUME = "NS-30", PAGES = "2436-2438", - COMMENT = {"For an accelerator lattice{\ldots}" {REDUCE} was used to obtain low -order coefficients in the calculation of the amplitude.}} - -@ARTICLE{Adkins:83, - AUTHOR = "G. S. Adkins", - TITLE = "Analytic Evaluation of an {O}($\alpha$) Vertex Correction to the -Rate of Orthopositronium", - JOURNAL = "Phys. Rev. A", - YEAR = 1983, VOLUME = 27, PAGES = "530-532", - ABSTRACT = {The order-$\alpha$ correction to the lowest order -orthopositronium decay rate due to the two outer-vertex graphs obtained in -analytic form.}} - -@ARTICLE{Adkins:83a, - AUTHOR = "G. S. Adkins and F. R. Brown", - TITLE = "Rate for Positronium Decay to Five Photons", - JOURNAL = "Phys. Rev. A", - YEAR = 1983, VOLUME = 28, PAGES = "1164-1165", - COMMENT = {{REDUCE} used to calculate trace of $\gamma$ matrices. Large -calculation.}} - -@ARTICLE{Adkins:85, - AUTHOR = "G. S. Adkins", - TITLE = "Inner-Vertex Contributions to the Decay Rate of Orthopositronium", - JOURNAL = "Phys. Rev. A", - YEAR = 1985, VOLUME = 31, PAGES = "1250-1252", - COMMENT = {{REDUCE} trace calculations. "In this paper the order-$\alpha$ -contribution to the inner-vertex graphs to the decay rate of -orthopositronium is obtained in analytic form."}} - -@ARTICLE{Aguilera-Navarro:87, - AUTHOR = "V. C. Aguilera-Navarro and R. Guardiola and C. Keller and -M. de Llano and M. Popovic and M. Fortes", - TITLE = "Van der {Waals} Perturbation Theory for Fermion and Boson -Ground-State Matter", - JOURNAL = "Phys. Rev. A", - YEAR = 1987, VOLUME = 35, PAGES = "3901-3910", - COMMENT = {Uses computer algebra to rearrange ideal-gas-based low-density -expansions; to them {REDUCE} or {MACSYMA} provide just the expertise they -require to substitute forms into equations, and so makes their -formulation possible.}} - -@TECHREPORT{Akselrod:90, - AUTHOR = "I.R. Akselrod and V.P. Gerdt and V.E. Kovtun and V.N. Robuk", - TITLE = "Construction of a {Lie} algebra by a subset of generators and -commutation relations", - INSTITUTION = "J.I.N.R.", YEAR = 1990, TYPE = "Preprint", - NUMBER = "E5-90-508", - ABSTRACT = {The problem of constructing the quotient algebra for a free -{Lie} algebra over an ideal given by a subset of generators and commutation -relations is investigated. The method proposed to solve this problem can be -applied in particular for constructing a {L-A} pair for nonlinear evolution -equations. The algorithm is based on the concept of {Hall} basis for a -free {Lie} algebra and is implemented in the computer algebra system -{REDUCE}.}} - -@ARTICLE{Aldins:69, - AUTHOR = "J. Aldins and S. J. Brodsky and A. J. Dufner and -T. Kinoshita", - TITLE = "Photon-Photon Scattering Contribution to the Sixth -Order Magnetic Moments of the Muon and Electron", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1969, VOLUME = 23, PAGES = "441-443"} - -@TECHREPORT{Alekseev:86, - AUTHOR = "A. I. Alekseev and V. F. Edneral", - TITLE = "Tensor Structure of Axial Gauge Polarization Operator in the -Infrared Region", - INSTITUTION = "IHEP", YEAR = 1986, TYPE = "Preprint", - NUMBER = "86-46"} - -@ARTICLE{Alekseev:87, - AUTHOR = "A. I. Alekseev and V. F. Edneral", - TITLE = "Tensor Structure of Gluon Polarization Operator in the -Axial Gauge for Infra-Red Region", - JOURNAL = "Journal of Nuclear Physics", - YEAR = 1987, PAGES = "1105-1114"} - -@TECHREPORT{Alekseev:87a, - AUTHOR = "A. I. Alekseev and V. F. Edneral", - TITLE = "On Evaluation of {Feynman} Integrals in Axial Gauge", - INSTITUTION = "IHEP", YEAR = 1987, TYPE = "Preprint", - NUMBER = "87-118", - ABSTRACT = {The recurrent algorithm for axial gauge calculations of -one-loop massless {Feynman} integrals in the n-dimensional -momentum space is described. The algorithm we suggest is -realized on the basis of {REDUCE} system and presented as -a procedure. It is rather effective for cumbersome -combinations of those integrals.}} - -@ARTICLE{Alfeld:82, - AUTHOR = "P. Alfeld", - TITLE = "Fixed Point Iteration with Inexact Function Values", - JOURNAL = "Math. Comp.", - YEAR = 1982, VOLUME = 38, PAGES = "87-98", - COMMENT = {Numerical analysis generating an improved iterative scheme. -"The technical manipulations in this paper were carried out using the -symbol manipulation language {REDUCE}."}} - -@TECHREPORT{Amirkhanov:87, - AUTHOR = "I. V. Amirkhanov and E. P. Zhidkov and I. E. Zhidkova", - TITLE = "The Conditions of Bounding of the Oscillation Amplitudes of -Charge Particle within the Resonance Vicinity Investigations", - INSTITUTION = "J.I.N.R., Dubna", YEAR = 1987, NUMBER = "P11-87-452"} - -@INPROCEEDINGS{Amirkhanov:91, - AUTHOR = "I.V. Amirkhanov and E.P. Zhidkov and I.E. Zhidkova", - TITLE = "The Betatron Oscillations in the Vicinity of Nonlinear Resonance -in Cyclic Accelerator Investigation", - EDITOR = "Stephen M. Watt", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, - PAGES = "452-453"} - -@ARTICLE{Antweiler:89, - AUTHOR = "Werner Antweiler and Andreas Strotmann and Volker Winkelmann", - TITLE = "A {\TeX}-{REDUCE}-Interface", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1989, VOLUME = 23, - MONTH = "February", PAGES = "26-33"} - -@ARTICLE{Appelquist:70, - AUTHOR = "T. W. Appelquist and S. J. Brodsky", - TITLE = "The Order $\alpha^{2}$ Electrodynamic Corrections to -the {Lamb} Shift", - JOURNAL = "Phys. Rev. Letters", - YEAR = 1970, VOLUME = 24, PAGES = "562-565"} - -@TECHREPORT{Arbuzov:86, - AUTHOR = "B. A. Arbuzov and E. E. Boos and A. I. Davydychev", - TITLE = "Infrared Asymptotics of Gluonic {Green} Functions -in Covariant Gauge", - INSTITUTION = "IHEP", YEAR = 1986, TYPE = "Preprint", - NUMBER = "86-123"} - -@TECHREPORT{Kendall:93, - AUTHOR = "Gerard Ben Arous and Michael Cranston and Wilfrid S. Kendall", - TITLE = "Coupling constructions for hypoelliptic diffusions: Two -examples", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1993, - MONTH = "October", TYPE = "Research Report", NUMBER = 261, - ABSTRACT = {Coupling constructions are given for two examples of -hypoelliptic diffusions with smooth coefficients: the two-dimensional -diffusion formed by scalar Brownian motion and its time integral; and the -three-dimensional diffusion formed by planar Brownian motion and its -stochastic area. In both cases it is shown that one can construct -co-adapted copies of Brownian motion such that the corresponding copies of -the diffusion will couple in finite time. The first case uses stopping -time arguments; the second is computationally more involved and the -solution was found using a computer algebra implementation of stochastic -calculus (though the final proof has been checked completely by hand). -Questions are formulated about coupling problems for more general -hypoelliptic diffusions with smooth coefficients.}} - -@ARTICLE{Aso:81, - AUTHOR = "T. Aso and T. Nonoyama and S. Kato", - TITLE = "Numerical Simulation of Semidiurnal Atmospheric Tides", - JOURNAL = "J. Geophysical R.", - YEAR = 1981, VOLUME = 86, NUMBER = 11, PAGES = "388-400", - COMMENT = {"Numerical modeling of the solar and lunar semidiurnal -atmospheric tides has been performed by invoking a comprehensive approach that -includes both algebraic manipulation and numerical solution of the -primitive equation system." Used {REDUCE} to overcome difficulties of -complication and error.}} - -@ARTICLE{Atherton:73, - AUTHOR = "R. W. Atherton and G. M. Homsey", - TITLE = "Use of Symbolic Computation to Generate Evolution -Equations and Asymptotic Solutions to Elliptic Equations", - JOURNAL = "Journ. Comp. Phys.", - YEAR = 1973, VOLUME = 1, PAGES = "45-59"} - -@ARTICLE{Aurenche:84, - AUTHOR = "P. Aurenche and A. Douir and R. Baier and M. Fontannaz and -D. Schiff", - TITLE = "Photoproduction of Hadrons at Large Transverse Momentum in -Second Order {QCD}", - JOURNAL = "Phys. Lett.", - YEAR = 1984, VOLUME = "135B", PAGES = "164-168", - COMMENT = {Uses {REDUCE} and {SCHOONSCHIP} in the extension of calculations -to a higher order to keep pace with experimental results.}} - -@ARTICLE{Aurenche:84a, - AUTHOR = "P. Aurenche and A. Douir and R. Baier and M. Fontannaz and -D. Schiff", - TITLE = "Prompt Photon Production at Large $p_{\tau}$ in {GCD} Beyond the -Leading Order", - JOURNAL = "Phys. Lett.", - YEAR = 1984, VOLUME = "140B", PAGES = "87-92", - COMMENT = {Uses {REDUCE} and {SCHOONSCHIP}.}} - -@ARTICLE{Autin:89, - AUTHOR = "B. Autin and J. Bengtsson", - TITLE = "Symbolic Evaluation of Integrals Occurring in Accelerator -Orbit Theory", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 7, NUMBER = 2, PAGES = "183-187", MONTH = "February"} - -@ARTICLE{Baekler:84, - AUTHOR = "P. Baekler and F. W. Hehl", - TITLE = "A Charged {Taub-NUT} Metric with Torsion: A New Axially -Symmetric Solution of the {Poincar\'{e}} Gauge Field Theory", - JOURNAL = "Phys. Lett.", - YEAR = 1984, VOLUME = "100A", PAGES = "277-316"} - -@TECHREPORT{Baekler:84a, - AUTHOR = "Peter Baekler and Friedrich W. Hehl", - TITLE = "On the Dynamics of the Torsion of Spacetime: -Exact Solutions in a Gauge Theoretical Model of Gravity", - INSTITUTION = "Department of Physics, University of California, -Los Angeles", YEAR = 1984, - NUMBER = "UCLA/84/TEP/19", PAGE = "18", MONTH = "December"} - -@INPROCEEDINGS{Baekler:86, - AUTHOR = "P. Baekler and F. W. Hehl and E. W. Mielke", - TITLE = "Nonmetricity and Torsion: Facts and Fancies in Gauge -Approaches to Gravity", - EDITOR = "R. Ruffini", - BOOKTITLE = "Proc. 4th Marcel Grossmann Meeting on -General Relativity", PUBLISHER = "North-Holland, Amsterdam", - YEAR = 1986, PAGES = "277-316"} - -@ARTICLE{Baekler:87, - AUTHOR = "P. Baekler and R. Hecht and F. W. Hehl and T. Shirafuji", - TITLE = "Mass and Spin of Exact Solutions of the {Poincar{\'e}} Gauge -Theory", - JOURNAL = "Prog. Theor. Phys.", - YEAR = 1987, VOLUME = 78, PAGES = "16-21"} - -@ARTICLE{Baekler:87a, - AUTHOR = "P. Baekler and M. Guerses", - TITLE = "Exact Solutions of the {Poincar{\'e}} Gauge Theory from Its -Linearized Field Equations", - JOURNAL = "Lett. Math. Phys.", - YEAR = 1987, VOLUME = 14, PAGES = "185-191"} - -@ARTICLE{Baekler:87b, - AUTHOR = "P. Baekler and E. W. Mielke and F. W. Hehl", - TITLE = "Kinky Torsion in a {Poincar{\'e}} Gauge Model of Gravity Coupled -to a Massless Scalar Field", - JOURNAL = "Nuclear Phys.", - YEAR = 1987, VOLUME = "B288", PAGES = "800-812"} - -@ARTICLE{Baekler:88, - AUTHOR = "P. Baekler and M. Seitz and V. Winkelmann", - TITLE = "Cylindrically Symmetric Solutions of Self-Consistently -Coupled {Dirac} Fields in Gauge Theories of Gravity", - JOURNAL = "Class. Quantum Grav.", - YEAR = 1988, VOLUME = 5, PAGES = "479-490"} - -@ARTICLE{Baekler:88a, - AUTHOR = "P. Baekler and M. Guerses and F. W. Hehl and J. D. McCrea", - TITLE = "The Exterior Gravitational Field of a Charged Spinning -Source in the {Poincar{\'e}} Gauge Theory: A {Kerr-Newman} Metric with -Dynamic Torsion", - JOURNAL = "Phys. Lett.", - YEAR = 1988, VOLUME = "A128", PAGES = "245-250"} - -@ARTICLE{Baekler:88b, - AUTHOR = "P. Baekler and M. Guerses and F. W. Hehl", - TITLE = "A New Method to Solve the Field Equations of {Poincar{\'e}} -Gauge Theories", - JOURNAL = "Class. Quantum Grav.", - YEAR = 1988} - -@TECHREPORT{Bahrdt:90, - AUTHOR = "J. Bahrdt and G. W{\"u}stefeld", - TITLE = "A New Tracking Routine for Particles in Undulator and -Wiggler Fields", - INSTITUTION = "Technischer Bericht", - YEAR = 1990, TYPE = "Report", NUMBER = "BESSY TB Nr. 158", - MONTH = "October", - ABSTRACT = {In this report we present an approximated solution of the -particle motion in wiggler and undulator fields by an algebraic mapping -routine. The solution is based on a series expansion up to the third -order in the two transversal angle coordinates and, as a third variable, -the bending radius of the particle orbit. The wiggler and undulator fields -are represented by an expansion as suggested by K. Halbach. - -The report consists of two parts. In the first part we solve the -equations of motion by an iteration procedure, which originally was also -the first approach. In the second part the solution is based on a Taylor -series expansion. Both approaches are equivalent.}, -ABSTRACT2 = {Beside the presentation of the solution, the main topics -discussed in the two parts are the calculation speed and accuracy of the -algebraic method in comparison to integration methods along undulator -fields, as they are typically applied in lattice design codes. - -As a further result of the discussion we obtain a proper canonical mapping -routine at least as accurate but faster than typical integration routines.}} - -@ARTICLE{Baier:81, - AUTHOR = {V. N. Baier and A. G. Grozin}, - TITLE = {Inclusive quarkonium production in {$e^+ e^-$} annihilation}, - JOURNAL = {Yad. Fiz. (Sov. J. Nucl. Phys.)}, - YEAR = 1981, VOLUME = 33, NUMBER = 2, PAGES = {491-500}} - -@ARTICLE{Baier:85, - AUTHOR = {V. N. Baier and A. G. Grozin}, - TITLE = {Gluonic contributions to the exclusive amplitudes}, - JOURNAL = {Zeit. f\"ur Phys. C}, - YEAR = 1985, VOLUME = 29, PAGES = {161-165}} - -@ARTICLE{Baier:90, - AUTHOR = {V. N. Baier and A. G. Grozin}, - TITLE = {Decay {$B \to D l \bar\nu$} from {QCD} sum rules}, - JOURNAL = {Zeit. f\"ur Phys. C}, - YEAR = 1990, VOLUME = 47, PAGES = {669-675}} - -@TECHREPORT{Bajla:78, - AUTHOR = "I. Bajla and G. A. Ososkov and A. C. Hearn", - TITLE = "The Orthogonalization Program of Polynomials -in Two Variables in {REDUCE}-2 Language", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1978, TYPE = "Report", NUMBER = "P10-11944", - ABSTRACT = {The analytical algorithm for constructing orthogonal -polynomials in two variables, based on the {Gram-Schmidt} -orthogonalization method, is proposed.}} - -@INPROCEEDINGS{Balian:78, - AUTHOR = "R. Balian and G. Parisi and A. Voros", - TITLE = "Quartic Oscillator", - YEAR = 1978, MONTH = "May", - BOOKTITLE = "Proc. of the Colloq. on Mathematical Problems in {Feynman} -Path Integrals, Marseille", - ABSTRACT = {On the example of the semi-classical expansion for the levels -of the quartic oscillator -(d**2/dq**2)+q**4, we show how the complex WKB -method provides information about the singularities of the Borel transform -of the semi-classical series.}} - -@ARTICLE{Baker:81, - AUTHOR = "G. A. Baker and L. P. Benofy and M. Fortes and M. de Llano and -S. M. Peltier and A. Plastino", - TITLE = "Hard-Core Square-Well Fermion", - JOURNAL = "Phys. Rev. A", - YEAR = 1982, VOLUME = 26, PAGES = "3575-3588", - COMMENT = {The mixed use of {FORTRAN} and {REDUCE}, various derivative were -calculated algebraically, but the double series was evaluated numerically.}} - -@ARTICLE{Barbier:92, - AUTHOR = "Christine Barbier and Peter Bettess and Jacqueline A. Bettess", - TITLE = "Automatic Generation of Mapping Functions for Infinite Elements -using {REDUCE}", - JOURNAL = "J. Symbolic Computation", - YEAR = 1992, VOLUME = 14, NUMBER = 5, PAGES = "523-534", MONTH = "November", - ABSTRACT = {Co continuous basis functions for use in the finite element -method when the elements extend to infinity in one or more directions can be -derived simply following the method of Zienkiewicz. The numerical code -for these functions can be generated automatically using computer algebra -languages such as {REDUCE}. This paper describes the method and explains -how {REDUCE} is used to easily produce numerical code.}} - -@ARTICLE{Barfoot:86, - AUTHOR = "D. T. Barfoot and D. J. Broadhurst", - TITLE = "Investigation of a bound on the anomalous dimensions of four-quark -operators", - JOURNAL = "Phys. Lett. B", - YEAR = 1986, VOLUME = 166, PAGES = "347-350"} - -@ARTICLE{Barfoot:87, - AUTHOR = "D. T. Barfoot and D. J. Broadhurst", - TITLE = "Finite field theories in three dimensions with and without -supersymmetry", - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1987, VOLUME = 33, PAGES = "391-395"} - -@ARTICLE{Barfoot:88, - AUTHOR = "D. T. Barfoot and D. J. Broadhurst", - TITLE = {$\mbox{Z}_2\times\mbox{S}_6$ symmetry of the two-loop diagram}, - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1988, VOLUME = 41, PAGES = "81-85"} - -@ARTICLE{Bark:78, - AUTHOR = "Fritz H. Bark and Herman Tinoco", - TITLE = "Stability of Plane {Poiseuille} Flow of a Dilute -Suspension of Slender Fibres", - JOURNAL = "J. Fluid Mech.", - YEAR = 1978, VOLUME = 87, PAGES = "321-333", - ABSTRACT = {The linear hydrodynamic stability problem for plane {Poiseuille} -flow of a dilute suspension of rigid fibers is solved -numerically. The constitutive equation given by {Batchelor} -is used to model the rheological properties of the suspension. -The resulting eigenvalue problem is shown to be singular.}} - -@ARTICLE{Barthes-Biesel:73, - AUTHOR = "D. Barthes-Biesel and A. Acrivos", - TITLE = "On Computer Generated Analytic Solutions to the -Equations of Fluid Mechanics, The Case of Creeping Flows", - JOURNAL = "Journ. Comp. Phys.", - YEAR = 1973, VOLUME = 3, PAGES = "403-411"} - -@ARTICLE{Barton:72, - AUTHOR = "David Barton and Anthony C. Hearn", - TITLE = "Comment on Problem \#2 - The {Y(2n)} Functions", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1972, VOLUME = 15, - ABSTRACT = {A compact program for the solution of {SIGSAM} Problem \#2 -is presented.}} - -@ARTICLE{Bateman:86, - AUTHOR = "G. Bateman and R. G. Storer", - TITLE = "Direct Determination of Axisymmetric Magnetohydrodynamic -Equilibrium in {Hamada} Coordinates", - JOURNAL = "Journ. Comp. Phys.", - YEAR = 1986, VOLUME = 64, PAGES = "161-176", - COMMENT = {Plasma. {"REDUCE} was used to analyse the general set of -equations for large numbers of {Fourier} harmonics {\ldots}"}} - -@INPROCEEDINGS{Belkov:91, - AUTHOR = "Alexander A. Bel'Kov and Alexander V. Lanyov", - TITLE = "{REDUCE} Usage for Calculation of Low-Energy Process Amplitudes in -Chiral {QCD} Model", - EDITOR = "Stephen M. Watt", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, - PAGES = "454-455", - ABSTRACT = {We describe the extension of {REDUCE} capabilities for the -calculations of strong and weak meson processes within the chiral -Lagrangians with higher derivatives. The main non-trivial difficulty is to -obtain the process amplitude from the Lagrangian, describing these -interactions. Another one is to overcome some {REDUCE} deficiencies such -as the lack of arguments in the matrix data type as well as of some -physical operations with the particle operators. This package of procedures -allows one to claculate the amplitudes of the strong and weak processes by -simple specifying the particles involved and their momenta.}} - -@TECHREPORT{Bennett:88, - AUTHOR = "J. P. Bennett and J. H. Davenport and H. M. Sauro", - TITLE = "Solution of Some Equations in Biochemistry", - INSTITUTION = "School of Mathematical Sciences, University of -Bath, England", NUMBER = "88-12", YEAR = 1988} - -@ARTICLE{Bennett:93, - AUTHOR = "J. P. Bennett and M. Grinfeld and J. Hubble", - TITLE = "Computer Algebra Techniques in Affinity Binding Equations: -the Dimer Case", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "79-83", MONTH = "January", - COMMENT = {In this note we apply computer algebra techniques to affinity -binding equations. We treat the situation in which the protein is -dimeric and shows cooperative binding. Special attention is paid to the -case where more than one molecule of the immobilized ligand can be -bound by the macromolecule.}} - -@ARTICLE{Berends:81, - AUTHOR = "A. Berends and R. Kleiss and P. de Causmaecher and T. T. Wu", - TITLE = "Single Bremsstrahlung Process in Gauge Theories", - JOURNAL = "Phys. Lett.", - YEAR = 1981, VOLUME = "103B", PAGES = "124-128", - COMMENT = {Used {REDUCE} to calculate 25 {Feynman} diagrams to produce -theoretical results which could be checked against experiment.}} - -@TECHREPORT{Berkovich:89, - AUTHOR = "L.M. Berkovich and V.P. Gerdt and Z.T. Kostova and -M.L. Nechaevsky", - TITLE = "Second Order Reducible Linear Differential Equations", - INSTITUTION = "J.I.N.R., Dubna", YEAR = 1989, TYPE = "Preprint", - NUMBER = "E5-89-141"} - -@TECHREPORT{Berkovich:90, - AUTHOR = "L.M. Berkovich and V.P. Gerdt and Z.T. Kostova and -M.L. Nechaevsky", - TITLE = "Computer algebra generating related {2nd} order linear differential -equation", - INSTITUTION = "J.I.N.R., Dubna", YEAR = 1990, TYPE = "Preprint", - NUMBER = "E5-90-509", - ABSTRACT = {An algorithm with its mathematical foundation concerning {2nd} -order ordinary linear differential equations {(OLDE)} is described. It -allows one to generate related {four-parametric} families of {OLDE} with -coefficients of preassigned (in the scope of the procedure) structures -integrable in terms of a given (generating) equation. The number of those -families in each next generation grows according to geometric progression -with ratio eight. Several examples of both mathematical and physical -significance illustrate the efficiency of the algorithm implemented in the -{REDUCE} compute algebra system.}} - -@ARTICLE{Berman:63, - AUTHOR = "S. M. Berman and Y. S. Tsai", - TITLE = "Intermediate Boson Pair Production as a Means for -Determining its Magnetic Moment", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1963, VOLUME = 11, PAGES = "483-487"} - -@INPROCEEDINGS{Berndt:91, - AUTHOR = "R. Berndt and A. Lock and G. Witte and Ch. W{\"o}ll", - TITLE = "Application of Computer Algebra to Surface Lattice Dynamics", - EDITOR = "Stephen M. Watt", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, - PAGES = "433-438", - ABSTRACT = {Lattice dynamical calculations for surfaces and in particular -for stepped and adsorbed covered surfaces are commonly hampered by the -complexity of the dynamical matrix for these systems. We propose the use -of computer algebra programs to set up the dynamical matrix. In the -present implementation the dynamical matrix is calculated fully analytically -within the framework of a force constant-model and partially analytically -for other interaction models such as the shell model or the bond charge -model.}} - -@ARTICLE{Bessis:85, - AUTHOR = "N. Bessis and G. Bessis and D. Roux", - TITLE = "Closed-Form Expressions for the {Dirac-Coulomb} Radial $r^{t}$ -Integrals", - JOURNAL = "Phys. Rev. A", - YEAR = 1985, VOLUME = 32, PAGES = "2044-2050", - COMMENT = {No direct algebraic manipluation, but the formula is stated to be -well suited to evaluation by {REDUCE} or {MACSYMA}, and this is an -advantage of their formula.}} - -@ARTICLE{Bilge:92, - AUTHOR = "Ay{\c{s}}e H{\"{u}}meyra Bilge", - TITLE = "A {REDUCE} program for the integration of differential -polynomials", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1992, VOLUME = 71, NUMBER = 3, PAGES = "263-268", - MONTH = "September", - COMMENT = {A differential polynomial F[u] is a polynomial expression of the -derivatives of the function u(x). A {REDUCE} program for the integration -of differential polynomials is given. The program is tested on the -computation of the conserved densities of polynomial evolution equations. -Input and output from the test runs are included in the library files.}} - -@TECHREPORT{Billoire:78, - AUTHOR = "A. Billoire and R. Lacaze and A. Morel and H. Navelet", - TITLE = "The {OZI} Rule Violating Radiative Decays of the Heavy -Pseudoscalars", - INSTITUTION = "{CEN}-Saclay", YEAR = 1978, TYPE = "Report", - NUMBER = "DpH-T 43/78", - COMMENT = {Submitted to Phys. Letters B. -In lowest order {QCD} the rates for radiative transitions violating the {OZI} -rule of heavy pseudoscalars are found to be extremely small.}} - -@ARTICLE{Biro:86, - AUTHOR = "T. S. Biro and J. Zimanyi and M. Zimanyi", - TITLE = "Hadrochemistry in Relativistic Mean Fields", - JOURNAL = "Physics Letters", - YEAR = 1986, VOLUME = "167B", NUMBER = 3, PAGES = "271-276", - MONTH = "February"} - -@ARTICLE{Biro:87, - AUTHOR = "T. S. Biro and K. Niita and A. L. de Paoli and W. Bauer -and W. Cassing and U. Mosel", - TITLE = "Microscopic Theory of Photon Production in Proton-Nucleus -and Nucleus-Nucleus Collisions", - JOURNAL = "Nuclear Physics", - YEAR = 1987, VOLUME = "475A", PAGES = "579-597", MONTH = "December"} - -@TECHREPORT{Birrell:77, - AUTHOR = "N. D. Birrell", - TITLE = "The Application of Adiabatic Regularization -to Calculations of Cosmological Interest", - INSTITUTION = "Dept. Math, King's College, London", - YEAR = 1977} - -@ARTICLE{Biswas:75, - AUTHOR = "S. N. Biswas and S. R. Chaudhuri and K. S. Taank -and J. A. Campbell", - TITLE = "Neutrino Production in Stellar Matter by Photons -in a Renormalizable Scalar-Boson-Exchange Model of Weak -Interactions", - JOURNAL = "Phys. Rev. D", - YEAR = 1975, VOLUME = 8, PAGES = "2523-2525"} - -@TECHREPORT{Bittencourt:90, - AUTHOR = "Guilherme Bittencourt and Jacques Calmet", - TITLE = "Integrating Computer Algebra and Knowledge Representation", - INSTITUTION = "Universit{\"a}t Karlsruhe Institut f{\"u}r -Algorithmen und Kognitive Systeme", YEAR = 1990, TYPE = "Preprint"} - -@InProceedings{Blum:93, - author = "W. Blum and V. Ganzha and W. Strampp", - title = "An Introduction to ODE's by CAS", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "110-119", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - comment = {Use of {REDUCE} and MATHEMATICA for math education.} -} - -@ARTICLE{Bocko:92, - AUTHOR = "J. Bocko", - TITLE = "{EQSHELL} - a {REDUCE-based} program for generation of equations -of equilibrium for shell", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1992, VOLUME = 69, NUMBER = 1, PAGES = "215-222", MONTH = "February", - COMMENT = {EQSHELL is a REDUCE-based program which generates the equations -of equilibrium for various shapes of shells. This program also produces -other important characteristics of the shell.}} - -@ARTICLE{Boege:86, - AUTHOR = "W. Boege and R. Gebauer and H. Kredel", - TITLE = "Some Examples for Solving Systems of Algebraic Equations -by Calculating {Groebner} Bases", - JOURNAL = "J. Symbolic Computation", - YEAR = 1986, VOLUME = 2, NUMBER = 1, PAGES = "83-98", MONTH = "March"} - -@ARTICLE{Bogdanova:88, - AUTHOR = "N. Bogdanova and H. Hogreve", - TITLE = "A {REDUCE} Package for Exact {Coulomb} Interaction Matrix -Elements", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1988, VOLUME = 48, NUMBER = 2, PAGES = "319-326", MONTH = "February"} - -@ARTICLE{Bordoni:81, - AUTHOR = "Luciana Bordoni and Attilio Colagrossi", - TITLE = "An Application of {REDUCE} to Industrial Mechanics", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1981, VOLUME = 15, NUMBER = 2, PAGES = "8-12", MONTH = "May"} - -@InProceedings{Borst:94, - author = "W. N. Borst and V. V. Goldman and J. A. van Hulzen", - title = {{GENTRAN} 90: a {REDUCE} package for the generation of - {Fortran} 90 code}, - booktitle = {Symbolic and Algebraic Computation}, - editor = {}, - series = {ISSAC}, - year = {1994}, - organization = {SIGSAM}, - publisher = {ACM}, - pages = {45--51}, - ABSTRACT = {GENTRAN is a code GENerator and TRANslator running under REDUCE -and MACSYMA. It is a tool for generating Fortran 77, RATFOR or C programs -from program specifications and symbolic expressions. Its facilities -include template processing, automatic segmentation of large expressions -and a file handling mechanism. GENTRAN can be used in combination with -SCOPE 1.5, a Source Code Optimization PackagE for REDUCE. We present an -extension of the REDUCE version of GENTRAN, called GENTRAN 90. It makes -generation of Fortran 90 code possible.}} - -@INPROCEEDINGS{Bowyer:87, - AUTHOR = "A. Bowyer and J. H. Davenport and P. S. Milne and J. A. Padget -and A. F. Wallis", - TITLE = "Applications of Computer Algebra in Solid Modelling", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "244-245", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Boyd:78, - AUTHOR = "John P. Boyd", - TITLE = "The Effects of Latitudinal Shear on Equatorial -Waves, Part {I}: Theory and Methods", - INSTITUTION = "Dept. of Atmos. and Oceanic Science, Univ. -of Michigan", - YEAR = 1978, TYPE = "Preprint", MONTH = "January", - COMMENT = {To be published in Journal of The Atmospheric Sciences. -By using the method of multiple scales in height and a -variety of methods in latitude, analytic solutions for -equatorial waves in combined vertical and horizontal shear -are derived.}} - -@ARTICLE{Boyd:93, - AUTHOR = "John P. Boyd", - TITLE = "Chebyshev and {Legendre} Spectral Methods in Algebraic Manipulation -Languages", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, MONTH = "October", VOLUME = 16, NUMBER = 4, PAGES = "377-399", - COMMENT = {In this tutorial, we show how to combine Galerkin and collocation -methods with algebraic manipulation languages. Because polynomial and -trigonometric manipulations are a special strength of {REDUCE}, Maple, and -other symbolic languages, it is easy to use Chebyshev and Legendre -polynomials and Fourier series as the basis sets. However, because the -truncation is small and calculations are performed symbolically in rational -arithmetic, many of the standard precepets for numerical use of spectral -methods must be modified or reversed. We offer many guidelines and -suggestions. Six examples programmed in {REDUCE}, and -Maple---eigenproblems, bifurcations, and nonlinear diffusion--illustrate -the possibilities.}} - -@INPROCEEDINGS{Brackx:87, - AUTHOR = "F. Brackx and H. Serras", - TITLE = "Boundary Value Problems for the {Laplacian} in {Euclidean} Space -Solved by Symbolic Computation", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "208-215", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Brackx:87a, - AUTHOR = "F. Brackx and D. Constales and R. Delanghe and H. Serras", - TITLE = "{Clifford} Algebra with {REDUCE}", - JOURNAL = "Rend. Circ. Mat. Palermo, Ser. II", - YEAR = 1987, VOLUME = 16, PAGES = "11-19"} - -@ARTICLE{Brackx:89, - AUTHOR = "F. Brackx and D. Constales and A. Ronveaux and H. Serras", - TITLE = "On the Harmonic and Monogenic Decomposition of Polynomials", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 8, NUMBER = 3, PAGES = "297-304", MONTH = "September"} - -@BOOK{Brackx:92, - AUTHOR = "F. Brackx and D. Constales", - TITLE = "Computer Algebra with LISP and REDUCE", - PUBLISHER = "Kluwer Academic Publishers", - YEAR = 1992, - PREFACE = {This text is based upon a series of lectures on LISP and REDUCE - held at the Universities of Averio and Coimbra (Portugal), as part of the - European Community's ERASMUS Project, and at the University of Gent - (Belgium). It has been adapted to the newest release of REDUCE, version - 3.4}} - -@INPROCEEDINGS{Bradford:86, - AUTHOR = "R. J. Bradford and A. C. Hearn and J. A. Padget -and E. Schr{\"u}fer", - TITLE = "Enlarging the {REDUCE} Domain of Computation", - BOOKTITLE = "Proc. of {SYMSAC} '86", - YEAR = 1986, PAGES = "100-106"} - -@INPROCEEDINGS{Bradford:88, - AUTHOR = "R. J. Bradford and J. H. Davenport", - TITLE = "Effective Tests for Cyclotomic Polynomials", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "244-251"} - -@InProceedings{Bradford90, - author = "Russell Bradford", - title = "A parallelization of the {Buchberger} Algorithm", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "296", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Broadhurst:83, - AUTHOR = "D. J. Broadhurst", - TITLE = "{Non-relativistic sum rules for $\mbox{QCD}_2$, {QED} and -$\mbox{QCD}_4$}", - JOURNAL = "Phys. Lett. B", - YEAR = 1983, VOLUME = 123, PAGES = "251-254"} - -@ARTICLE{Broadhurst:84, - AUTHOR = "D. J. Broadhurst and S. C. Generalis", - TITLE = "Can mass singularities be minimally subtracted?", - JOURNAL = "Phys. Lett. B", - YEAR = 1984, VOLUME = 142, PAGES = "75-79"} - -@ARTICLE{Broadhurst:85, - AUTHOR = "D. J. Broadhurst and S. C. Generalis", - TITLE = "Dimension-8 contributions to light-quark {QCD} sum rules", - JOURNAL = "Phys. Lett. B", - YEAR = 1985, VOLUME = 165, PAGES = "175-180"} - -@ARTICLE{Broadhurst:85a, - AUTHOR = "D. J. Broadhurst", - TITLE = "Evaluation of a Class of {Feynman} Diagrams for all Numbers of -Loops and Dimensions", - JOURNAL = "Phys. Lett. B", - YEAR = 1985, VOLUME = 164, PAGES = "356-360", - COMMENT = {Uses {REDUCE} to calculate explicitly the l-loop member of a -class of massless, dimensionally regularized {Feynman} diagrams, in order to -verify an explicit formula.}} - -@ARTICLE{Broadhurst:86, - AUTHOR = "D. J. Broadhurst and A. G. Grozin", - TITLE = "Exploiting the 1,440-fold symmetry of the master two-loop diagram", - JOURNAL = "Zeitschrift {f\"{u}r} Physik c", - YEAR = 1986, VOLUME = 32, PAGES = "249-253"} - -@ARTICLE{Broadhurst:87, - AUTHOR = "D. J. Broadhurst", - TITLE = "Two-loop negative-dimensional integration", - JOURNAL = "Phys. Lett. B", - YEAR = 1987, VOLUME = 197, PAGES = "179-182"} - -@ARTICLE{Broadhurst:90, - AUTHOR = "D. J. Broadhurst", - TITLE = "The master two-loop diagram with masses", - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1990, VOLUME = 47, PAGES = "115-124"} - -@ARTICLE{Broadhurst:91, - AUTHOR = {D. J. Broadhurst and A. G. Grozin}, - TITLE = {Two-loop renormalization of the effective field theory -of a static quark}, - JOURNAL = {Phys. Lett. B}, - YEAR = 1991, VOLUME = 267, PAGES = {105-110}} - -@TECHREPORT{Broadhurst:91a, - AUTHOR = {D. J. Broadhurst and A. G. Grozin}, - TITLE = {Operator product expansion in static-quark effective theory: -large perturbative corrections}, - INSTITUTION = {Open University, Milton Keynes MK7 6AA, England}, - YEAR = 1991, NUMBER = {OUT-4102-31}} - -@ARTICLE{Broadhurst:91b, - AUTHOR = "D. J. Broadhurst and N. Gray and K. Schilcher", - TITLE = {Gauge-invariant on-shell ${Z}_2$ in {QED}, {QCD} and the effective -field theory of a static quark}, - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1991, VOLUME = 52, PAGES = "111-122"} - -@ARTICLE{Broadhurst:92, - AUTHOR = {D. J. Broadhurst and A. G. Grozin}, - TITLE = "Operator product expansion in static-quark effective field theory: -Large perturbative correction", - JOURNAL = {Phys. Lett. B}, - YEAR = 1992, VOLUME = 274, PAGES = {421- }} - -@ARTICLE{Broadhurst:92a, - AUTHOR = {D. J. Broadhurst}, - TITLE = {Three-loop on-shell charge renormalization without integration: -$\Lambda^{\overline{\rm MS}}_{\rm QED}$ to four loops}, - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1992, VOLUME = 54, PAGES = {599- }} - -@ARTICLE{Broadhurst:93, - AUTHOR = "D. J. Broadhurst", - TITLE = "Large {N} expansion of {QED}: asymptotic photon propagator and -contributions to the muon anomaly, for any number of loops", - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1993, VOLUME = 58, PAGES = {339-345}} - -@ARTICLE{Broadhurst:93a, - AUTHOR = "D. J. Broadhurst and J. Fleischer and O. V. Tarasov", - TITLE = "Two-loop two-point functions with masses: asymptotic expansions -and {Taylor} series, in any dimension", - JOURNAL = "Physics Letters", VOLUME = "B329", PAGES = {103-110}, YEAR = 1994, - ABSTRACT = {In all mass cases needed for quark and gluon self-energies, -the two-loop master diagram is expanded at large and small $q^{2}$, in -$d$ dimensions, using identities derived from integration by parts. -Expansions are given, in terms of hypergeometric series, for all gluon -diagrams and for all but one of the quark diagrams; expansions of the -latter are obtained from differential equations. Pad\'{e} approximants -to truncations of the expansions are shown to be of great utility. As an -application, we obtain the two-loop photon self-energy, for all $d$, and -achieve highly accelerated convergence of its expansions in powers of -$q^{2}/m^{2}/q^{2}$, for $d=4$.}} - -@TECHREPORT{Broadhurst:94, - AUTHOR = {D. J. Broadhurst and P. A. Baikov and J. Fleischer and V. A. -Smirnov}, - TITLE = {Two-loop gluon-condensate contributions to heavy-quark -current correlators: exact results and approximations}, - INSTITUTION = {Open University, Milton Keynes MK7 6AA, England}, - YEAR = 1994, NUMBER = {OUT-4102-49}, - ABSTRACT = {The coefficient functions of the gluon condensate $\langle -G^2\rangle$, in the correlators of heavy-quark vector, axial, scalar and -pseudoscalar currents, are obtained analytically, to two loops, for all values -of $z=q^2/4m^2$. In the limiting cases $z\to0$, $z\to1$, and $z\to-\infty$, -comparisons are made with previous partial results. Approximation methods, -based on these limiting cases, are critically assessed, with a view to -three-loop work. High accuracy is achieved using a few moments as input. -A {\em single\/} moment, combined with only the {\em leading\/} threshold and -asymptotic behaviours, gives the two-loop corrections to better than 1\% in -the next 10 moments. A two-loop fit to vector data yields -$\langle\frac{\alpha_{\rm s}}{\pi}G^2\rangle\approx0.021$~GeV$^4$}} - -@ARTICLE{Brodsky:62, - AUTHOR = "S. J. Brodsky and A. C. Hearn and R. G. Parsons", - TITLE = "Determination of the Real Part of the {Compton} Amplitude -at a Nucleon Resonance", - JOURNAL = "Phys. Rev.", - YEAR = 1962, VOLUME = 187, PAGES = "1899-1904"} - -@ARTICLE{Brodsky:67, - AUTHOR = "S. J. Brodsky and J. D. Sullivan", - TITLE = "W-Boson Contribution to the Anomalous Magnetic Moment of the -Muon", - JOURNAL = "Phys. Rev.", - YEAR = 1967, VOLUME = 156, PAGES = "1644-1647"} - -@INPROCEEDINGS{Brodsky:69, - AUTHOR = "S. J. Brodsky", - TITLE = "Status of Quantum Electrodynamics", - YEAR = 1969, - BOOKTITLE = "Proc. International Symposium on -Electron and Photon Interactions at High Energies, Liverpool, -England"} - -@TECHREPORT{Brodsky:70, - AUTHOR = "S. J. Brodsky", - TITLE = "Quantum Electrodynamic Theory: Its Relation to Precision Low -Energy Experiments", - INSTITUTION = "SLAC", - YEAR = 1970, TYPE = "Report", NUMBER = "SLAC-PUB-795", - MONTH = "August"} - -@INPROCEEDINGS{Brodsky:71, - AUTHOR = "S. J. Brodsky", - TITLE = "Algebraic Computation Techniques in Quantum Electrodynamics", - YEAR = 1971, VOLUME = "II", PAGES = "IV-1 to IV-27", - BOOKTITLE = "Proc. {2nd} Computing Methods in Theoretical Physics, -Marseilles"} - -@TECHREPORT{Brodsky:72, - AUTHOR = "S. J. Brodsky", - TITLE = "Atomic Physics and Quantum Electrodynamics in the Infinite -Momentum Frame", - INSTITUTION = "SLAC", YEAR = 1972, - TYPE = "Report", - NUMBER = "SLAC-PUB-1118", MONTH = "August", - COMMENT = {Presented at the Third International Conference on Atomic -Physics.}} - -@ARTICLE{Brodsky:72a, - AUTHOR = "S. J. Brodsky and J. F. Gunion and R. L. Jaffe", - TITLE = "Test for Fractionally Charged Partons from -Deep-Inelastic Bremsstrahlung in the Scaling Region", - JOURNAL = "Phys. Rev. D", - YEAR = 1972, VOLUME = 6, PAGES = "2487-2494"} - -@ARTICLE{Brodsky:72b, - AUTHOR = "S. J. Brodsky and R. Roskies", - TITLE = "Quantum Electrodynamics and Renormalization Theory -in The Infinite Momentum Frame", - JOURNAL = "Phys. Lett.", - YEAR = 1972, VOLUME = "41B", PAGES = "517-520"} - -@ARTICLE{Brodsky:73, - AUTHOR = "S. J. Brodsky and R. Roskies and R. Suaya", - TITLE = "Quantum Electrodynamics and Renormalization Theory in the -Infinite-Momentum Frame", - JOURNAL = "Phys. Rev. D", - YEAR = 1973, VOLUME = 8, PAGES = "4574-4594"} - -@ARTICLE{Broughan:82, - AUTHOR = "K. A. Broughan", - TITLE = "{Grad-Fokker-Planck} Plasma Equations. Part 1. {Collision} -Moments", - JOURNAL = "J. Plasma Phys.", - YEAR = 1982, VOLUME = 27, PAGES = "437-452", - COMMENT = {{REDUCE} used in collaboration with hand calculation. {REDUCE} -did the substitutions, with hand integrations. "Thirteen moments are taken -of the collision term in Boltzmann-Fokker-Planck -equation{\ldots}plasma{\ldots}"}} - -@ARTICLE{Broughan:91, - AUTHOR = "K. A. Broughan and G. Keady and T. D. Robb and M. G. Richardson -and M. C. Dewar", - TITLE = "Some Symbolic Computing Links to the {NAG} Numeric Library", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1991, VOLUME = 25, NUMBER = 3, PAGES = "28-37", MONTH = "July"} - -@ARTICLE{Brown:79, - AUTHOR = "W. S. Brown and A. C. Hearn", - TITLE = "Applications of Symbolic Algebraic Computation", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1979, VOLUME = 17, PAGES = "207-215", - COMMENT = {This paper is a survey of applications of systems for symbolic -algebraic computation.}} - -@ARTICLE{Bryan-Jones:87, - AUTHOR = "Jane Bryan-Jones", - TITLE = "A Tutorial in Computer Algebra for Statisticians", - JOURNAL = "The Professional Statistician", - YEAR = 1987, VOLUME = 6, NUMBER = 6, MONTH = "December",PAGES = "TBD"} - -@TECHREPORT{Burnel, - AUTHOR = "A. Burnel and H. Caprasse", - TITLE = "Locality in Class III Noncovariant Gauges", - INSTITUTION = "Physique Th{\'e}orique et Math{\'e}matique, -Universit{\'e} de Li{\`e}ge", - ABSTRACT = {It is shown within a perturbative calculation of the gluon -self-energy that, in the framework of a general formulation of linear gauges, -axial gauges do not exhibit nonlocal counterterms.}} - -@TECHREPORT{Burnel:94, - AUTHOR = "A. Burnel and H. Caprasse and A. Dresse", - TITLE = "Computing the {BRST} operator", - INSTITUTION = "D{\'e}partement d'Astronomie et d'Astrophysique, -Universit{\'e} de Li{\`e}ge", YEAR = 1994, - ABSTRACT = {It is shown that for a large class of non-holonomic quantum -mechanical systems one can make the computation of {BRST} charge fully -algorithmic. Two computer algebra programs written in the language of -{REDUCE} are described. They are able to realize the complex calculations -needed to determine the charge for general nonlinear algebras. Some -interesting specific solutions are discussed.}} - -@ARTICLE{Burnel:94a, - AUTHOR = "A. Burnel and H. Caprasse", - TITLE = "Computing the {BRST} Operator Used in Quantization of Gauge -Theories", - JOURNAL = "International Journal of Modern Physics C", - YEAR = 1994, VOLUME = 5, NUMBER = 6, PAGES = "1035-1047", - COMMENTS = {It is shown that for a large class of non-holonomic quantum -mechanical systems one can make the computation of BRST charge fully -algorithmic. Two computer algebra programs written in the language of REDUCE -are described. They are able to realize the complex calculations needed -to determine the charge for general nonlinear algebras. Some interesting -specific solutions are discussed.}} - -@TECHREPORT{Calmet:72, - AUTHOR = "Jacques Calmet", - TITLE = "Further Evaluation of the Sixth Order Corrections to the -Anomalous Magnetic Moment of the Electron", - INSTITUTION = "Department of Physics, University of Utah", - YEAR = 1972, - ABSTRACT = {We report on the contributions to the $\alpha^{3}$ -part of the anomalous magnetic moment of the electron from the -seven so-called cross and ladder diagrams.}} - -@ARTICLE{Calmet:72a, - AUTHOR = "Jacques Calmet", - TITLE = "A {REDUCE} Approach to the Calculation of {Feynman} Diagrams", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1972, VOLUME = 4, PAGES = "199-204", - ABSTRACT = {A brief survey of two existing {REDUCE} programs (by -Campbell-Hearn and by Calmet) dealing with algebraic computation of -{Feynman} diagrams is given. Work in progress on a more general approach -to this problem is discussed.}} - -@ARTICLE{Calmet:74, - AUTHOR = "Jacques Calmet", - TITLE = "Computer Recognition of Divergences in {Feynman} Graphs", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1974, VOLUME = 8, NUMBER = 3, PAGES = "74-75", MONTH = "August", - ABSTRACT = {A description of a program for the recognition of divergences -in {Feynman} graphs is given.}} - -@INCOLLECTION{Calmet:83, - AUTHOR = "J. Calmet and J. A. van Hulzen", - TITLE = "Computer Algebra Applications", - EDITOR = "B. Buchberger and G. E. Collins and R. Loos and R. Albrecht", - BOOKTITLE = "Computer Algebra Symbolic and Algebraic Computation", - EDITION = "2nd", PUBLISHER = "Springer-Verlag", YEAR = 1983} - -@ARTICLE{Campbell:67, - AUTHOR = "J. A. Campbell", - TITLE = "Algebraic Computation of Radiative Corrections for -Electron-Positron Scattering", - JOURNAL = "Nucl. Phys.", - YEAR = 1967, VOLUME = "B1", PAGES = "283-300"} - -@ARTICLE{Campbell:68, - AUTHOR = "J. A. Campbell", - TITLE = "Astrophysical Consequences of the Existence of Charged -Intermediate Vector Bosons", - JOURNAL = "Aust. Journ. of Phys.", - YEAR = 1968, VOLUME = 21, PAGES = "139-148"} - -@ARTICLE{Campbell:70, - AUTHOR = "J. A. Campbell and A. C. Hearn", - TITLE = "Symbolic Analysis of {Feynman} Diagrams by Computer", - JOURNAL = "Journ. of Comp. Phys.", - YEAR = 1970, VOLUME = 5, PAGES = "280-327"} - -@ARTICLE{Campbell:70a, - AUTHOR = "J. A. Campbell and R. B. Clark and D. Horn", - TITLE = "Low-T Theorems for Charged-Pion Photoproduction", - JOURNAL = "Phys. Rev. D", - YEAR = 1970, VOLUME = 2, PAGES = "217-224"} - -@ARTICLE{Campbell:74, - AUTHOR = "J. A. Campbell", - TITLE = "Symbolic Computing and Its Relationship to Particle Physics", - JOURNAL = "Acta Physica Austriaca", - YEAR = 1974, VOLUME = "Suppl. XIII", PAGES = "595-647"} - -@ARTICLE{Campbell:87, - AUTHOR = "J. A. Campbell and P. O. Fr{\"o}man and E. Walles", - TITLE = "Explicit series formulae for the evaluation of integrals by the -method of steepest descents", - JOURNAL = "Studies in Applied Mathematics", - YEAR = 1987, VOLUME = 77, PAGES = "151-172"} - -@TECHREPORT{Caprasse:84, - AUTHOR = "H. Caprasse", - TITLE = "Description et Utilisation d'Une Extension du Programme {REDUCE}", - INSTITUTION = "Physique Th{\'e}orique et Math{\'e}matique, -Universit{\'e} de Li{\`e}ge", YEAR = 1984, MONTH = "October"} - -@ARTICLE{Caprasse:85, - AUTHOR = "H. Caprasse and M. Hans", - TITLE = "A New Use of Operators in the Algebraic Mode of {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "46-52", MONTH = "August"} - -@ARTICLE{Caprasse:86, - AUTHOR = "H. Caprasse", - TITLE = "Description of an Extension of the Matrix Package of {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1986, VOLUME = 20, NUMBER = 4, PAGES = "7-10", MONTH = "December"} - -@ARTICLE{Caprasse:86a, - AUTHOR = "H. Caprasse", - TITLE = "A Complete Simplification Package for the Absolute Value -Function in {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "18-21", - MONTH = "February and May", - COMMENT = {Implementation for {REDUCE} 3.2 of the function {"ABS"}.}} - -@INPROCEEDINGS{Caprasse:88, - AUTHOR = "H. Caprasse and J. Demaret and E. Schruefer", - TITLE = "Can {EXCALC} be Used to Investigate {High-dimensional} -Cosmological Models with {Non-Linear Lagrangians}?", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, PAGES = "116-124"} - -@ARTICLE{Caprasse:89a, - AUTHOR = "H. Caprasse", - TITLE = "Les Th{\'e}ories des {Champs} dans le monde de {REDUCE} -(in {French})", - JOURNAL = "{CALSYF} (to appear)", - YEAR = 1989} - -@ARTICLE{Caprasse:90, - AUTHOR = "H. Caprasse", - TITLE = "Renormalization Group, Function Iterations and Computer -Algebra", - JOURNAL = "J. Symbolic Computation", - YEAR = 1990, VOLUME = 9, NUMBER = 1, PAGES = "61-72", MONTH = "January", - COMMENT = {Based on a renormalization group equation met in Quantum Field -Theory, Continuous Iterations of a large class of functions are computed -using {REDUCE}.}} - -@ARTICLE{Caprasse:91, - AUTHOR = "H. Caprasse and J. Demaret and K. Gatermann and H. Melenk", - TITLE = "Power-law type solutions of fourth-order gravity for -multidimensional {Bianchi I} Universes", - JOURNAL = "International Journal of Modern Physics C", - YEAR = 1991, VOLUME = 2, NUMBER = 2, PAGES = "601-611", - COMMENT = {This paper is devoted to the application of computer algebra to -the study of solutions of the field equations derived from a non-linear -Lagrangian, as suggested by recently proposed unified theories. More -precisely, we restrict ourselves to the most general quadratic Lagrangian, -i.e. containing quadratic contributions in the different curvature tensors -exclusively. The corresponding field equations are then fourth-order in the -metric tensor components. The cosmological models studied are the simplest -ones in the class of spatially homogeneous but anisotropic models, -i.e. Bianchi I models. For these models, we consider only power-law -type solutions of the field equations. All the solutions of the associated -system of algebraic equations are found, using computer algebra, from a -search of its Groebner bases. While, in space dimension d=3, the -Einsteinian-Kasner metric is still the most general power-law type solution, -for d>3, no solution, other than the Minkowski space-time, is common to the -three systems of equations corresponding to the three contributions to the -Lagrangian density. In the case of a pure Riemann-squared contribution to the -Lagrangian (suggested by a recent calculation of the effective action for -the heterotic string), the possibility exists to realize a splitting of the -d-dimensional space into a (d-3)-dimensional internal space and a physical -3-dimensional space, the latter expanding in time as a power bigger than -2 (about 4.5 when d=9).}} - -@ARTICLE{Carlson:80, - AUTHOR = "P. Carlson", - TITLE = "Coordinate Free Relativity", - JOURNAL = "J. Math. Phys.", - YEAR = 1980, VOLUME = 21, PAGES = "1149-1154", - COMMENT = {{REDUCE} programs for tetrad formulation of GR.}} - -@PHDTHESIS{Carroll:73, - AUTHOR = "R. Carroll", - TITLE = "The Anomalous Magnetic Moment of the Electron in the -Mass Operator Formalism", - SCHOOL = "University of Michigan", - YEAR = 1973} - -@ARTICLE{Carroll:75, - AUTHOR = "R. Carroll", - TITLE = "Mass-Operator Calculation of the Electron g-Factor", - JOURNAL = "Phys. Rev. D", - YEAR = 1975, VOLUME = 8, PAGES = "2344-2354"} - -@TECHREPORT{Cejchan, - AUTHOR = "A. Cejchan and J. Nadrchal", - TITLE = "Application of {REDUCE}-2 and Analytic Integration -Program in the Theoretical Solid State Physics", - INSTITUTION = "Institute of Physics, CSAV, Prague"} - -@INPROCEEDINGS{Chaffy:88, - AUTHOR = "C. Chaffy-Camus", - TITLE = "An Application of {REDUCE} to the Approximation of $f(x,y)$", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "73-84"} - -@ARTICLE{Chinnick:86, - AUTHOR = "K. Chinnick and C. Gibson and J. F. Griffiths and W. Kordylewski", - TITLE = "Isothermal Interpretations of Oscillatory Ignition During -Hydrogen Oxidation in an Open System. {I}. {Analytical} Predictions and -Experimental Measurements of Periodicity", - JOURNAL = "Proc. Royal Soc. Lond.", - YEAR = 1986, VOLUME = "A405", PAGES = "117-128", - COMMENT = {Used {REDUCE} to solve Jacobian, but answer too complicated to -be of any use.}} - -@ARTICLE{Cline:90, - AUTHOR = "Terry Cline and Harold Abelson and Warren Harris", - TITLE = "Symbolic Computing in Engineering Design", - JOURNAL = "AI EDAM", YEAR = 1990, MONTH = "February"} - -@TECHREPORT{Cohen:76, - AUTHOR = "H. I. Cohen and O. Leringe and Y. Sundblad", - TITLE = "The Use of Algebraic Computing in General Relativity", - INSTITUTION = "The Royal Institute of Technology Department of Mechanics", - YEAR = 1976, NUMBER = "TRITA-MEK-76-02"} - -@TECHREPORT{Cohen:76a, - AUTHOR = "I. Cohen and F. Bark", - TITLE = "Perturbation Calculations for the Spin Up Problem Using {REDUCE}", - INSTITUTION = "The Royal Institute of Technology, Department -of Mechanics", - YEAR = 1976, NUMBER = "TRITA-MEK-76-03"} - -@TECHREPORT{Cohen:77, - AUTHOR = "I. Cohen and S. Yu. Slavyanov", - TITLE = "Smooth Perturbations of the {Schr{\"o}dinger} Equation with a -Linear Potential Related to the Charmonium Models", - INSTITUTION = "University of Stockholm Institute of Physics", - YEAR = 1977, TYPE = "USIP Report", NUMBER = "77-17"} - -@ARTICLE{Cohen:79, - AUTHOR = "J. P. Fitch and H. I. Cohen", - TITLE = "Using {CAMAL} for Algebraic Calculations in General Relativity", - JOURNAL = "General Relativity and Gravitation", VOLUME = 11, YEAR = 1979, - PAGES = "411-418"} - -@ARTICLE{Cohen:84, - AUTHOR = "H. I. Cohen and I. B. Frick and J. E. {\AA}man", - TITLE = "Algebraic Computing in General Relativity", - JOURNAL = "General Relativity and Gravitation, ed.", - YEAR = 1984, PAGES = "139-162", - COMMENT = {General relativity review.}} - -@INPROCEEDINGS{Cohen:89, - AUTHOR = "Joel S. Cohen", - TITLE = "The Effective Use of Computer Algebra Systems", - YEAR = 1989, PAGES = "677-698", - BOOKTITLE = "Transactions of the Sixth Army Conference on Applied -Mathematics and Computing", - COMMENT = {Review of author's experience with four computer algebra -systems.}} - -@ARTICLE{Connor:84, - AUTHOR = "J. N. L. Connor and P. R. Curtis and D. Farrelly", - TITLE = "The Uniform Asymptotic Swallowtail Approximation: Practical -Methods for Oscillating Integrals with Four Coalescing Saddle Points", - JOURNAL = "J. Phys. A", - YEAR = 1984, VOLUME = 17, PAGES = "283-310", - COMMENT = {Used {REDUCE} and {SCHOONSCHIP} for some algebraic -manipulations, and then checked the results with {MACSYMA}; this is the most -distrustful reference we have found.}} - -@ARTICLE{Connor:84a, - AUTHOR = "J. N. L. Connor and P. R. Curtis and C. J. Edge and A. Lagan{`a}", - TITLE = "The Uniform Asymptotic Swallowtail Approximation: Application -to the Collinear $H+F_{2}$", - JOURNAL = "J. Chem. Phys.", YEAR = 1984, VOLUME = 80, NUMBER = 3, - PAGES = "1362-1363", MONTH = "February"} - -@ARTICLE{Conwell:84, - AUTHOR = "P. R. Conwell and P. W. Barber and C. K. Rushworth", - TITLE = "Resonant Spectra of Dielectric Sphere", - JOURNAL = "J. Opt. Soc. Am. A", - YEAR = 1984, VOLUME = 1, PAGES = "62-67", - COMMENT = {{REDUCE} used to confirm independently convergence and accuracy -of {Numerical Bessel} function routine, expanding series by {REDUCE} and -using bigfloats. Described as slow but worthwhile.}} - -@INPROCEEDINGS{Cowan:79, - AUTHOR = "Richard M. Cowan and Martin L. Griss", - TITLE = "Hashing -- The Key to Rapid Pattern Matching", - BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes -in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "266-278", - PUBLISHER = "Springer-Verlag"} - -@BOOK{Cox:92, - AUTHOR = "D. Cox and J. Little and D. O'Shea", - TITLE = "deals, Varieties and Algorithms: - An Introduction of Computational Algebraic Geometry - and Commutative Algebra", - PUBLISHER = "Springer-Verlag", - YEAR = 1992, - COMMENTS = {The appendix contains a discussion of the Groebner basis - package for REDUCE}, - ABSTRACT = {This book is an introduction to algebraic geometry and -commutative algebra aimed primarily at undergraduates. It emphasizes -applications and the computational and algorithmic aspects of the -subject. Less abstract than other texts, and with prerequisites -(a course in linear algebra and any course discussing how to do -simple proofs), the text is also ideal for computer scientists as -well as mathematicians interested in the subject. The exposition -assumes that students have access to a computer algebra system such -as Maple, REDUCE or Mathematica, but assumes no prior experience -with a computer. - -Table of Contents: Geometry, Algebra and Algorithms; Groebner Bases; -Elimination Theory; The Algebra-Geometry Dictionary; Polynomial and -Rational Functions on a Variety; Robotics and Automatic Geometric -Theorem Proving; Invariant Theory of Finite Groups; Projective -Algebraic Geometry; The Dimension of a Variety; Appendices on Some -Concepts From Algebra, Pseudocode, Computer Algebra Systems, and -Independent Projects.}} - -@ARTICLE{Cung:75, - AUTHOR = "V. K. Cung", - TITLE = "Differential Cross Section of e+ + e- to e+ + $\mu-$ + -$\bar{\nu}_\mu$ + $\bar{\nu}_e$", - JOURNAL = "Phys. Lett.", - YEAR = 1975, VOLUME = "55B", PAGES = "67-70"} - -@TECHREPORT{Darbaidze:86, - AUTHOR = "Ya. Z. Darbaidze", - TITLE = "A Gluon Bremsstrahlung in Supersymmetry {QCD}", - INSTITUTION = "JINR", YEAR = 1986, TYPE = "Preprint", - NUMBER = "P2-86-825"} - -@ARTICLE{Darbaidze:86a, - AUTHOR = "J. Z. Darbaidze and V. A. Matveev and -Z. V. Merebashvili and L. A. Slepchenko", - TITLE = "Gluon Bremsstrahlung in Supersymmetric {QCD}", - JOURNAL = "Phys. Lett.", - YEAR = 1986, VOLUME = "B177", PAGE = "188"} - -@TECHREPORT{Darbaidze:88, - AUTHOR = "Ya. Z. Darbaidze and Z.V. Merebashvili and V.A. Rostovtsev", - TITLE = "Some Computer Realizations of the {REDUCE-3} Calculations for -Exclusive Processes", - INSTITUTION = "JINR", YEAR = 1988, TYPE = "Preprint", - NUMBER = "P2-88-769"} - -@TECHREPORT{Darbaidze:89, - AUTHOR = "Ya. Z. Darbaidze and V.A. Rostovtsev", - TITLE = "Analysis of the Differential Equations for the Exclusive Processes -and Explanation for the {``Mystery''} of the {Gamma-Distribution}", - INSTITUTION = "JINR", YEAR = 1989, TYPE = "Preprint", - NUMBER = "E2-89-286"} - -@INPROCEEDINGS{Dautcourt:79, - AUTHOR = "G. Dautcourt", - TITLE = "Application of {REDUCE} to Algebraic Computations in General -Relativity and Astrophysics", - YEAR = 1979, MONTH = "September", - BOOKTITLE = "Proc. of the Workshop in Symbolic Computation, Dubna, -{U.S.S.R.}", - COMMENT = {Reports the use of the system {REDUCE} 2 for general relativistic -calculations.}} - -@TECHREPORT{Dautcourt:80, - AUTHOR = "G. Dautcourt and K. P. Jann", - TITLE = "A Program Package in {REDUCE} 2 for Algebraic Computations in -General Relativity", - YEAR = 1980, - INSTITUTION = "Zentralinstitut fuer Astrophysik der -Akademie der Wissenschaften"} - -@ARTICLE{Dautcourt:81, - AUTHOR = "G. Dautcourt and K. P. Jann and E. Riemer and M. Riemer", - TITLE = "User's Guide to {REDUCE} Subroutines For Algebraic -Computations in General Relativity", - JOURNAL = "Astron. Nachr.", - YEAR = 1981, VOLUME = 302, PAGES = "1-13"} - -@ARTICLE{Dautcourt:83, - AUTHOR = "G. Dautcourt", - TITLE = "The Cosmological Problem as an Initial Value Problem on the -Observer's Past Light Cone: Geometry", - JOURNAL = "J. Phys. A", - YEAR = 1983, VOLUME = 16, PAGES = "3507-3528", - COMMENT = {Checked calculations with {REDUCE}, mainly {Riemann} tensor in -null coordinates.}} - -@ARTICLE{Davenport:81, - AUTHOR = "James Harold Davenport", - TITLE = "On the Integration of Algebraic Functions", - JOURNAL = "Lecture Notes in Computer Science", - PUBLISHER = "Springer-Verlag", - YEAR = 1981, VOLUME = 102, PAGES = "1-197"} - -@ARTICLE{Davenport:82, - AUTHOR = "James H. Davenport", - TITLE = "Fast {REDUCE:} The {trade-off} between efficiency and -generality", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 1, PAGES = "8-11", MONTH = "February"} - -@ARTICLE{Davenport:82a, - AUTHOR = "James H. Davenport", - TITLE = "What do we want from a {high-level} language?", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "6-9", MONTH = "November"} - -@INPROCEEDINGS{Davenport:85, - AUTHOR = "James Davenport and Julian Padget", - TITLE = "{HEUGCD:} How Elementary Upperbounds Generate Cheaper Data", - BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes -in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "18-28", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Davenport:88, - AUTHOR = "J. H. Davenport", - TITLE = "The World of Computer Algebra", - JOURNAL = "New Scientist", - YEAR = 1988, MONTH = "September", VOLUME = 1629, PAGES = "71-72"} - -@BOOK{Davenport:88a, - AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", - TITLE = "Computer Algebra, Systems and Algorithms for Algebraic Computation", - PUBLISHER = "Academic Press", EDITION = "2nd", YEAR = 1993} - -@BOOK{Davenport:88b, - AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", - TITLE = "Calcul Formel (in French)", - PUBLISHER = "Masson", EDITION = "2nd", YEAR = 1993} - -@BOOK{Davenport:88c, - AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", - TITLE = "Kompyuter Algebra (in Russian)", - PUBLISHER = "MIR", EDITION = "1st", YEAR = 1991} - -@TECHREPORT{Della-Dora:81, - AUTHOR = "J. Della Dora and E. Tournier", - TITLE = "Solutions Formelles D'Equations Differentielles au Voisinage de -Points Singuliers Reguliers", - INSTITUTION = "Centre National de la Recherche Scientifique", - YEAR = 1981, TYPE = "Report", NUMBER = 239} - -@INPROCEEDINGS{Della-Dora:84, - AUTHOR = "J. Della Dora and E. Tournier", - TITLE = "Homogeneous Linear Difference Equation {(Frobenius-Boole Method)}", - BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes -in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "2-12", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Della-Dora:85, - AUTHOR = "Jean Della-Dora and Claire Dicrescenzo and Dominique Duval", - TITLE = "About a New Method for Computing in Algebraic Number Fields", - INSTITUTION = "Universit{\'e} de Grenoble, Institut Fourier, -France", YEAR = 1985, MONTH = "November"} - -@ARTICLE{Demaret:89, - AUTHOR = "J. Demaret and H. Caprasse and A. Moussiaux and Ph. Tombal and -D. Papadopoulos", - TITLE = "{Ten-dimensional Lovelock-type Space-Times}", - JOURNAL = "{To appear} Phys. Rev. D", - YEAR = 1989, MONTH = "July"} - -@ARTICLE{DeMenna:87, - AUTHOR = "L. De Menna and G. Miano and G. Rubinacci", - TITLE = "Volterra's Series Solutions of Free Boundary Plasma Equilibria", - JOURNAL = "Phys. Fluids", - YEAR = 1987, VOLUME = 30, PAGES = "409-416", - COMMENT = {Magnetohydrodynamics. "We have carried out the computations up -to the fourth order, (the fourth order has been obtained by means of the -symbolic program {REDUCE}").}} - -@ARTICLE{Demichev:85, - AUTHOR = "A. P. Demichev and A. Ya. Rodionov", - TITLE = "A {REDUCE} Program for the Calculation of Geometrical -Characteristics of Compactified Multidimensional {Riemannian} Space", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1985, VOLUME = 38, PAGES = "441-448", - COMMENT = {Covariant theories in N dimensional ($N \geq 4$) space-time. -{REDUCE} programs to calculate {Ricci, Einstein and Yang-Mills} curvature -and energy-momentum tensor.}} - -@TECHREPORT{Demichev:86, - AUTHOR = "A. P. Demichev and A. Ya. Rodionov", - TITLE = "Freund-{Rubin} Type Solutions for Different Compactifications of -the Eleven-Dimensional Space", - INSTITUTION = "Institute for High Energy Physics", YEAR = 1986, - TYPE = "Preprint", NUMBER = "86-85", - ABSTRACT = {The results of calculating geometrical characteristics of -seven-dimensional quotient spaces are represented. These -quantities are necessary for the construction of compactifying -solutions of the eleven-dimensional supergravity.}} - -@ARTICLE{deRop:88, - AUTHOR = "Y. de Rop and J. Demaret", - TITLE = "Using {EXCALC} to Study Nondiagonal Multidimensional -Spatially Homogeneous Cosmologies", - JOURNAL = "Gen. Rel. Grav.", - YEAR = 1988, VOLUME = 20, PAGES = "1127-1139"} - -@TECHREPORT{DeVos:89, - AUTHOR = "Alexis De Vos", - TITLE = "The use of {Reduce} in solar energy conversion theory", - INSTITUTION = "State University of Gent, {CAGe} Computer Algebra -Group", YEAR = 1989, TYPE = "Reports of the {CAGe} Project", -NUMBER = 4, MONTH = "August"} - -@TECHREPORT{DeVos:93, - AUTHOR = "Alexis De Vos", - TITLE = "Carnot engines, {Gr{\"o}bner} bases and all the winds on the Earth", - INSTITUTION = "University of Gent, {CAGe} Computer Algebra Group", - YEAR = 1993, TYPE = "The {CAGe} Reports", NUMBER = 9, MONTH = "March", - ABSTRACT = {In the present paper, we determine which part of the solar -energy incident on a planet can be converted into mechanical work. The -planet is assumed to be spherical and not rotating around an axis. From -numerical calculations, we find that at the most 9.64% of the absorbed -solar energy can be converted into work. But can we find an analytical -expression for this fundamental number? We try this challenge with the -REDUCE procedures for manipulation of polynomials.}} - -@INPROCEEDINGS{Dewar:89, - AUTHOR = "M. C. Dewar", - TITLE = "{IRENA --} An Integrated Symbolic and Numerical Computation -Environment", - BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", - YEAR = 1989, PAGES = "171-179"} - -@ARTICLE{Dhar:85, - AUTHOR = "D. Dhar and J-M. Maillard", - TITLE = "Susceptibility of the Checkerboard {Ising} Model", - JOURNAL = "J. Phys. A", - YEAR = 1985, VOLUME = 18, PAGES = "L383-L388", - COMMENT = {Used {REDUCE} for tedious algebra, and got a simple answer. -statistical mechanics(?). "At the disorder variety, the n-point correlation -functions of the checkerboard Potts model has a simple causal -structure. An exact expression for the susceptibility in the Ising -case is obtained."}} - -@TECHREPORT{Dicrescenzo:85, - AUTHOR = "Claire Dicrescenzo", - TITLE = "Algebraic Computation on Algebraic Numbers", - INSTITUTION = "Institut Fourier, Laboratoire de -Math{\'e}matiques, France", YEAR = 1985, MONTH = "December", - COMMENT = {Examples are given of a new method, implemented on {REDUCE}, -for computing algebraically on algebraic numbers.}} - -@TECHREPORT{Diver, - AUTHOR = "D. A. Diver and E. Q. Laing and C. C. Sellar", - TITLE = "Waves in a Cold Plasma with a Spatially Rotating Magnetic Field", - YEAR = 1988, - INSTITUTION = "Department of Physics and Astronomy, University of -Glasgow, Plasma Physics Group", TYPE = "Report", NUMBER = "GU TPA 88/12-1", - COMMENT = {"{\ldots}The algebraic manipulation system {REDUCE} was used in -constructing the following tensor definitions which allows us to make fewer -approximations than other authors."}} - -@INPROCEEDINGS{Diver:86, - AUTHOR = "D. A. Diver and E. W. Laing", - TITLE = "Proc. 8th {Europhysics} Conference on -Computational Physics", - YEAR = 1986, - BOOKTITLE = "Computing in Plasma Physics"} - -@INPROCEEDINGS{Diver:88, - AUTHOR = "D. A. Diver and E. W. Laing", - BOOKTITLE = "Proc. {XV} {European} Conference on Controlled -Fusion and Plasma Heating", - YEAR = 1988} - -@TECHREPORT{Diver:88a, - AUTHOR = "D. A. Diver and E. W. Laing", - TITLE = "Alfven Resonance Absorption in a Magnetofluid", - YEAR = 1988, TYPE = "Report", - INSTITUTION = "Department of Physics and Astronomy, University of -Glasgow, Plasma Physics Group", - NUMBER = "GUTPA 88/04-01", MONTH = "July", - COMMENT = {Presented at 15th {UK} Plasma Physics Conference, {UMIST}.}} - -@ARTICLE{Diver:91, - AUTHOR = "D. A. Diver", - TITLE = "Modelling Waves with Computer Algebra", - JOURNAL = "J. Symbolic Computation", - YEAR = 1991, VOLUME = 11, NUMBER = 3, PAGES = "275-289", MONTH = "March", - ABSTRACT = {A sophisticated model for linear waves in an inhomogeneous -plasma is tackled completely using the computer algebra system {REDUCE}. -The algebra code mirrors the mathematics, and is structured in a simple -and straightforward manner. In so doing, the solution technique is made -obvious, and the overall philosophy of the approach is intuitive to the -{non-specialist} computer algebra user.}} - -@TECHREPORT{Dorfi:85, - AUTHOR = "E. A. Dorfi and L. O'C. Drury", - TITLE = "Simple Adaptive Grids for {1D} Initial Value Problems", - INSTITUTION = "Max-Plack-Institut fuer Kernphysik, Heidelberg, -West Germany", YEAR = 1985, - NUMBER = "MPI H-1985-V21"} - -@ARTICLE{Dorizzi:86, - AUTHOR = "B. Dorizzi and B. Grammaticos and J. Hietarinta and A. Ramani -and F. Schwarz", - TITLE = "New integrable three dimensional quartic potentials", - JOURNAL = "Phys. Lett.", - YEAR = 1986, VOLUME = "116A", PAGES = "432-436", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@TECHREPORT{dosSantos:85, - AUTHOR = "R. P. dos Santos and P. P. Srivastava", - TITLE = "Two-loop Effective Potential for {Wess-Zumino} Model using -Superfields", - INSTITUTION = "International Centre for Theoretical Physics", - YEAR = 1985, NUMBER = "IC/85/205", MONTH = "October", - ABSTRACT = {For the case of several interacting chiral superfields the -propagators for the unconstrained superfield potentials in the 'shifted' -theory, where the supersymmetry is explicitly broken, are derived in a -compact form. They are used to compute one-loop effective potential in -the general case, while a superfield calculation of renormalized effective -potential to two loops for the Wess-Zumino model is performed.}} - -@ARTICLE{dosSantos:87, - AUTHOR = "Renato P. dos Santos", - TITLE = "Using {REDUCE} in Supersymmetry", - JOURNAL = "J. Symb. Comp.", - YEAR = 1989, VOLUME = 7, PAGES = "523-525"} - -@PHDTHESIS{dosSantos:87a, - AUTHOR = "R. P. dos Santos", - TITLE = "O M{\'e}todo de Supercampos para o C{\'a}lculo de Potencial -Efetivo em Modelos com Supercampos Quirais: Os Modelos de Wess e -Zumino e de O'Raifeartaigh", - SCHOOL = "Centro Brasileiro de Pesquisas F{\'i}sicas", - YEAR = 1987, - COMMENT = {{(In Portuguese)} Using the method of {Superfields}, the -effective potential for supersymmetric models of {Wess-Zumino} and of -{O'Raifeartaigh} is evaluated up to two-loop order. The spontaneous -supersymmetry breaking is discussed. {REDUCE} plays very important -role in evaluation of the {Feynman} superdiagrams and in -renormalization.}} - -@TECHREPORT{dosSantos:88a, - AUTHOR = "Renato P. dos Santos", - TITLE = "Introdu\c{c}\~{a}o ao Sistema {REDUCE} de C\'{a}lculo -Alg\'{e}brico", - INSTITUTION = "CBPF, Rio de Janeiro, Brazil", - YEAR = 1988, NUMBER = "CBPF-NT-001/88", - COMMENT = {{(In Portuguese)} Lecture notes of a course on {REDUCE}.}} - -@ARTICLE{dosSantos:90, - AUTHOR = "R. P. dos Santos and W. L. Roque", - TITLE = "On the Design of an Expert Help System for Computer Algebra -Systems", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1990, VOLUME = 24, NUMBER = 4, PAGES = "22-25", MONTH = "October"} - -@InProceedings{Dresse:93, - author = "A. Dresse", - title = "Treatment of Dummy Variables and {BRST} Theory in Computer - Algebra", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "110-119", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - comment = {A canonical form algorithm for quantities with locally scoped - variables (e.g. Summation convention, tensor products) is - developed in a {REDUCE} package.} -} - -@ARTICLE{Drska:90, - AUTHOR = "Ladislav Drska and Richard Liska and Milan Sinor", - TITLE = "Two practical packages for computational physics{-GCPM, RLFI}", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1990, VOLUME = 61, NUMBER = "1-2", MONTH = "November", - PAGES = "225-230", - ABSTRACT = {Two handy computer-program packages for technical support of -the work in two different branches of the computational physics are reported: -(1) A general package for the symbolic and numerical transformation of -expressions from one system of units to another. (2) A package allowing -high-quality two-dimensional output of mathematical formulas from the -computer-algebra system {REDUCE}.}} - -@ARTICLE{Dubowsky:75, - AUTHOR = "S. Dubowsky and J. L. Grant", - TITLE = "Application of Symbolic Manipulation to Time -Domain Analysis of Nonlinear Dynamic Systems", - JOURNAL = "Journ. of Dynamic Systems, Measurement, and Control", - YEAR = 1975, VOLUME = "75-Aut-J"} - -@ARTICLE{Dudley:89, - AUTHOR = "M. L. Dudley and R. W. James", - TITLE = "{Computer-aided} Derivation of Spherical Harmonic Spectral Equations -in Astrogeophyics", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 8, NUMBER = 4, PAGES = "423-427", MONTH = "October"} - -@ARTICLE{Dufner:69, - AUTHOR = "A. M. Dufner and Y. S. Tsai", - TITLE = "Phenomenological Analysis of the $\gamma$NN* Form Factors", - JOURNAL = "Phys. Rev.", - YEAR = 1969, VOLUME = 168, PAGES = "1801-1809"} - -@INPROCEEDINGS{Dulyan:87, - AUTHOR = "L. S. Dulyan", - TITLE = "The Calculation of {QCD} Triangular {Feynman} Graphs in the -External Gluonic Field Using {REDUCE}-2 System", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "172-173", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Duncan:86, - AUTHOR = "Anthony Duncan and Ralph Roskies", - TITLE = "Representations of Unusual Mathematical Structures in Scientific -Applications of Symbolic Computation", - JOURNAL = "J. Symbolic Computation", - YEAR = 1986, VOLUME = 2, NUMBER = 2, PAGES = "201-206", MONTH = "June", - ABSTRACT = {We present examples of techniques we have used to apply {REDUCE} -to problems in particle physics which have mathematical structures unknown to -{REDUCE}.}} - -@PHDTHESIS{Duval:87, - AUTHOR = "Dominique Duval", - TITLE = "Diverses questions relatives au Calcul Formel -Avec des Nombres Alg{\'e}briques", - SCHOOL = "L'Universit{\'e} Scientifique, Technologique -et M{\'e}dicale de Grenoble", YEAR = 1987} - -@InProceedings{Dyer:94, - author = {Charles C. Dyer}, - title = {An Application of Symbolic Computation in the - Physical Sciences}, - booktitle = {Symbolic and Algebraic Computation}, - editor = {}, - series = {ISSAC}, - year = {1994}, - organization = {SIGSAM}, - publisher = {ACM}, - pages = {181--186} -} - -@ARTICLE{Earles:70, - AUTHOR = "D. Earles", - TITLE = "A Measurement of the Electron-Production of Muon Pairs", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1970, VOLUME = 25, PAGES = "129-133"} - -@ARTICLE{Eastwood:87, - AUTHOR = "James W. Eastwood", - TITLE = "Orthovec: A {REDUCE} Program for {3-D} Vector Analysis -in Orthogonal Curvilinear Coordinates", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1987, VOLUME = 47, NUMBER = 1, PAGES = "139-147", MONTH = "October"} - -@TECHREPORT{Eastwood:87a, - AUTHOR = "James W. Eastwood and Christopher J. H. Watson", - TITLE = "An Analytic Theory of {Wave-Current} Interactions", - INSTITUTION = "Culham Laboratory, Theory and Optics Division", - YEAR = 1987, NUMBER = "Plasma Physics Note 87/7", MONTH = "February", - ABSTRACT = {This report presents results of the Department of Energy -contract to obtain high order analytic solutions to nonlinear hydrodynamic -equation describing steady periodic waves propagating in sheared currents. -The purpose of this work is to provide working formulae for computing -combined wave and current loadings in the design of offshore structures. -Using the {REDUCE} algebra package, we have identified minor typographical -errors in the published fifth coefficients for uniform currents given by -{Fenton [2]} and by Skjelbreia and {Hendrickson [5]}. We have demonstrated -the equivalence of corrected forms of these expressions to fifth order, and -extended Fenton's expansion to seventh order. We present a new fifth order -theory for bilinear current profiles. {FORTRAN} software for the seven order -uniform current and fifth order bilinear current theories are given.}} - -@ARTICLE{Eastwood:91, - AUTHOR = "James W. Eastwood", - TITLE = "{ORTHOVEC:} version 2 of the {REDUCE} program for {3-D} vector -analysis in orthogonal curvilinear coordinates", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1991, VOLUME = 64, NUMBER = 1, PAGES = "121-122", MONTH = "April"} - -@TECHREPORT{Edelen:81, - AUTHOR = "Dominic G. B. Edelen", - TITLE = "Programs for Calculation of Isovector Fields in the -{REDUCE}-2 Environment", - INSTITUTION = "Center for the Application of Mathematics, -Lehigh University", YEAR = 1981, NUMBER = "TBD", MONTH = "August"} - -@ARTICLE{Edelen:82, - AUTHOR = "D. G. B. Edelen", - TITLE = "Isovector Fields for Problems in the Mechanics of Solids and -Fluids", - JOURNAL = "Int. Journ. Eng. Sci.", - YEAR = 1982, VOLUME = 20, PAGES = "803-815", - COMMENT = {Prolongation methods as a {REDUCE} package for this, available -from Center for Applications of Mathematics, Lehigh Univ., Bethlehem, PA -18015. Applications to mechanics of solids and fluids.}} - -@BOOK{Edneral:89, - AUTHOR = "Viktor F. Edneral and Aleksandr P. Kryukov and -Anatolii Ia. Rodionov", - TITLE = "The language of the analytic computer program {REDUCE}", - PUBLISHER = "Moscow, {Izd-vo}, Moskovskogo {un-ta}", YEAR = 1989, - COMMENT = {This monograph -- first in The Soviet Union with a systematic -treatment of the analytical computer (program) {REDUCE}.}} - -@ARTICLE{Eisenberger:90, - AUTHOR = "Moshe Eisenberger", - TITLE = "Application of Symbolic Algebra to the Analysis of Plates -on Variable Elastic Foundation", - JOURNAL = "J. Symbolic Computation", - YEAR = 1990, VOLUME = 9, NUMBER = 2, PAGES = "207-213", MONTH = "February"} - -@TECHREPORT{Eissfeller:86, - AUTHOR = "Bernd Ei{\ss}feller and G{\"u}nter W. Hein", - TITLE = "A Contribution to {3D-Operational} Geodesy", - INSTITUTION = "Universit{\"a}rer Studiengang Vermessungswesen -and Universit{\"a}t der Bundeswehr M{\"u}nchen", - YEAR = 1986, NUMBER = "Heft 17", MONTH = "December"} - -@PHDTHESIS{Eitelbach:73, - AUTHOR = "D. L. Eitelbach", - TITLE = "Automatic Analysis of Problems in Elementary Mechanics", - SCHOOL = "University of Illinois", - YEAR = 1973} - -@ARTICLE{Eleuterio:82, - AUTHOR = "S. M. Eleut{\'e}rio and R. V. Mendes", - TITLE = "Note on Equivalence and Singularities: An Application of -Computer Algebra", - JOURNAL = "Journ. Comp. Phys.", - YEAR = 1982, VOLUME = 48, PAGES = "150-156", - COMMENT = {{GR} equivalence, commenting on \AAman & Karlhede.}} - -@ARTICLE{Eliseev:85, - AUTHOR = "V. P. Eliseev and R. N. Fedorova and V. V. Kornyak", - TITLE = "A {REDUCE} Program for Determining Point and Contact {Lie} -Symmetries of Differential Equations", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1985, VOLUME = 36, PAGES = "383-389", - ABSTRACT = {A universal {REDUCE} program for obtaining the systems of -determining equations of the Lie algebra of point and contact -symmetries is proposed.}} - -@ARTICLE{Elishakoff:87, - AUTHOR = "Isaac Elishakoff and Joseph Hollkamp", - TITLE = "Computerized Symbolic Solution for a Nonconservative -System in Which Instability Occurs by Flutter in One Range -of a Parameter and by Divergence in Another", - JOURNAL = "Comp. Methods in Applied Mechanics and Engineering", - YEAR = 1987, VOLUME = 62, PAGES = "27-46", - COMMENT = {"{\ldots}the problem is solved by the {Galerkin} method in -conjunction with computerized symbolic algebra". The system used is {REDUCE}. -"It carries out algebraic operations irrespective of their complexity". -Includes snatches of code and algebraic answers. Mainly -differentiation and substitution, plus a little integration. The -coefficients get rather large (18 digits or so).}} - -@ARTICLE{Elishakoff:87a, - AUTHOR = "Isaac Elishakoff and Brian Couch", - TITLE = "Application of Symbolic Algebra to the Instability of a -Nonconservative System", - JOURNAL = "J. Symbolic Computation", - YEAR = 1987, VOLUME = 4, NUMBER = 3, PAGES = "391-396", MONTH = "December"} - -@ARTICLE{Esteban:90, - AUTHOR = "E.P. Esteban and E. Ramos", - TITLE = "Algebraic computing and the {Newman-Penrose} formalism", - JOURNAL = "Computers in Physics", - YEAR = 1990, PAGES = "285-290", MONTH = "May/June"} - -% REDUCE BIBLIOGRAPHY - -% Part 2: F-H - -% Copyright (c) 1995 RAND. All Rights Reserved. - -% Additions and corrections are solicited. Please send them, in the -% same format as these entries if possible, to reduce at rand.org. - - -@ARTICLE{Falck:89, - AUTHOR = "N. K. Falck and D. Graudenz and G. Kramer", - TITLE = "Cross section for {five-parton} production in $e^{+} e^{-}$ -annihilation", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1989, VOLUME = 56, PAGES = "181-198", NUMBER = 2, MONTH = "December"} - -@ARTICLE{Fazio:84, - AUTHOR = "P. M. Fazio and G. E. Copeland", - TITLE = "Cooper-Type Minima in Multipole Cross Sections of Atomic Hydrogen", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1984, VOLUME = 53, NUMBER = "2", MONTH = "July"} - -@INPROCEEDINGS{Fedorova:87, - AUTHOR = "R. N. Fedorova and V. P. Gerdt and N. N. Govorun -and V. P. Shirikov", - TITLE = "Computer Algebra in Physical Research of {Joint Institute} -for {Nuclear Research}", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "1-10", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Fedorova:87a, - AUTHOR = "R. N. Fedorova and V. V. Kornyak", - TITLE = "Computer Algebra Application for Determining Local Symmetries -of Differential Equations", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "174-175", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Feldmar:86, - AUTHOR = "E. Feldmar and K. S. K{\"o}lbig", - TITLE = "{REDUCE} Procedures for the Manipulation of Generalized -Power Series", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1986, VOLUME = 39, PAGES = "267-284"} - -@ARTICLE{Feuillebois:84, - AUTHOR = "F. Feuillebois", - TITLE = "Sedimentation in a Dispersion with Vertical Inhomogenieties", - JOURNAL = "Journ. Fluid Mech.", - YEAR = 1984, VOLUME = 139, PAGES = "145-171", - COMMENT = {Uses {REDUCE} and {INT} to evaluate some integrals in the -expansion of 1/s, a small quantity.}} - -@ARTICLE{Fitch:73, - AUTHOR = "John Fitch", - TITLE = "Problems \#3 and \#4 in {REDUCE} and {MACSYMA}", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1973, PAGES = "10-11", - ABSTRACT = {The algebra systems {REDUCE} and {MACSYMA} are used to solve -{SIGSAM} Problem \#3, the Reversion of a Double Series, and {SIGSAM} -Problem \#4, the Lie Transform Solution of the Harmonic Oscillator.}} - -@INPROCEEDINGS{Fitch:81, - AUTHOR = "J. P. Fitch", - TITLE = "User-based Integration Software", - BOOKTITLE = "Proc. 1981 {ACM} Symposium on Symbolic -and Algebraic Computation", - YEAR = 1981, PAGES = "245-248"} - -@INPROCEEDINGS{Fitch:83, - AUTHOR = "J. P. Fitch", - TITLE = "Implementing {REDUCE} on a Microprocessor", - BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes -in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "128-136", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Fitch:85, - AUTHOR = "J. P. Fitch", - TITLE = "Solving Algebraic Problems with {REDUCE}", - JOURNAL = "J. of Symbolic Computation", - YEAR = 1985, VOLUME = 1, NUMBER = 2, PAGES = "211-227", MONTH = "June"} - -@INPROCEEDINGS{Fitch:85a, - AUTHOR = "J. P. Fitch", - TITLE = "Applying Computer Algebra", - BOOKTITLE = "International Conference on Computer Algebra and its -Application in Theory", - YEAR = 1985, PAGES = "262-275"} - -@INPROCEEDINGS{Fitch:87, - AUTHOR = "J. P. Fitch", - TITLE = "Utilisation du Calcul Formel", - BOOKTITLE = "Calcul Formel et Automatique", - EDITOR = "P. Chenin", PUBLISHER = "Editions du {CNRS}", - YEAR = 1987, PAGES = "119-136"} - -@INPROCEEDINGS{Fitch:87a, - AUTHOR = "J. P. Fitch and R. G. Hall", - TITLE = "Symbolic Computation and the Finite Element Method", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "95-96", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Fitch:89, - AUTHOR = "J. P. Fitch", - TITLE = "Can {REDUCE} be run in parallel?", - BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", - YEAR = 1989, PAGES = "155-162"} - -@ARTICLE{Fitch:89a, - AUTHOR = "J. Fitch", - TITLE = "Compiling for Parallelism", - JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora -and J. Fitch", - YEAR = 1989, PAGES = "19-31", PUBLISHER = "Academic Press, London"} - -@InProceedings{Fitch90, - author = "J. P. Fitch", - title = "A delivery system for {REDUCE}", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "76-81", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Fitch:90a, - AUTHOR = "John Fitch", - TITLE = "The symbolic-numeric interface", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1990, VOLUME = 61, NUMBER = "1-2", MONTH = "November", - PAGES = "22-33", - ABSTRACT = {Algebraic computation can be of great assistance in the -preparation of numerical programs. The paper considers some of these, -from simple to complex, and describes work currently in progress to produce -a true integrated symbolic-numeric computing system.}} - -@ARTICLE{Fitch:93, - AUTHOR = "John Fitch", - TITLE = "Mathematics goes automatic", - JOURNAL = "Physics world", - YEAR = 1993, VOLUME = 6, NUMBER = 6, MONTH = "June", PAGES = "48-52", - COMMENT = {Computer algebra enhances the productivity of any scientist or -engineer by increasing efficiency and doing away with tedious operations}} - -@TECHREPORT{Flatau:86, - AUTHOR = "Piotr J. Flatau and John P. Boyd and William R. Cotton", - TITLE = "Symbolic Algebra in Applied Mathematics and Geophysical -Fluid Dynamics - {REDUCE} Examples", - INSTITUTION = "Dept. of Atmospheric and Oceanic Science, University -of Michigan, and Dept. of Atmospheric Science, Colorado State -University", YEAR = 1986} - -@TECHREPORT{Flath:86, - AUTHOR = "Dan Flath", - TITLE = "Remarks on Tensor Operators", - INSTITUTION = "National University of Singapore, Department -of Mathematics", TYPE = "Research Report", - YEAR = 1986, NUMBER = 266, MONTH = "July"} - -@ARTICLE{Fleischer:71, - AUTHOR = "J. Fleischer", - TITLE = "Partial Wave Analysis of Nucleon-Nucleon {Bethe}-{Salpeter} -Equation on the Computer", - JOURNAL = "Journ. of Comp. Phys.", - YEAR = 1971, VOLUME = 12, PAGES = "112-123"} - -@ARTICLE{Fleischer:73, - AUTHOR = "J. Fleischer and J. L. Gammel and M. T. Menzel", - TITLE = "Matrix {Pad\'e} Approximants for the {1SO}- and -{3PO}- Partial Waves in Nucleon-Nucleon Scattering", - JOURNAL = "Phys. Rev. D", - YEAR = 1973, VOLUME = 8, PAGES = "1545-1552"} - -@ARTICLE{Fleischer:75, - AUTHOR = "J. Fleischer and J. A. Tjon", - TITLE = "Bethe-{Salpeter} Equation for {J}=0 Nucleon-Nucleon -Scattering with One-Boson Exchange", - JOURNAL = "Nuclear Physics", - YEAR = 1975, VOLUME = "B84", PAGES = "375-396"} - -@ARTICLE{Fogelholm:82, - AUTHOR = "Rabbe Fogelholm and Inge B. Frick", - TITLE = "Standard {LISP} for the {VAX:} A Provisional Implementation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "10-12", MONTH = "November"} - -@ARTICLE{Foster:89, - AUTHOR = "Kenneth R. Foster and Haim H. Bau", - TITLE = "Symbolic Manipulation Programs for the Personal Computer", - JOURNAL = "Science", - YEAR = 1989, VOLUME = 243, PAGES = "679-243", MONTH = "February", - COMMENT = {Reviews several algebra programs that run on small machines. -doesn't rate the {PC} version of {REDUCE} very highly because of the small -workspace.}} - -@ARTICLE{Fox:71, - AUTHOR = "J. A. Fox", - TITLE = "Recalculation of the Crossed Graph Contribution -to the 4th Order {Lamb} Shift", - JOURNAL = "Phys. Rev. D", - YEAR = 1971, VOLUME = 3, PAGES = "3228-3230"} - -@ARTICLE{Fox:74, - AUTHOR = "John A. Fox and Anthony C. Hearn", - TITLE = "Analytic Computation of Some Integrals in Fourth Order -Quantum Electrodynamics", - JOURNAL = "Journ. Comp. Phys.", - YEAR = 1974, VOLUME = 14, PAGES = "301-317", - ABSTRACT = {A program for the analytic evaluation of some parametric -integrals which occur in fourth order {QED} calculations is described.}} - -@ARTICLE{Franceschetti:85, - AUTHOR = "G. Franceschetti and I. Pinto", - TITLE = "Nonlinear Propagation and Scattering: Analytical Solution and -Symbolic Code Implementation", - JOURNAL = "J. Opt. Soc. Am. A", - YEAR = 1985, VOLUME = 2, PAGES = "997-1006", - COMMENT = {Volterra series using {REDUCE}. Perturbation expansions.}} - -@INPROCEEDINGS{Freire:88, - AUTHOR = "E. Freire and E. Gamero and E. Ponce and L. G. Franquelo", - TITLE = "An Algorithm for Symbolic Computation of Center Manifolds", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "218-230"} - -@INPROCEEDINGS{Freire:89, - AUTHOR = "E. Freire and E. Gamero and E. Ponce", - TITLE = "An Algorithm for Symbolic Computation of {Hopf} Bifurcation", - BOOKTITLE = "Proc. Computers and Mathematics '89", - EDITOR = "E. Kaltofen and S. M. Watt", - YEAR = 1989, PAGES = "109-118", PUBLISHER = "Springer-Verlag, New York"} - -@TECHREPORT{Frick:82, - AUTHOR = "I. G. Frick and R. Fogelholm", - TITLE = "An Implementation of {Standard} {Lisp} Built on Top of {Franz Lisp}", - INSTITUTION = "University of Stockholm, Institute of -Physics", YEAR = 1982, TYPE = "Report", MONTH = "April", - COMMENT = {A Standard {LISP} system has been built for the {VAX-11} -large-address-space computer by embedding the required function -definitions in the available Franz Lisp system for {VAX/UNIX}.}} - -@ARTICLE{Fujimoto:84, - AUTHOR = "Y. Fujimoto and T. Garavaglia", - TITLE = "Phase Diagrams in {Scalar QED}", - JOURNAL = "Physics Letters", - YEAR = 1984, VOLUME = "148B", NUMBER = "1,2,3", PAGES = "220-224", - MONTH = "November"} - -@ARTICLE{Fuzio:85, - AUTHOR = "P. M. Fuzio and G. E. Copeland", - TITLE = "Partial Radiative-Recombination Cross Sections for Excited -States of Hydrogen", - JOURNAL = "Phys. Rev. A", - YEAR = 1985, VOLUME = 31, NUMBER = 1, PAGES = "187-195", - ABSTRACT = {The squares of the dipole and quadrupole matrix elements for the -free-to-bond transitions of hydrogen uptp high bound states are -derived in closed analytic form using a method suitable for computer -algebra.}} - -@TECHREPORT{Gaemers, - AUTHOR = "K. J. F. Gaemers and R. Gastmans and F. M. Renard", - TITLE = "Neutrino Counting in e+ e- Collisions", - INSTITUTION = "NIKHEF-H, Amsterdam", TYPE = "Preprint", - ABSTRACT = {The possibility of counting the number of neutrino types -in e+ e- $\rightarrow$ gamma nu nubar is re-examined by taking into -account effects of the Z-pole.}} - -@TECHREPORT{Gaemers:78, - AUTHOR = "K. J. F. Gaemers and G. J. Gounaris", - TITLE = "Polarization Amplitudes For e+e- $\rightarrow$ W+W- -$\rightarrow$ ZZ", - INSTITUTION = "CERN", YEAR = 1978, TYPE = "Preprint", - NUMBER = "TH.2548-CERN", MONTH = "August", - ABSTRACT = {The main purpose of this work is to study the three weak boson -vertex. We give explicit formulae for all polarization amplitudes of -the processes e+e- $\rightarrow$ W+W- and e+e- $\rightarrow$ ZZ, with -arbitrary couplings between the various intermediate vector bosons.}} - -@INPROCEEDINGS{Ganzha:89, - AUTHOR = "V. Ganzha and R. Liska", - TITLE = "Application of the {REDUCE} Computer Algebra System to Stability -Analysis of Difference Schemes", - BOOKTITLE = "Proc. Computers and Mathematics '89", - EDITOR = "E. Kaltofen and S. M. Watt", - YEAR = 1989, PAGES = "119-129", PUBLISHER = "Springer-Verlag, New York"} - -@InProceedings{Ganzha90, - author = "Victor G. Ganzha and Michail Yu. Shaskov", - title = "Local Approximation Study of Difference Operators by - means of {REDUCE} System", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "185-192", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@InProceedings{Ganzha90a, - author = "V. G. Ganzha and S. V. Meleshko and V. P. Shelest", - title = "Application of {REDUCE} System for Analyzing - Consistency of Systems of {P.D.E.'s}", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "301", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@INPROCEEDINGS{Ganzha:91, - AUTHOR = "V.G. Ganzha and B. Yu. Scobelev and E.V. Vorozhtsov", - TITLE = "Stability Analysis of Difference Schemes by the Catastrophe -Theory Methods and by Means of Computer Algebra", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "427-428", - YEAR = 1991} - -@InProceedings{Ganzha:94, - author = "V. G. Ganzha and E. V. Vorozhtsov and J. Boers and - J. A. van Hulzen", - title = {Symbolic-Numeric Stability Investigations of {Jameson's} - Schemes for Thin-layer {Navier-Stokes} Equations}, - booktitle = {Symbolic and Algebraic Computation}, - editor = {}, - series = {ISSAC}, - year = {1994}, - organization = {SIGSAM}, - publisher = {ACM}, - pages = {234--241} -} - -@TECHREPORT{Garavaglia, - AUTHOR = "Theodore Garavaglia", - TITLE = "Polarized Electron Scattering on Spin Zero and Polarized Spin -$\frac{1}{2}$ Targets: Deep Inelastic Scattering, Elastic Electron-muon -Scattering, and Elastic Electron-Nucleon Scattering", - INSTITUTION = "Inst. Teich. Bhaile Atha Cliath, Eire", TYPE = "Preprint", - ABSTRACT = {A covariant formulation is developed and used to derive -cross-sections for the analysis of experiments in which -polarized electrons(muons) are scattered from spin zero and -from polarized spin 1/2 targets.}} - -@ARTICLE{Garavaglia:80, - AUTHOR = "T. Garavaglia", - TITLE = "A Covariant Formulation for Polarized Electron (Muon) -Scattering on Spin-Zero and Polarized Spin-$\frac{1}{2}$ Targets", - JOURNAL = "Il Nuovo Cimento", - YEAR = 1980, VOLUME = "56A", PAGES = "121-128", - COMMENT = {{REDUCE} used in quantum mechanics.}} - -@ARTICLE{Garavaglia:84, - AUTHOR = "Theodore Garavaglia", - TITLE = "{Dirac-} and {Majorana-neutrino-mass} effects in -{neutrino-electron} elastic scattering", - JOURNAL = "Physical Review {D}", - YEAR = 1984, VOLUME = 29, NUMBER = 3, PAGES = "387-392", MONTH = "February"} - -@ARTICLE{Garcia:86, - AUTHOR = "Arnaldo Garcia and Paulo Viana", - TITLE = "Weierstrass Points on Certain Non-Classical Curves", - JOURNAL = "Arch. Math.", - YEAR = 1986, VOLUME = 46, PAGES = "315-322"} - -@ARTICLE{Garrad:86, - AUTHOR = "A. D. Garrad and D. C. Quarton", - TITLE = "Symbolic Computing as a Tool in Wind Turbine Dynamics", - JOURNAL = "Journ. of Sound and Vibration", - YEAR = 1986, VOLUME = 109, NUMBER = 1, PAGES = "65-78", - COMMENT = {{REDUCE} as a tool in turbine design, in particular present a -program for part of a stability analysis for a turbine tower.}} - -@ARTICLE{Gastmans:79, - AUTHOR = "R. Gastmans and A. van Proeyen and P. Verbaeten", - TITLE = "Symbolic Evaluations of Dimensionally Regularized {Feynman} -Diagrams", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1979, VOLUME = 18, PAGES = "201-203", - ABSTRACT = {A modification of the symbolic and algebraic manipulation -program {REDUCE} is reported which allows the treatment of vector and gamma -algebra in an arbitrary number of dimensions.}} - -@TECHREPORT{Gatermann:90, - AUTHOR = "Karin Gatermann", - TITLE = "Gruppentheoretische {Konstruktion} von symmetrischen -{Kubaturformeln}", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1990, TYPE = "Preprint", NUMBER = "TR 90-1", MONTH = "January"} - -@InProceedings{Gatermann90a, - author = "Karin Gatermann", - title = "Symbolic solution of polynomial equation systems with - symmetry", - booktitle = "Proceedings of the 1990 International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "112-119", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Gatermann:91, - AUTHOR = "Karin Gatermann and Andreas Hohmann", - TITLE = "Symbolic Exploitation of Symmetry in Numerical Pathfollowing", - JOURNAL = "IMPACT of Computing in Science and Engineering", - YEAR = 1991, MONTH = "December", VOLUME = 3, NUMBER = 4, - PAGES = "330-365", - ABSTRACT = {{Parameter-dependent} systems of nonlinear equations with -symmetry are treated by a combination of symbolic and numerical computations. -In the symbolic part of the algorithm the complete analysis of the symmetry -occurs, and it is here where symmetrical normal forms, symmetry reduced -systems, and block diagonal Jacobians are computed. Given a particular -problem, the symbolic algorithm can create and compute through the list of -possible bifurcations thereby forming a {so-called} tree of decisions -correlated to the different types of symmetry breaking bifurcation points. -The remaining part of the algorithm deals with the numerical pathfollowing -based on the implicit reparametrisation as suggested and worked out by -{Deuflhard/Fiedler/Kunkel}. The symmetry preserving bifurcation points are -computed using recently developed augmented systems incorporating the use -of symmetry.}} - -@INPROCEEDINGS{Gatermann:91a, - AUTHOR = "Karin Gatermann", - TITLE = "Mixed symbolic-numeric solution of symmetrical nonlinear systems", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - ORGANIZATION = "ACM", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "431-432", - YEAR = 1991, - ABSTRACT = {The mixed symbolic-numeric algorithm {SYMCON} for the fully -automatical treatment of equivariant systems is presented. The global -aspects of the theory of Vanderbauwhede for these systems are viewed with -regard to the full bifurcation scenario containing solution paths with -different isotropy groups and symmetry preserving and symmetry breaking -bifurcation points. The advanced exploitation of symmetry in the numerical -computations causes an comprehensive symmetry analysis and complicated -organization of numerical work which is done by the symbolic part of the -algorithm.}} - -@TECHREPORT{Gatermann:91b, - AUTHOR = "Karin Gatermann and Andreas Hohmann", - TITLE = "Hexagonal Lattice Dome--Illustration of a Nontrivial Bifurcation -Problem", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1991, MONTH = "July", TYPE = "Preprint", NUMBER = "SC-91-8"} - ABSTRACT = {The deformation of a hexagonal lattice dome under an external -load is an example of a parameter dependent system which is equivariant -under the symmetry group of a regular hexagon. In this paper the mixed -symbolic-numerical algorithm SYMCON is applied to analyze its steady state -solutions automatically showing their different symmetry and stability -properties.}} - -@TECHREPORT{Gatermann:92, - AUTHOR = "Karin Gatermann", - TITLE = "Computation of Bifurcation Graphs", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1992, MONTH = "June", TYPE = "Preprint", NUMBER = "SC-92-13"} - ABSTRACT = {The numerical treatment of equivariant parameter-dependent -nonlinear equation systems, and even more its automation requires the -intensive use of group theory. This paper illustrates the group theoretic -computations which are done in the preparation of the numerical computations. -The bifurcation graph which gives the bifurcation subgroups is determined -from the interrelationship of the irreducible representations of a group -and its subgroups. The Jacobian is transformed to block diagonal -structure using a modification of the transformation which transforms to -block diagonal structure with respect to a supergroup. The principle of -conjugacy is used everywhere to make symbolic and numerical computations -even more efficient. Finally, when the symmetry reduced problems and -blocks of Jacobian matrices are evaluated numerically, the fact that the -given representation is a quasi-permutation representation is exploited -automatically.}} - -@TECHREPORT{Gatermann:93, - AUTHOR = "Karin Gatermann and Bodo Werner", - TITLE = "Group Theoretical Mode Interactions with Different Symmetries", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1993, MONTH = "January", TYPE = "Preprint", NUMBER = "SC-93-3"} - ABSTRACT = {In two-parameter systems two symmetry breaking bifurcation -points of different types coalesce generically within one point. This causes -secondary bifurcation points to exit. The aim of this paper is to -understand this phenomenon with group theory and the innerconnectivity of -irreducible representations of supergroup and subgroups. Colored pictures -of examples are included.}} - -@TECHREPORT{Gatermann:93a, - AUTHOR = "Karin Gatermann and Bodo Werner", - TITLE = "Secondary {Hopf} bifurcation caused by steady-state steady-state -mode interaction", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1993, MONTH = "July", TYPE = "Preprint", NUMBER = "SC-93-16", - ABSTRACT = {In two-parameter systems with symmetry two steady state -bifurcation points of different symmetry types coalesce generically within -one point. Under certain group theoretic conditions involving the action -of the symmetry group on the kernels, we show that secondary Hopf -bifurcation is borne by the mode interaction. We explain this phenomenon -by using linear representation theory. For motivation an example with -$D_{3}$-symmetry is investigated where the main properties causing the Hopf -bifurcation are summarized.}} - -@TECHREPORT{Gatermann:94, - AUTHOR = "Karin Gatermann", - TITLE = "Semi-invariants, equivariants and algorithms", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1994, MONTH = "May", TYPE = "Preprint", NUMBER = "SC-94-11", - ABSTRACT = {The results from invariant theory and the results for semi- -invariants and equivariants are summarized in a way suitable for the -combination with G{r\"o}bner basis computation. An algorithm for the -determination of fundamental equivariants using projections and a -Poinca\'{r}e series is described. Secondly, an algorithm is given for the -representation of an equivariant in terms of the fundamental equivariants. -Several ways for the exact determination of zeros of equivariant systems -are discussed.}} - -@TECHREPORT{Gatermann:95, - AUTHOR = "Karin Gatermann and Reiner Lauterbach", - TITLE = "Automatic classification of normal forms", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1995, MONTH = "February", TYPE = "Preprint", NUMBER = "SC-95-3", - ABSTRACT = {The aim of this paper is to demonstrate a specific application -of Computer Algebra to bifurcation theory with symmetry. The -classification of different bifurcation phenomena in case of several -parameters is automated, based on a classification of G{r\"o}bner bases of -possible tangent spaces. The computations are performed in new coordinates -of fundamental invariants and fundamental equivariants, with the induced -weighted ordering. In order to justify the approach the theory of -intrinsic modules is applied. Results for the groups $D_{3},Z_{2}$, and -$Z_{2} x Z_{2}$ demonstrate that the algorithm works independent of the -group and that new results are obtained.}} - -@INPROCEEDINGS{Gates:85, - AUTHOR = "Barbara L. Gates and J. A. van Hulzen", - TITLE = "Automatic Generation of Optimized Programs", - BOOKTITLE = "Proc. {EUROCAL} '85", YEAR = 1985, - MONTH = "April"} - -@ARTICLE{Gates:85a, - AUTHOR = "Barbara L. Gates", - TITLE = "Gentran: An Automatic Code Generation Facility -for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "24-42", MONTH = "August"} - -@TECHREPORT{Gates:85b, - AUTHOR = "Barbara L. Gates", - TITLE = "Gentran User's Manual - {REDUCE} Version", - INSTITUTION = "Twente University of Technology, Department of -Computer Science, The Netherlands", TYPE = "Memorandum", - YEAR = 1985, NUMBER = "INF-85-11", MONTH = "June"} - -@TECHREPORT{Gates:85c, - AUTHOR = "Barbara L. Gates", - TITLE = "Gentran Design and Implementation, {REDUCE} Version", - INSTITUTION = "Twente University of Technology, Department of Computer -Science, The Netherlands", YEAR = 1985, TYPE = "Memorandum", - NUMBER = "INF-85-12", MONTH = "August"} - -@INPROCEEDINGS{Gates:86, - AUTHOR = "Barbara L. Gates", - TITLE = "A Numerical Code Generation Facility for {REDUCE}", - BOOKTITLE = "Proc. {SYMSAC} '86", - YEAR = 1986, PAGES = "94-99", MONTH = "July"} - -@TECHREPORT{Gebauer:85, - AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", - TITLE = "A Fast Variant of {Buchberger's} Algorithm", - INSTITUTION = "Universit{\"a}t Heidelberg and -Fernuniversit{\"a}t {Hagen}", YEAR = 1985, MONTH = "October"} - -@ARTICLE{Gebauer:88, - AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", - TITLE = "On an Installation of {Buchberger's} Algorithm", - JOURNAL = "J. Symbolic Computation", - YEAR = 1988, VOLUME = 6, NUMBER = "2 and 3", PAGES = "275-286"} - -@ARTICLE{Generalis:84, - AUTHOR = "S. C. Generalis and D. J. Broadhurst", - TITLE = "The heavy-quark expansion and {QCD} sum rules for light quarks", - JOURNAL = "Physics Lett. B", - YEAR = 1984, VOLUME = 139, PAGES = "85-89"} - -@ARTICLE{George:68, - AUTHOR = "D. J. George", - TITLE = "A Covariant Theory of the Disintegration of the -Deuteron by Pions and Photons at High Energy", - JOURNAL = "Phys. Rev.", - YEAR = 1968, VOLUME = 167, PAGES = "1357-1364"} - -@ARTICLE{Gerdt:80, - AUTHOR = "V. P. Gerdt", - TITLE = "Analytical Calculations in High Energy Physics by Computer", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1980, VOLUME = 20, PAGES = "85-90", - COMMENT = {A review, comparing {SCHOONSCHIP, ASHMEDAI and REDUCE-2}.}} - -@ARTICLE{Gerdt:80a, - AUTHOR = "V. P. Gerdt and O. V. Tarasov and D. V. Shirkov", - TITLE = "Analytical Calculations on Digital Computers for Applications -in Physics and Mathematics", - JOURNAL = "Sov. Phys. USP", - YEAR = 1980, VOLUME = 23, PAGES = "59-77", - COMMENT = {General review of applications in many languages.}} - -@TECHREPORT{Gerdt:80b, - AUTHOR = "V. P. Gerdt", - TITLE = "On Global Structure of the General Solution of the -{Chew-Low} Equations", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1980, TYPE = "Preprint", NUMBER = "P2-80-436"} - -@ARTICLE{Gerdt:85, - AUTHOR = "V. P. Gerdt and A. B. Shvachka and A. Yu. Zharkov", - TITLE = "Computer Algebra Application for Classification of -Integrable Non-Linear Evolution Equations", - JOURNAL = "J. Symb. Comp.", - YEAR = 1985, VOLUME = 1, PAGES = "101-107"} - -@TECHREPORT{Gerdt:85a, - AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev -and R. P. Roussev", - TITLE = "Calculation of the Matrix Elements of the -{Hamiltonian} of the Interacting Vector Boson Model Using -Computer Algebra - Basic Concepts of the Interacting Vector -Boson Model and Matrix Elements of the {SU(3)-Quadrupole} -Operator", - INSTITUTION = "Institute for Nuclear Research and Nuclear -Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", - YEAR = 1985, NUMBER = "E4-85-262"} - -@TECHREPORT{Gerdt:85b, - AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev", - TITLE = "Calculation of the Matrix Elements of the -{Hamiltonian} of the Interacting Vector Boson Model Using -Computer Algebra - Matrix Elements of the {Hamiltonian} and -Some {U(6)-Clebsch-Gordon} Coefficients", - INSTITUTION = "Institute for Nuclear Research and Nuclear -Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", - YEAR = 1985, NUMBER = "E4-85-263"} - -@TECHREPORT{Gerdt:85c, - AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev -and R. P. Roussev", - TITLE = "Calculation of the Matrix Elements of the -{Hamiltonian} of the Interacting Vector Boson Model -Using Computer Algebra - Matrix Elements of the {Hamiltonian} - -Analytical Results", - INSTITUTION = "Institute for Nuclear Research and Nuclear -Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", - YEAR = 1985, NUMBER = "E4-85-264"} - -@TECHREPORT{Gerdt:86, - AUTHOR = "V. P. Gerdt and M. G. Meshcheryakov and D. V. Shirkov", - TITLE = "Computers in Theoretical Physics", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1986, NUMBER = "P2-86-848", - ABSTRACT = {The paper is written on the basis of the report presented by -two authors ({M.G. Meshcheryakov} and {D.V. Shirkov}) at the 60th session -of the JINR Scientific Council, June 5, 1986. It reviews the usage of -computer mathematics in theoretical and mathematical investigations -carried out in the Joint Institute. Recommendations are given on further -development of the JINR Computer Center in accordance with the program of -theoretical researches in nearest Five-Year Plan.}} - -@INPROCEEDINGS{Gerdt:87, - AUTHOR = "V. P. Gerdt and A. B. Shabat and S. I. Svinolupov -and A. Yu. Zharkov", - TITLE = "Computer Algebra Application for Investigating -Integrability of Nonlinear Evolution Systems", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "81-92", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Gerdt:87a, - AUTHOR = "V. P. Gerdt and N. A. Kostov and Z. T. Kostova", - TITLE = "Computer Algebra and Computation of {Puiseux} Expansions of -Algebraic Functions", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "206-207", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Gerdt:89, - AUTHOR = "V. P. Gerdt and N. A. Kostov", - TITLE = "Computer Algebra in the theory of Ordinary Differential Equations -of Halphen type", - BOOKTITLE = "Proc. Computers and Mathematics '89", - EDITOR = "E. Kaltofen and S. M. Watt", - YEAR = 1989, PAGES = "279-288", PUBLISHER = "Springer-Verlag, New York"} - -@TECHREPORT{Gerdt:89a, - AUTHOR = "V. P. Gerdt and Z. T. Kostova and N. A. Kostov and I. P. Yudin", - TITLE = "Algebraic-Numeric Calculations of Proton Trajectories in Bending -Magnets of Synchrotron Accelerator", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1989, TYPE = "Preprint", NUMBER = "E11-89-755", - ABSTRACT = {We study a solution of nonlinear differential equation of the -second degree which describes the trajectories of the charged particles in -the fully inhomogeneous field of cyclic accelerator. We give the clear -mathematical statement of the problem and algorithm of solving it. We -realize this algorithm on the Computer Algebra System {REDUCE 3.2}. Our -algorithm is based both on the existence of exact solution in terms of -hyperelliptic integral and on the existence of power series solution of -specific inversion problem. We use the known {REDUCE} procedures of -operation on generalized power series. Using the {FORTRAN} code we give the -numerical analysis of these series in the close relation to the concrete -physical situation. We apply our results to the beam dynamics modeling -of the protons in the bending magnets in synchrotron accelerator.}} - -@TECHREPORT{Gerdt:89b, - AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", - TITLE = "Solving the Polynomial System Arising in Classification of -Integrable Coupled {KdV-like} Systems", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1989, TYPE = "Preprint", NUMBER = "P5-89-231", - ABSTRACT = {A system of algebraic equations which follows from the -necessary integrability conditions for the {ten-parametric} family of -coupled {KdV-like} nonlinear evolution systems is considered. The method -for solving this system based on the structure of the canonical local -conservation laws densities is described. Computer algebra system -{REDUCE} was used to find all the solutions. As a result we obtain the -complete list of integrable coupled {KdV-like} systems.}} - -@InProceedings{Gerdt90, - author = "V. P. Gerdt and A. Yu. Zharkov", - title = "Computer Generation of Necessary Integrability - Conditions for Polynomial-Nonlinear Evolution Systems", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "250-254", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@InProceedings{Gerdt90a, - author = "Vladimar P. Gerdt and Nikolai V. Khutornoy and Alexey - Yu. Zharkov", - title = "Solving Algebraic Systems which arise as Necessary - Integrability Conditions for Polynomial-Nonlinear - evolution Equations", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "299", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Gerdt:90b, - AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", - TITLE = "Computer Classification of Integrable Coupled {KdV-Like} Systems", - JOURNAL = "J. Symb. Comp.", - YEAR = 1990, VOLUME = 10, PAGES = "203-207", - ABSTRACT = {The foundations of the symmetry approach to the classification -problem of integrable {non-linear} evolution systems are briefly described. -Within the framework of the symmetry approach the {ten-parametric} family -of the third order {non-linear} evolution coupled {KdV-like} systems is -investigated. The necessary integrability conditions lead to an -{over-determined} {non-linear} algebraic system. To solve that system an -effective method based on its structure has been used. This allows us -to obtain the complete list of integrable systems of a given type. All -computation has been completed on the basis of computer algebra systems -{FORMAC} and {REDUCE}.}} - -@INPROCEEDINGS{Gerdt:90c, - AUTHOR = "V. P. Gerdt and N. A. Kostov and A. Yu. Zharkov", - TITLE = "Nonlinear Evolution Equations and Solving Algebraic Systems: -The Importance of Computer Algebra", - YEAR = 1990, - BOOKTITLE = "International Conference on Solitons and Its Applications", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "120-128"} - ABSTRACT = {In the present paper we study the application of computer -algebra to solve the nonlinear polynomial systems which arise in -investigation of nonlinear evolution equations. We consider several -systems which are obtained in classification of integrable nonlinear -evolution equations with uniform rank. Other polynomial systems are related -with the finding of algebraic curves for finite-gap elliptic potentials of -{Lame} type and generalizations. All systems under consideration are -solved using the method based on construction of the {Groebner} basis for -corresponding polynomial ideals. The computations have been carried out -using computer algebra systems.}} - -@INPROCEEDINGS{Gerdt:91, - AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", - TITLE = "Lie-{B{\"a}cklund} Symmetries of Coupled Nonlinear -{Schr{\"o}dinger} Equations", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "313-314", - YEAR = 1991} - -@TECHREPORT{Gerdt:91a, - AUTHOR = "V. P. Gerdt and P. Tiller", - TITLE = "A {Reduce} Program for Symbolic Computation of {Puiseux} -Expansions", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1991, TYPE = "Preprint", NUMBER = "E5-91-401"} - ABSTRACT = {The program is described for computation of Puiseux expansions -of alebraic functions. The Newton polygon method is used for construction -of initial coefficients of all the Puiseux series at the given point. The -program is written in computer algebra language Reduce. Some illustrative -examples are given.}} - -@TECHREPORT{Gerdt:91b, - AUTHOR = "V. P. Gerdt", - TITLE = "Computer Algebra Tools for Higher Symmetry Analysis of Nonlinear -Evolution Equations", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1991, TYPE = "Preprint", NUMBER = "E5-91-402"} - ABSTRACT = {This paper presents a computer-aided approach and a software -package for symbolic algebraic computation to solve the problem of -verifying the existence of the canonical Lie-B{\"a}cklund symmetries -for multicomponent quasilinear evolution equations with polynomial- -nonlinearity and computing a given order symmetry if any. In the presence -of arbitrary numerical parameters the problem is reduced to investigation -and solving of nonlinear algebraic equations in those parameters. It is -remarkable that in all the known cases these algebraic equations are -completely solvable by the Gr{\"o}bner basis technique implemented as a part -of the software package.}} - -@InProceedings{Gerdt:93, - author = "V. Gerdt", - title = "Homogeneity of Integrability Conditions for Multiparametric - Families of Polynomial-Nonlinear Evolution Equations", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "181-186", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - comment = {A canonical form algorithm for quantities with locally scoped - variables (e.g. Summation convention, tensor products) is - developed in a {REDUCE} package.} -} - -@ARTICLE{Gervois:74, - AUTHOR = "A Gervois and Y. Pomeau", - TITLE = "Logarithmic Divergence in the Virial Expansion -of Transport Coefficients of Hard Spheres", - JOURNAL = "Phys. Rev. A", - YEAR = 1974, VOLUME = 9, PAGES = "2196-2213"} - -@TECHREPORT{Gladd:82, - AUTHOR = "N. T. Gladd", - TITLE = "Computational Aspects of Research on the -Relativistic {Whistler} Instability", - INSTITUTION = "Jaycor", YEAR = 1982, - NUMBER = "J530-82-020", MONTH = "June"} - -@INPROCEEDINGS{Gladkih:83, - AUTHOR = "I. Gladkih and E. Lovas", - TITLE = "On the Application of Computer Algebra Languages in the {Central -Research Institute for Physics}", - BOOKTITLE = "Proceedings of the International Conference on Systems and -Techniques of Analytical Computing and Their Applications in Theoretical -Physics, {D11-83-511, Dubna}", YEAR = 1983} - -@INPROCEEDINGS{Gladkih:84, - AUTHOR = "I. Gladkih and M. Zimanyi", - TITLE = "Comparison of systems for Symbolic Computing in use in the -{Central Research Institute for Physics} (in {Russian})", - BOOKTITLE = "Proceedings of the International Conference on {Computer-Based} -Scientific Research, Plovdiv", YEAR = 1984} - -@ARTICLE{Goldman:89, - AUTHOR = "V. V. Goldman and J. A. van Hulzen", - TITLE = "Automatic Code Vectorization of Arithmetic Expressions by -Bottom-Up Structure Recognition", - JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora -and J. Fitch", - YEAR = 1989, PAGES = "119-132", PUBLISHER = "Academic Press, London"} - -@INPROCEEDINGS{Golley, - AUTHOR = "Bruce W. Golley and Joseph Petrolito", - TITLE = "An Alternative Finite Strip Technique for the Static Analysis of -Single-Span, Multi-Span and Continuous Plates", - YEAR = 1982, - BOOKTITLE = "Proc. International Conference on -Finite Element Methods"} - -@ARTICLE{Good:75, - AUTHOR = "D. Good and R. L. London and W. W. Bledsoe", - TITLE = "An Interactive Program Verification System", - JOURNAL = "Sigplan Notices", - YEAR = 1975, VOLUME = 10, NUMBER = 6, PAGES = "482-492"} - -@ARTICLE{Goto:77, - AUTHOR = "E. Goto and T. Soma", - TITLE = "{MOL} (Moving Objective Lens) Formulation of -Deflective Aberration Free System", - JOURNAL = "Optik", - YEAR = 1977, VOLUME = 48, PAGES = "255-270"} - -@INPROCEEDINGS{Goto:78, - AUTHOR = "E. Goto and T. Soma", - TITLE = "Electron Beam Lithography for Advanced {LSI} Fabrication", - YEAR = 1978, PAGES = "1223-1228", - BOOKTITLE = "Proc. 1978 National Computer Conference, -{AFIPS} Press, New Jersey"} - -@ARTICLE{Gould:84, - AUTHOR = "H. W. Gould and M. E. Mays", - TITLE = "Series Expansions of Means", - JOURNAL = "Journ. of Mathematical Analysis and Applications", - YEAR = 1984, VOLUME = 101, NUMBER = 2, PAGES = "611-621", - MONTH = "July"} - -@ARTICLE{Graebe:93, - AUTHOR = "Hans-Gert Gr{\"a}be", - TITLE = "On Lucky Primes", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, VOLUME = 15, NUMBER = 2, PAGES = "199-209", MONTH = "February", - COMMENT = {Winkler (1988) and Pauer (1992) present algorithms for a Hensel -lifting of a modular Gr{\"o}bner basis over lucky primes to a rational -one. They have to solve a linear system with modular polynomial entries -that requires another (modular) Gr{\"o}ner basis computation. -After an extension of luckiness to arbitrary (commutative noetherian) base -rings we show in this paper that for a homogeneous polynomial ideal I one -lift not only only its Gr{\"o}bner basis but also a homogeneous basis of -its syzygy module. The same result holds for arbitrary ideals and -liftings from Z/p to Q. Moreover the same lifting can be obtained from a -true Gro{\"o}bner trace by linear algebra over Q only. Parallel modular -techniques allow to find such a true Gro{\"o}bner and a lucky prime with -high probability. -All these results generalize in an obvious way to homogeneous modules -generated by the rows of matrices with polynomial entries. Since -luckiness can be weakened to a condition that transfers from I to higher -syzygy modules the lifting theorem generalizes to a lifting theorem for -the resolution of I.}} - -@PHDTHESIS{Gragert:81, - AUTHOR = "Peter Gragert", - TITLE = "Symbolic Computations in Prolongation Theory", - SCHOOL = "Twente University of Technology, The Netherlands", - YEAR = 1981} - -@BOOK{Grammaticos, - AUTHOR = "B. Grammaticos and A. Voros", - TITLE = "Semi-Classical Approximations for Nuclear -{Hamiltonians}: {II}. {Spin-dependent} Potentials", - ABSTRACT = {A systematic semi-classical expansion procedure for physical -quantities in nuclei, based on the Thomas-Fermi approximation -to the Hartree-Fock equations and constructed in a previous -work, is extended here to the realistic case where the -effective one-body {Hamiltonian} for nucleons contains -spin-dependent terms.}} - -@TECHREPORT{Grammaticos:78, - AUTHOR = "B. Grammaticos and A. Voros", - TITLE = "Semi-classical Approximations for Nuclear -{Hamiltonians} {I}. {Spin-independent} Potentials", - INSTITUTION = "CEN, Saclay", YEAR = 1978, TYPE = "Preprint", - NUMBER = "DPh-T/78-75", MONTH = "August", - COMMENT = {Submitted to Annals of Physics}, - ABSTRACT = {A systematic procedure for calculating semi-classical -expansions of physically interesting quantities is presented.}} - -@ARTICLE{Grammaticos:85, - AUTHOR = "B. Grammaticos and B. Dorizzi and A. Ramani and J. Hietarinta", - TITLE = "Extending integrable {Hamiltonian} systems from 2 to {N} -dimensions", - JOURNAL = "Phys. Lett.", - YEAR = 1985, VOLUME = "109A", PAGES = "81-84", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Gray:90, - AUTHOR = "N. Gray and D. J. Broadhurst and W. Grafe and K. Schilcher", - TITLE = {Three-loop relation of quark $\overline{\rm MS}$ and pole masses}, - JOURNAL = "Zeitschrift {f\"{u}r} Physik C", - YEAR = 1990, VOLUME = 48, PAGES = "673-679"}} - -@ARTICLE{Greenland:84, - AUTHOR = "P. T. Greenland", - TITLE = "Comparison Between Phase Diffusion and Random Telegraph Signal -Models of Laser Bandwidth", - JOURNAL = "Journ. Phys. B", - YEAR = 1984, VOLUME = 17, PAGES = "1919-1925", - COMMENT = {{REDUCE} calculation of correlation matrix for molecular physics. -Tedious, but simple result.}} - -@ARTICLE{Grimm, - AUTHOR = "R. Grimm and H. K{\"u}hnelt", - TITLE = "Using {REDUCE} in Problems of Supersymmetry and Supergravity", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1980, VOLUME = 20, PAGES = "77", - COMMENT = {Describes how {REDUCE} may be used with advantage in tedious -calculations of supersymmetry and supergravity.}} - -@INPROCEEDINGS{Griss:74, - AUTHOR = "M. L. Griss", - TITLE = "The Algebraic Solution of Large Sparse Systems of Linear -Equations Using {REDUCE} 2", - YEAR = 1974, PAGES = "105-111", - BOOKTITLE = "Proc. ACM 74", - ABSTRACT = {This paper discusses some of the problems encountered during the -solution of a large system of sparse linear equations with algebraic -coefficients, using {REDUCE} 2.}} - -@ARTICLE{Griss:74a, - AUTHOR = "M. L. Griss", - TITLE = "The Algebraic Solution of Sparse Linear Systems Via Minor -Expansion", - JOURNAL = "ACM TOMS 2", - YEAR = 1976, PAGES = "31-49", - ABSTRACT = {An improved algorithm for computing the determinants of a (large) -sparse matrix of polynomials is described.}} - -@INPROCEEDINGS{Griss:75, - AUTHOR = "Martin L. Griss", - TITLE = "The {REDUCE} System for Computer Algebra", - BOOKTITLE = "Proc. ACM 75", - YEAR = 1975, PAGES = "4-5", - ABSTRACT = {A brief description of {REDUCE} is presented.}} - -@INPROCEEDINGS{Griss:76, - AUTHOR = "Martin L. Griss", - TITLE = "The Definition and Use of Data-Structures in {REDUCE}", - BOOKTITLE = "Proc. SYMSAC 76", - YEAR = 1976, PAGES = "53-59", - ABSTRACT = {This paper gives a brief description and motivation of the mode -analyzing and data-structuring extensions to the algebraic language -{REDUCE}.}} - -@INPROCEEDINGS{Griss:76a, - AUTHOR = "Martin L. Griss", - TITLE = "An Efficient Sparse Minor Expansion Algorithm", - BOOKTITLE = "Proc. ACM 76", - YEAR = 1976, PAGES = "429-434", - ABSTRACT = {An improved algorithm for computing the minors of a (large) -sparse matrix of polynomials is described, with emphasis on efficiency and -optimal ordering. A possible application to polynomial resultant -computation is discussed.}} - -@INPROCEEDINGS{Griss:77, - AUTHOR = "Martin L. Griss", - TITLE = "Efficient Expression Evaluation in Sparse Minor -Expansion, Using Hashing and Deferred Evaluation", - YEAR = 1977, PAGES = "169-172", - BOOKTITLE = "Proc. 10th Hawaii International Conference on -Systems Sciences, Western Periodicals, Calif.", - ABSTRACT = {Efficient computation of the determinant of a matrix with -symbolic entries using minor expansion requires careful control of expression -evaluation. The use of hashing and deferred evaluation to avoid -excess computation is explored.}} - -@ARTICLE{Griss:77a, - AUTHOR = "M. L. Griss", - TITLE = "Efficient Recursive Minor Expansion", - JOURNAL = "ACM TOMS", - YEAR = 1977, - ABSTRACT = {The use of a "memo" facility to develop an efficient recursive -minor expansion algorithm (RMEM) is discussed. The method is simple and -efficient, and can be implemented as an interesting non-trivial -recursive procedure. The method is particularly attractive for -sparse symbolic matrices, and can also be used to enhance other -minor expansion methods developed for sparse symbolic matrices.}} - -@ARTICLE{Griss:78, - AUTHOR = "Martin L. Griss", - TITLE = "Using an Efficient Sparse Minor Expansion Algorithm to Compute -Polynomial Subresultants and the Greatest Common Denominator", - JOURNAL = "IEEE Trans on Computers", - YEAR = 1978, VOLUME = "C-27", NUMBER = 10, PAGES = "945-950", - ABSTRACT = {In this paper, the use of an efficient sparse minor expansion -method to directly compute the subresultants needed for the {GCD} of two -polynomials is described. The sparse minor expansion method (applied -either to Sylvester's or Bezout's matrix) naturally computes the -coefficients of the subresultants in the order corresponding to -a {PRS}, avoiding wasteful recomputation as much as possible. It is -suggested that this is an efficient method to compute the Resultant -and {GCD} of Sparse Polynomials.}} - -@INPROCEEDINGS{Griss:78a, - AUTHOR = "Martin L. Griss and Robert R. Kessler", - TITLE = "{REDUCE}/1700: A Micro-coded Algebra System", - YEAR = 1978, VOLUME = 11, PAGES = "130-138", - BOOKTITLE = "Proc. Micro, {IEEE}", - ABSTRACT = {In this paper, we report on the status of an ongoing project -aimed at producing a micro-coded Algebra machine.}} - -@ARTICLE{Griss:79, - AUTHOR = "Martin L. Griss and Anthony C. Hearn", - TITLE = "Portable {LISP} Compiler", - JOURNAL = "Software - Practice and Experience", VOLUME = 11, - PAGES = "541-605", YEAR = 1979, - ABSTRACT = {This paper describes the development of a portable {LISP} -compiler in the sense that only Standard {LISP} functions are used in its -definition and the output is a sequence of standard macro calls -easily implementable on current computers.}} - -@TECHREPORT{Griss:79a, - AUTHOR = "Martin L. Griss and Robert R. Kessler", - TITLE = "A Micro-programmed Implementation of {Standard} {LISP} and -{REDUCE} on the {Burroughs B1700/B1800} Computer", - INSTITUTION = "University of Utah", YEAR = 1979, TYPE = "Report", - MONTH = "February", - ABSTRACT = {This paper describes the implementation of a microcoded {LISP} -"machine" (the MTLISP) for the Burroughs B1700/B1800 computers. -This interpreter supports a complete Standard {LISP} and {REDUCE} -Algebra system, as well as a variety of experimental {LISP-like} -systems.}} - -@INPROCEEDINGS{Grozin:83, - AUTHOR={A. G. Grozin}, - TITLE={Calculation of one-loop diagrams of {$1 \to 2$} decays with {REDUCE}}, - BOOKTITLE={Proc. Int. Conf. on Computer Algebra in Theoretical Physics, -Dubna}, - YEAR = 1983, PAGES = {226-231}, - COMMENT = {To appear in Phys. Lett. B}} - -@TECHREPORT{Grozin:88, - AUTHOR = "A. G. Grozin", - TITLE = "Solving Physical Problems with {REDUCE.} {1. REDUCE} -Language {2. Classical} Nonlinear Oscillator", - INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, -{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-115", - ABSTRACT = {This preprint is the first part of the problem book on using -{REDUCE} in physics. It contains many examples useful for the -construction of programs for solving physical problems of very -different nature. This part contains examples illustrating {REDUCE} -language (sect. 1) and the problem of classical nonlinear -oscillator (sect. 2). To be published (with additions) as a book with -"Nauka" publishers, Moscow.}} - -@TECHREPORT{Grozin:88a, - AUTHOR = "A. G. Grozin", - TITLE = "Solving Physical Problems with {REDUCE.} {3. Nonlinear} -Water Waves {4. Calculation} of the Curvature Tensor {5. Angular} -Momentum Addition", - INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, -{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-136", - ABSTRACT = {This preprint is the second part of the problem book on using -{REDUCE} in physics. It contains many examples useful for the construction of -programs for solving physical problems of very different nature. This -part contains the problem of nonlinear water waves (sect. 3), the -calculation of the curvature tensor (sect. 4) and angular momentum -addition (sect. 5).}} - -@TECHREPORT{Grozin:88b, - AUTHOR = "A. G. Grozin", - TITLE = "Solving Physical Problems with {REDUCE.} {6. Quantum} -Nonlinear Oscillator {7. Rotator} in a Weak Field {8. Radiative} -Transitions in Charmonium", - INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, -{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-140", - ABSTRACT = {This preprint is the last part of the problem book on using -{REDUCE} in physics. It contains many examples useful for the construction of -programs for solving physical problems of very different nature. This -part contains the problem of quantum nonlinear oscillator (sect. 6), -rotator in a weak field (sect. 7) and radiative transitions in -charmonium (sect. 8).}} - -@TECHREPORT{Grozin:90, - AUTHOR = {A. G. Grozin}, - TITLE = {{REDUCE} in elementary particle physics. {Introduction}}, - INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, - YEAR = 1990, NUMBER = {INP 90-42}, - COMMENT = {These 5 preprints together with the previous 3 will be published -as a book "Solving physical problems with REDUCE"}} - -@TECHREPORT{Grozin:90a, - AUTHOR = {A. G. Grozin}, - TITLE = {{REDUCE} in elementary particle physics. {Quantum electrodynamics}}, - INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, - YEAR = 1990, NUMBER = {INP 90-71}} - -@TECHREPORT{Grozin:90b, - AUTHOR = {A. G. Grozin}, - TITLE = {{REDUCE} in elementary particle physics. {Quantum chromodynamics}}, - INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, - YEAR = 1990, NUMBER = {INP 90-62}} - -@TECHREPORT{Grozin:91, - AUTHOR = {A. G. Grozin}, - TITLE = {{REDUCE} in elementary particle physics. {Weak interactions}}, - INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, - YEAR = 1991, NUMBER = {INP 91-56}} - -@TECHREPORT{Grozin:91a, - AUTHOR = {A. G. Grozin}, - TITLE = {{REDUCE} in elementary particle physics. {Radiative corrections}}, - INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, - YEAR = 1991, NUMBER = {INP 91-46}} - -@ARTICLE{Gunion:72, - AUTHOR = "J. F. Gunion and S. J. Brodsky and R. Blankenbecler", - TITLE = "Composite Theory of Large Angle Scattering and New -Tests of Parton Concepts", - JOURNAL = "Phys. Lett.", - YEAR = 1972, VOLUME = "39B", PAGES = "649-653"} - -@TECHREPORT{Gunion:73, - AUTHOR = "J. F. Gunion and S. J. Brodsky and R. Blankenbecler", - TITLE = "Large Angle Scattering and the Interchange Force", - INSTITUTION = "SLAC", - YEAR = 1973, TYPE = "Report", NUMBER = "SLAC-PUB-1183"} - -@ARTICLE{Gunion:85, - AUTHOR = "J. F. Gunion and Z. Kunszt", - TITLE = "Improved Analytic Techniques for Tree Graph Calculations and -the $g g q {\bar q} l {\bar l}$ subprocess", - JOURNAL = "Phys. Lett.", - YEAR = 1985, VOLUME = "161B", PAGES = "333-340"} - -@ARTICLE{Hadinger:87, - AUTHOR = "G. Hadinger and Y. S. Tergimen", - TITLE = "Recurrence Relations for the {Dunham} Coefficients and Analytic -Expressions of the Diagonal Radial Matrix Elements for an Anharmonic -Oscillator", - JOURNAL = "Journ. Chem. Phys.", - YEAR = 1987, VOLUME = 87, NUMBER = 4, PAGES = "2143-2150", - COMMENT = {"As an illustrative application, all the set of $Y_{n}$ -coefficients previously published are found again by using the -computer algebraic manipulation language {REDUCE}. A number of diagonal -matrix elements of {CO, HBr and HCl} have been symbolically computed and -compared with previous available results." Their method depends on -some algebraic manipulation, and the main point is that automation -gives a simpler formulation of the problem.}} - -@ARTICLE{Handy:87, - AUTHOR = "N. C. Handy", - TITLE = "The Derivation of Vibration-Rotation Kinetic Energy Operators, -in Internal Coordinates", - JOURNAL = "Mol. Phys.", - YEAR = 1987, VOLUME = 61, PAGES = "207-223", - COMMENT = {{REDUCE USED} to produce a straightforward method for the -derivation of kinetic energy operators in molecular vibration-rotation. He -notes in the introduction "The purpose of this paper is to derive a simple and -straightforward procedure for which it is possible to make the -computer do all the hard work. After many years of investigating this -problem, this author believes that this must be the reliable way to -proceed."}} - -@PHDTHESIS{Harper:87, - AUTHOR = "David Harper", - TITLE = "Dynamics of the Outer Satellites of Saturn", - SCHOOL = "Univ. of Liverpool, England", - YEAR = 1987} - -@TECHREPORT{Harper:89, - AUTHOR = "David Harper and Chris Wooff and David Hodgkinson", - TITLE = "A Guide to Computer Algebra Systems", - INSTITUTION = "Computer Laboratory, The University of Liverpool, -Liverpool, England", YEAR = 1989, MONTH = "September", TYPE = "Report"} - -@ARTICLE{Harper:89a, - AUTHOR = "David Harper", - TITLE = "{Vector33:} A {REDUCE} Program for Vector Algebra and Calculus -in Orthogonal Curvilinear Coordinates", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1989, VOLUME = 54, NUMBER = "2 and 3", PAGES = "295-305", - MONTH = "June and July"} - -@ARTICLE{Harrington:77, - AUTHOR = "Steven J. Harrington", - TITLE = "A Symbolic Limit Evaluation Program in {REDUCE}", - YEAR = 1977, - ABSTRACT = {A program for the automatic evaluation of algebraic -limits, implemented in {MODE-REDUCE}, is described. The program -incorporates many of the techniques previously employed, including -the top-down recursive evaluation, power series expansion, and -L'Hopital's rule. It also introduces the concept of a special -algebraic form for limits.}} - -@ARTICLE{Harrington:77a, - AUTHOR = "S. J. Harrington", - TITLE = "{REDUCE} Solution to Problem \#8", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = "1977 and 1978", VOLUME = "11 and 12", NUMBER = "4 and 1", - PAGES = "7-8", MONTH = "November and February"} - -@ARTICLE{Harrington:79, - AUTHOR = "Steven J. Harrington", - TITLE = "A New Symbolic Integration System in {REDUCE}", - JOURNAL = "Comp. Journ.", - YEAR = 1979, VOLUME = 22, NUMBER = 2, PAGE = "127-131", - ABSTRACT = {A new integration system, employing both algorithmic and -pattern match integration schemes is presented. The organization of the -system differs from that of earlier programs in its emphasis on the -algorithmic approach to integration, its modularity, and its ease of -revision. The new {Norman-Risch} algorithm and its implementation at the -University of Cambridge are employed, supplemented by a powerful -collection of simplification and transformation rules. The facility for -user defined integrals and functions is also included. The program is -both fast and powerful, and can be easily modified to incorporate -anticipated developments in symbolic integration.}} - -@ARTICLE{Harrington:79a, - AUTHOR = "Steven J. Harrington", - TITLE = "A Symbolic Limit Evaluation Program in {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1979, VOLUME = 13, NUMBER = 1, PAGES = "27-31", MONTH = "February"} - -@ARTICLE{Hartley:91, - AUTHOR = "David Hartley and Robin W. Tucker", - TITLE = "A Constructive Implementation of the {Cartan-K{\"a}hler} Theory -of Exterior Differential Systems", - JOURNAL = "J. Symb. Comp.", - YEAR = 1991, VOLUME = 12, NUMBER = 6, PAGES = "655-667", - MONTH = "December", - ABSTRACT = {An efficient algorithm for the construction of a regular chain -of involutive integral elements for a general exterior differential system -is presented. It is based upon the existence theorems of the -{Cartan-}K{"\a}hler theory, and may be used to analyse partial differential -equations by formulating them as exterior differential systems.}} - -@ARTICLE{Hasenfratz:80, - AUTHOR = "Anna Hasenfratz and Peter Hasenfratz", - TITLE = "The Connection Between the Parameters of Lattice and -Continuum {QCD}", - JOURNAL = "Phys. Lett.", - YEAR = 1980, VOLUME = "93B", NUMBER = "1,2", PAGES = "165-169", - MONTH = "June"} - -@INPROCEEDINGS{Hearn:68, - AUTHOR = "Anthony C. Hearn", - TITLE = "{REDUCE}: A User-Oriented Interactive System for Algebraic -Simplification", - YEAR = 1968, PAGES = "79-90", - EDITOR = "M. Klerer and J. Reinfelds", - BOOKTITLE = "Interactive Systems for Experimental Applied Mathematics", - PUBLISHER = "Academic Press", ADDRESS = "New York"} - -@ARTICLE{Hearn:69, - AUTHOR = "A. C. Hearn and P. K. Kuo and D. R. Yennie", - TITLE = "Radiative Corrections to an Electron-Positron Scattering -Experiment", - JOURNAL = "Phys. Rev.", - YEAR = 1969, VOLUME = 187, PAGES = "2088-2096"} - -@INPROCEEDINGS{Hearn:69a, - AUTHOR = "Anthony C. Hearn", - TITLE = "The Problem of Substitution", - YEAR = 1969, PAGES = "3-19", - EDITOR = "R.G. Tobey", - BOOKTITLE = "Proc. of the 1968 Summer Institute on Symbolic Mathematical -Computation", - PUBLISHER = "IBM Boston Prog. Center", ADDRESS = "Cambridge, Mass", - COMMENT = "IBM Programming Laboratory Report No. FSC-69-0312"} - -@ARTICLE{Hearn:71, - AUTHOR = "Anthony C. Hearn", - TITLE = "Applications of Symbolic Manipulation in Theoretical Physics", - JOURNAL = "Comm. ACM", - YEAR = 1971, VOLUME = 14, PAGES = "511-516"} - -@INPROCEEDINGS{Hearn:71a, - AUTHOR = "Anthony C. Hearn", - TITLE = "{REDUCE} 2: A System and Language for Algebraic Manipulation", - YEAR = 1971, PAGES = "128-133", - EDITOR = "S.R. Petrick", - BOOKTITLE = "Proc. of Second Symposium on Symbolic and -Algebraic Manipulation", - PUBLISHER = "ACM, New York"} - -@INPROCEEDINGS{Hearn:71b, - AUTHOR = "Anthony C. Hearn", - TITLE = "Calculation of Traces of Products of Gamma Matrices", - YEAR = 1971, PAGES = "I-30 - I-44", - BOOKTITLE = "Proc. of the Second Colloquium on Advanced Computing -Methods in Theoretical Physics, {CNRS}, Marseilles", - ABSTRACT = {A survey of the algorithms available for the calculation of -traces of products of Dirac gamma matrices is presented.}} - -@INPROCEEDINGS{Hearn:71c, - AUTHOR = "Anthony C. Hearn", - TITLE = "The Computer Solution of Algebraic Problems by Pattern Matching", - YEAR = 1971, PAGES = "I-45 - I-57", - BOOKTITLE = "Proc. of the Second Colloquium on Advanced Computing -Methods in Theoretical Physics, {CNRS}, Marseilles", - ABSTRACT = {This paper discusses computer techniques for the solution of -algebraic problems in theoretical physics and related areas by pattern -matching.}} - -@INPROCEEDINGS{Hearn:72, - AUTHOR = "Anthony C. Hearn", - TITLE = "Computer Solution of Symbolic Problems in Theoretical Physics", - YEAR = 1972, PAGES = "567-596", - BOOKTITLE = "Computing as a Language of Physics, {IAEA}, Vienna", - ABSTRACT = {A survey of the computing techniques currently available for -the solution of nonnumerical problems in theoretical physics and related -areas is presented.}} - -@ARTICLE{Hearn:72a, - AUTHOR = "Anthony C. Hearn", - TITLE = "Improved Non-modular Polynomial {GCD} Algorithm", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1972, PAGES = "10-15", - ABSTRACT = {An improved non-modular algorithm for the calculation of the -greatest common divisor of two multivariate polynomials is presented.}} - -@ARTICLE{Hearn:72b, - AUTHOR = "Anthony C. Hearn", - TITLE = "A {REDUCE} Solution of Problem \#2 - The {Y(2n)} Functions", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1972, VOLUME = 14, - ABSTRACT = {A {REDUCE} solution to {SIGSAM} Problem \#2 is described.}} - -@INPROCEEDINGS{Hearn:73, - AUTHOR = "Anthony C. Hearn and R{\"u}diger G. K. Loos", - TITLE = "Extended Polynomial Algorithms", - YEAR = 1973, PAGES = "147-152", - BOOKTITLE = "Proc. {ACM} 73", - ABSTRACT = {It is shown that standard polynomial algorithms may be -applied to a much wider class of functions by making a straightforward -generalization of the concept of the exponent. The implementation of a -computer algebra system from a standard set of polynomial programs which -allows for any coefficient or exponent structure is also discussed.}} - -@INPROCEEDINGS{Hearn:73a, - AUTHOR = "Anthony C. Hearn", - TITLE = "The {REDUCE} Program for Computer Algebra", - YEAR = 1973, - BOOKTITLE = "Proc. of the Third Colloquium on Advanced Computing Methods -in Theoretical Physics, {CNRS}, Marseilles", - ABSTRACT = {The status of the {REDUCE} program for computer algebra in 1973 -is illustrated by a discussion of some aspects of its design philosophy.}} - -@INPROCEEDINGS{Hearn:74, - AUTHOR = "Anthony C. Hearn", - TITLE = " Polynomial and Rational Function Representations", - YEAR = 1974, PAGE = "211", - BOOKTITLE = "Proc. Math Software II, Purdue University", - ABSTRACT = {A survey of some current methods for computer manipulation of -polynomials and rational functions is presented. Particular emphasis -is placed on the desirability of writing programs which avoid explicit -reference to the data structures used in the manipulation."}} - -@INPROCEEDINGS{Hearn:74a, - AUTHOR = "Anthony C. Hearn", - TITLE = "A Mode Analyzing Algebraic Manipulation Program", - YEAR = 1974, PAGES = "722-724", - BOOKTITLE = "Proc. {ACM} 74", - COMMENT = {Describes a version of the {REDUCE} program for algebraic -manipulation which performs a complete mode analysis as a separate extension -of the parse.}} - -@ARTICLE{Hearn:76, - AUTHOR = "Anthony C. Hearn", - TITLE = "Scientific Applications of Symbolic Computation", - JOURNAL = "Computer Science and Scientific Comp.", - YEAR = 1976, PAGES = "83-108", - ABSTRACT = {This paper reviews the use of symbolic computation systems for -problem solving in scientific research.}} - -@INPROCEEDINGS{Hearn:76a, - AUTHOR = "A. C. Hearn", - TITLE = "A New {REDUCE} Model for Algebraic Simplification", - YEAR = 1976, PAGES = "46-52", - BOOKTITLE = "Proc. {SYMSAC} 76, {ACM}", - ABSTRACT = {This paper shows how the general concepts of mode analysis can -play a useful role in the design and implementation of programs -for algebraic simplification.}} - -@INPROCEEDINGS{Hearn:76b, - AUTHOR = "A. C. Hearn", - TITLE = "Symbolic Computation", - YEAR = 1976, PAGES = "201-211", - BOOKTITLE = "Proc. {CERN} 1976 Computing School, {CERN} Geneva", - COMMENT = {Lecture Notes.}} - -@INPROCEEDINGS{Hearn:77, - AUTHOR = "A. C. Hearn", - TITLE = "The Structure of Algebraic Computations", - YEAR = 1977, PAGES = "1-15", - BOOKTITLE = "Proc. of the Fourth Colloquium on Advanced Comp. -Methods in Theor. Physics. St. Maximin, France", - ABSTRACT = {Most algebraic computations which arise from physical problems -have considerable structure in their specification because of the many -physical conservation laws and the nature of our approximation techniques. -The exploitation of this structure is often the reason why hand -calculations of non-trivial problems are possible. However, most -available algebra systems do not preserve such structure in a consistent -manner, and consequently produce results which are far less comprehensible -than equivalent hand calculations. In this paper we shall describe -techniques which can utilize the algebraic structure more effectively and -apply them to several examples.}} - -@INPROCEEDINGS{Hearn:78, - AUTHOR = "Anthony C. Hearn", - TITLE = "Algebraic Manipulation by Computer", - YEAR = 1978, PAGES = "96-116", - BOOKTITLE = "Proc. Intern. Meeting on Programm. and Math. Meth. for -Solving Phys. Probs., Dubna, USSR", - ABSTRACT = {This paper reviews the use of algebraic manipulation by computer -as a tool for scientific problem solving.}} - -@INPROCEEDINGS{Hearn:79, - AUTHOR = "Anthony C. Hearn", - TITLE = "Non-Modular Computation of Polynomial {GCDs} Using Trial -Division", - YEAR = 1979, VOLUME = 72, PAGES = "227-239", - BOOKTITLE = "Proc. {EUROSAM} 79", - ABSTRACT = {This paper describes a new algorithm for the determination of -the {GCD} of two multivariate polynomials by non-modular means.}} - -@ARTICLE{Hearn:79a, - AUTHOR = "Anthony C. Hearn and Arthur C. Norman", - TITLE = "A One-Pass Prettyprinter", - JOURNAL = "Sigplan Notices, ACM 12", - YEAR = 1979, VOLUME = 14, PAGES = "50-58", - ABSTRACT = {We propose a new method for program formatting which is -described in terms of two coroutines.}} - -@INPROCEEDINGS{Hearn:80, - AUTHOR = "Anthony C. Hearn", - TITLE = "The Personal Algebra Machine", - YEAR = 1980, PAGES = "621-628", - BOOKTITLE = "Information Processing 80, Proc. {IFIP} -Congress 80"} - -@ARTICLE{Hearn:81, - AUTHOR = "Anthony C. Hearn and S. Watanabe", - TITLE = "Analytic Integration by Computer", - JOURNAL = "Information Processing Society of Japan 22", - YEAR = 1981, PAGES = "639-650"} - -@INPROCEEDINGS{Hearn:81a, - AUTHOR = "Anthony C. Hearn", - TITLE = "Symbolic Computation and its Application to -High-Energy Physics", - YEAR = 1981, PAGES = "390-406", - BOOKTITLE = "Proc. 1980 {CERN} School of Computing, Geneva"} - -@INPROCEEDINGS{Hearn:82, - AUTHOR = "Anthony C. Hearn", - TITLE = "{REDUCE} - A Case Study in Algebra System Development", - YEAR = 1982, VOLUME = 144, PAGES = "263-272", - BOOKTITLE = "Proc. of {EUROCAM} '82, Lecture Notes on Comp. -Science"} - -@INPROCEEDINGS{Hearn:82a, - AUTHOR = "Anthony C. Hearn and M. L. Griss and E. Benson", - TITLE = "Current Status of a Portable {LISP} Compiler", - YEAR = 1982, - BOOKTITLE = "Proc. {SIGPLAN} '82 Symp. on Compiler -Construction, ACM", PAGES = "276-283"} - -@INPROCEEDINGS{Hearn:85, - AUTHOR = "Anthony C. Hearn", - TITLE = "Structure: The Key to Improved Algebraic Computation", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "215-230"} - -@INPROCEEDINGS{Hearn:86, - AUTHOR = "Anthony C. Hearn", - TITLE = "Optimal Evaluation of Algebraic Expressions", - BOOKTITLE = "Proc. {AAECC}-3, Lecture Notes on Comp. Science", - PUBLISHER = "Springer Verlag", - YEAR = 1986, VOLUME = 229, PAGES = "392-403"} - -@TECHREPORT{Hearn:91, - AUTHOR = "Anthony C. Hearn", - TITLE = "{REDUCE} User's Manual, {Version} 3.6", - INSTITUTION = "RAND", - YEAR = 1995, TYPE = "Report", - NUMBER = "CP 78", MONTH = "July"} - -@INPROCEEDINGS{Hearn:93, - AUTHOR = "Anthony C. Hearn and Eberhard Schr{\"u}fer", - TITLE = "An Order-sorted Approach to Algebraic Computation", - BOOKTITLE = "Proc. {DISCO '93}, Lecture Notes on Comp. Science", - YEAR = 1993, VOLUME = 722, PAGES = "134-144", - PUBLISHER = "Springer-Verlag", - ABSTRACT = {This paper presents the prototype design of an algebraic -computation system that manipulates algebraic quantities as generic objects -using order-sorted algebra as the underlying model. The resulting programs -have a form that is closely related to the algorithmic description of a -problem, but with the secruity of full type checking in a compact, natural -style.}} - -@ARTICLE{Hearn:95, - AUTHOR = "Anthony C. Hearn and Eberhard Schr{\"u}fer", - TITLE = "A Computer Algebra System based on Order-sorted Algebra", - JOURNAL = "Journ. Symbolic Computation", - YEAR = 1995, VOLUME=19, PAGES = "65-77", - ABSTRACT = "This paper presents the prototype design of an algebraic -computation system that manipulates algebraic quantities as generic -objects using order-sorted algebra as the underlying model. The resulting -programs have a form that is closely related to the algorithmic -description of a problem, but with the security of full type checking in a -compact, natural style."} - -@ARTICLE{Hehl:92, - AUTHOR = "Friedrich W. Hehl and Hartmut Meyer", - TITLE = "Mit Buchstaben auf dem Computer rechnen", - JOURNAL = "Physikalische {Bl\"{a}tter}", - YEAR = 1992, VOLUME = "48", PAGES = "377-381", - COMMENT = {(in German) Describes the application of - symbolic computation using examples coded in {REDUCE}. The CA systems - of interest for physicists are classified. A series of problems - from physics which have successfully been solved with CA methods - is given}} - -@BOOK{Hehl:92a, - AUTHOR = "F.W. Hehl and V. Winkelmann and H. Meyer", - TITLE = "Computer-Algebra. Ein Kompaktkurs {\"{u}ber} die Anwendung von -REDUCE", - PUBLISHER = "Springer-Verlag, Berlin, Heidelberg, New York, - ISBN 3-540-55724-5", - YEAR = 1992} - -@ARTICLE{Hermann:83, - AUTHOR = "R. Hermann", - TITLE = "Geometric Construction and Properties of Some Families of -Solutions of Nonlinear Partial Differential Equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1983, VOLUME = 24, NUMBER = "3", PAGES = "510-521", - COMMENT = {First of series of papers on 19th century pde theory. The -presentation is aimed at including systems such as {MACSYMA} and {REDUCE} -as tools. This paper is on Lagrange-Charpit method. "I have in mind -developing the differential algebraic aspects of the formalism, going -beyond the 19th century with the aid of symbolic computer systems".}} - -@ARTICLE{Hess:84, - AUTHOR = "P. O. Hess and W. Greiner", - TITLE = "The Collective Modes of Nuclear Molecules", - JOURNAL = "Il Nuovo Cimento", - YEAR = 1984, VOLUME = "83A", PAGES = "76-177", - COMMENT = {A long paper, admits use of {REDUCE} (on page 101) to invert -11 x 11 matrix.}} - -@TECHREPORT{Hettich:77, - AUTHOR = "R. P. Hettich and J. A. van Hulzen", - TITLE = "Approximation with a Class of Rational Functions", - INSTITUTION = "Department of Applied Mathematics, Twente -University of Technology, The Netherlands", - YEAR = 1977, TYPE = "Memorandum", - NUMBER = 165, MONTH = "May"} - -@ARTICLE{Hietarinta:83, - AUTHOR = "J. Hietarinta", - TITLE = "A search for integrable two-dimensional {Hamiltonian} systems -with polynomial potential", - JOURNAL = "Phys. Lett.", - YEAR = 1983, VOLUME = "96A", PAGES = "273-278", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:83a, - AUTHOR = "J. Hietarinta", - TITLE = "Integrable Families of {Henon-Heiles} Type {Hamiltonians} and a -New Duality", - JOURNAL = "Phys. Rev. A", - YEAR = 1983, VOLUME = 28, PAGES = "3670-3672", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:84, - AUTHOR = "J. Hietarinta", - TITLE = "Classical versus quantum integrability", - JOURNAL = "J. Math. Phys.", - YEAR = 1984, VOLUME = 25, PAGES = "1833-1840", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:84a, - AUTHOR = "J. Hietarinta", - TITLE = "New integrable {Hamiltonians} with transcendental invariants", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1984, VOLUME = 52, PAGES = "1057-1060", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:84b, - AUTHOR = "J. Hietarinta and B. Grammaticos and B. Dorizzi and A. Ramani", - TITLE = "Coupling-Constant Metamorphosis and Duality between -Integrable {Hamiltonian} Systems", - JOURNAL = "Phys. Rev. Lett.", - YEAR = 1984, VOLUME = 53, PAGES = "1707-1710", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:85, - AUTHOR = "J. Hietarinta", - TITLE = "How to construct integrable {Fokker-Planck} and -electromagnetic {Hamiltonians} from ordinary integrable {Hamiltonians}", - JOURNAL = "J. Math. Phys.", - YEAR = 1985, VOLUME = 26, PAGES = "1970-1975", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:87, - AUTHOR = "J. Hietarinta", - TITLE = "Direct methods for the search of the second invariant", - JOURNAL = "Physics Reports", - YEAR = 1987, VOLUME = 147, PAGES = "87-154", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@ARTICLE{Hietarinta:87a, - AUTHOR = "J. Hietarinta", - TITLE = "A search of bilinear equations passing {Hirota's} three-soliton -condition: {I.} {KdV}-type bilinear equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1987, VOLUME = 28, PAGES = "1732-1742", - COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables -vanish on a affine manifold defined by {LET-rules}. Large scale -computation.}} - -@ARTICLE{Hietarinta:87b, - AUTHOR = "J. Hietarinta", - TITLE = "A search of bilinear equations passing {Hirota's} three-soliton -condition: {II.} {mKdV}-type bilinear equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1987, VOLUME = 28, PAGES = "2094-2101", - COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables -vanish on a affine manifold defined by {LET-rules}. Large scale -computation.}} - -@ARTICLE{Hietarinta:87c, - AUTHOR = "J. Hietarinta", - TITLE = "A search of bilinear equations passing {Hirota's} three-soliton -condition: {III.} {Sine-Gordon}-type bilinear equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1987, VOLUME = 28, PAGES = "2586-2592", - COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables -vanish on a affine manifold defined by {LET-rules}. Large scale -computation.}} - -@ARTICLE{Hietarinta:88, - AUTHOR = "J. Hietarinta", - TITLE = "A search of bilinear equations passing {Hirota's} three-soliton -condition: {IV.} Complex bilinear equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1988, VOLUME = 29, PAGES = "628-635", - COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables -vanish on a affine manifold defined by {LET-rules}. Large scale computation. -computation.}} - -@ARTICLE{Hietarinta:89, - AUTHOR = "J. Hietarinta and B. Grammaticos", - TITLE = "On the $\hbar^{2}$-correction terms in quantum integrability", - JOURNAL = "J. Phys. A: Mat. Gen.", - YEAR = 1989, VOLUME = "TBD", PAGES = "TBD", - COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} - -@INPROCEEDINGS{Hietarinta:91, - AUTHOR = "J. Hietarinta", - TITLE = "From an analytical formula to a movie by way of {REDUCE} and {C}", - BOOKTITLE = "Proc. of the Workshop on Symbolic and Numeric Computation", - PUBLISHER = "Research Reports, Computing Centre of Helsinki University", - YEAR = 1991, PAGES = "117-126"} - -@TECHREPORT{Hietarinta:92, - AUTHOR = "Jarmo Hietarinta", - TITLE = "Solving the {Yang-Baxter} equation in 2 dimensions with massive -use of factorizing Gr{"\o}bner basis computations", - INSTITUTION = "University of Turku, Finland", YEAR = 1992, - MONTH = "January", TYPE = "Preprint", - COMMENT = {Submitted to ISSAC '92}, - ABSTRACT = {The complete solution to the constant (quantum) Yang-Baxter -equation was recently obtained in the two dimensional case -(= all indices range over 1,2). This amounts to solving a set of 64 -equations in 16 variables. We describe here how the problem was solved, -first by breaking it into smaller subproblems by using the symmetries of -the equation, and then by solving each subproblem by computing the -factorized Gr{"\o}bner basis using the {'grobner'-}package written by Melenk, -M{"\o}ller and Neun for REDUCE 3.4.}}. - -@TECHREPORT{Hietarinta:92a, - AUTHOR = "Jarmo Hietarinta", - TITLE = "Solving the two-dimensional constant quantum {Yang-Baxter} - equation", - INSTITUTION = "University of Turku, Finland", YEAR = 1992, - MONTH = "May", TYPE = "Report", NUMBER = "TURKU-FL-R7"} - -@BOOK{Hirota:89, - AUTHOR = "Ryogo Hirota and Masaaki Ito", - TITLE = "Introduction to {REDUCE --- Doing} Symbolic Computation on {PC}", - PUBLISHER = "Science sha, Tokyo", MONTH = "June", YEAR = 1989, - COMMENT = {(In Japanese).}} - -@TECHREPORT{Horowitz:75, - AUTHOR = "E. Horowitz and D. R. Musser", - TITLE = "The Synthesis and Use of Algebraic Specifications of Data -Structures", - INSTITUTION = "University of Southern California", - YEAR = 1975, TYPE = "Preprint"} - -@ARTICLE{Horwitz:83, - AUTHOR = "B. Horwitz", - TITLE = "Unequal Diameters and Their Effects on Time Varying Voltages -in Branched Neurons", - JOURNAL = "BioPhys. J.", - YEAR = 1983, VOLUME = 41, PAGES = "51-66", - COMMENT = {Theoretical biophysics. Much algebra, and used {REDUCE} to -decrease mental labor. "Crucial point is that the existence of such computer -techniques allows higher-order correction terms to be used."}} - -@ARTICLE{Hughes:90, - AUTHOR = "D. I. Hughes", - TITLE = "Symbolic Computation with Fermions", - JOURNAL = "J. Symbolic Computation", - YEAR = 1990, VOLUME = 10, NUMBER = 6, PAGES = "657-664", MONTH = "December", - ABSTRACT = {A set of {REDUCE} routines for manipulating operators which -anticommute amongst themselves is described. These routines have -applications in theories such as supergravity where anticommuting operators -are used to represent fermions. The Dirac bracket of the supersymmetry -constraints arising in a quantum cosmological model based on N = 1 -supergravtiy coupled to a massless scalar multiplet is calculated as an -example.}} - -@INPROCEEDINGS{Hulshof:84, - AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", - TITLE = "Automatic Error Cumulation Control", - BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes -in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "260-271", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Hulshof:85, - AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", - TITLE = "An Expression Compression Package for {REDUCE} based on -Factorization and Controlled Expansion", - BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes -in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "315-316", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Hulshof:81, - AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen and J. Smit", - TITLE = "Code Optimization Facilities Applied in the {Netform} Context", - INSTITUTION = "Department of Applied Mathematics, Twente -University of Technology, The Netherlands", - YEAR = 1981, TYPE = "Memorandum", NUMBER = 368, - MONTH = "December"} - -@ARTICLE{Hulshof:83, - AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", - TITLE = "Some {REDUCE} Facilities for Pretty Printing Subscripts and Formal -Derivatives", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "16-20", MONTH = "February"} - -@ARTICLE{Hunt:91, - AUTHOR = "R. E. Hunt and D. G. Crighton", - TITLE = "Instability of flows in spatially developing media", - JOURNAL = "Proc. Roy. Soc. Lond. A", -YEAR = 1991, VOLUME = 435, PAGES = "109-128", - COMMENT = {Uses {REDUCE} to find series solutions for two fluid-dynamical - problems, and then condenses the series into exact solutions}} - -@TECHREPORT{Husberg:81, - AUTHOR = "N. Husberg", - TITLE = "Preliminary {II} {REDUCE}-2 and {Analitik-74}, a Comparison", - INSTITUTION = "Helsinki University of Technology Computing -Center", YEAR = 1981, MONTH = "November"} - -% REDUCE BIBLIOGRAPHY - -% Part 3: I-O - -% Copyright (c) 1993 RAND. All Rights Reserved. - -% Additions and corrections are solicited. Please send them, in the -% same format as these entries if possible, to reduce at rand.org. - - -@TECHREPORT{Idesawa:77, - AUTHOR = "M. Idesawa and T. Yatagai", - TITLE = "General Theory of Projection-Type {Moir\'e} Topography", - INSTITUTION = "Institute of Physical and Chemical Research, -Wako-Shi, Saitama", YEAR = 1977, TYPE = "Scientific Papers", - NUMBER = 71, - ABSTRACT = {The configuration of equi-order surfaces in the projection-type -{Moire} topography is described in terms of system parameters -without any restrictions on the measurement condition.}} - -@INPROCEEDINGS{Ilyin:87, - AUTHOR = "V. A. Ilyin and A. P. Kryukov", - TITLE = "{DIMREG} - The Package for Calculations in the Dimensional -Regularization with {4-dimensional} $\gamma^{5}$ -matrix in Quantum Field -Theory", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "225-232", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Ilyin:89, - AUTHOR = "V. A. Ilyin and A. P. Kryukov and A. Ya. Rodioniov and -A. Yu. Taranov", - TITLE = "Fast Algorithm for Calculation of {Dirac}'s Gamma-Matrices Traces", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1989, VOLUME = 23, NUMBER = 4, PAGES = "15-24", MONTH = "October"} - -@INPROCEEDINGS{Ilyin:91, - AUTHOR = "V. A. Ilyin and A. P. Kryukov", - TITLE = "Symbolic Simplification of Tensor Expressions Using Symmetries, -Dummy Indices and Identities", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "224-228", - YEAR = 1991, - ABSTRACT = {The algorithm based on simple geometrical ideas is suggested -for simplification of tensor expressions which takes into account -symmetries, dummy indices, and linear identities with many terms. The -results of the realization in REDUCE system are adduced.}} - -@INPROCEEDINGS{Ilyin:91a, - AUTHOR = "V. A. Ilyin and A. P. Kryukov and A. Ya. Rodionov and A Yu. -Taranov", - TITLE = "{PC} Implementation of Fast {Dirac} Matrix Trace Calculations", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "456-457", - YEAR = 1991, - COMMENT = {We present an implementation of fast algorithm for Dirac -matrix trace calculations. This implementation is made for {IBM} i -compatible {PC} and works under {REDUCE 3.3.1}. Name of package is -{CVIT}. The algorithm itself was described in [1]. It is based on intense -use of Fierz identities in N-dimensional space (N is arbitrary natural -number or symbol) and may be considered as an extension of well known -Kahane algorithm [2] on higher space dimensions.}} - -@TECHREPORT{Inada:80, - AUTHOR = "Nobuyuki Inada", - TITLE = "Fortran-Based {LISP} System for {REDUCE}", - INSTITUTION = "Information Science Laboratory, The Institute -of Physical and Chemical Research", - YEAR = 1980} - -@TECHREPORT{Ioakimidis:90, - AUTHOR = "N. I. Ioakimidis", - TITLE = "Construction of the Equation of Caustics in Dynamic Plane -Elasticity Problems with the Help of {REDUCE}", - INSTITUTION = "Division of Applied Mathematics and Mechanics, School of -Engineering, University of Patras, Greece", - YEAR = 1990} - ABSTRACT = {The method of caustics has become a very efficient tool in -crack, hole and many additional plane elasticity problems. Unfortunately, -the fundamental equation of the caustics frequently requires complicated -algebraic computations including that of a Jacobian determinant. Here we -show that computer algebra software can prove very efficient in these -computations, using as a vehicle for this illustration the already known -fundamental equation of caustics in dynamic plane elasticity (both for crack -problems in fracture mechanics as well as for hole and additional problems). -We have used the programming capabilities of {REDUCE}, a very popular -computer algebra system, for our algebraic computations. Moreover, we -illustrate the "learning" abilities of {REDUCE} especially for the -derivation of the complex form of this equation. The case of static plane -elasticity results simply as a special case of dynamic plane elasticity. -Additional possibilities are suggested in brief.}} - -@TECHREPORT{Ioakimidis:90a, - AUTHOR = "N. I. Ioakimidis", - TITLE = "Construction of Singular Integral Equations for Interacting -Straight Cracks by Using {REDUCE}", - INSTITUTION = "Division of Applied Mathematics and Mechanics, School of -Engineering, University of Patras, Greece", - YEAR = 1990} - ABSTRACT = {The method of singular integral equations has been applied to -the solution of crack problems in plane and antiplane elasticity -hundreds of times during the last twenty years. Here we revisit the case of -an arbitrary number of interacting straight cracks in plane elasticity and -we illustrate the possibility of constructing (algebraically) the -corresponding system of singular integral equations by using computer -algebra software. We present a procedure (computer program) by using -{REDUCE} as well as several examples of application of the present approach, -extensions and generalizations of which follow rather trivially.}} - -@ARTICLE{Ito:85, - AUTHOR = "M. Ito", - TITLE = "A {REDUCE} Program for Evaluating a {Lax} Pair Form", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1985, VOLUME = 34, PAGES = "325-331", - COMMENT = {{REDUCE} in nonlinear equations.}} - -@ARTICLE{Ito:85a, - AUTHOR = "M. Ito and F. Kako", - TITLE = "A {REDUCE} Program for Finding Conserved Densities of Partial -Differential Equations with Uniform Rank", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1985, VOLUME = 38, PAGES = "415-419"} - -@ARTICLE{Ito:88, - AUTHOR = "Masaaki Ito", - TITLE = "A {REDUCE} Program for {Hirota's} Bilinear Operator and -{Wronskian} Operations", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1988, VOLUME = 50, NUMBER = 3, PAGES = "321-330", MONTH = "August"} - -@ARTICLE{Ito:90, - AUTHOR = "Nobuyasu Ito and Tetsuhiko Chikyu", - TITLE = "Multi-Spin-Flip Dynamics of the {Ising} Chain", - JOURNAL = "Physica A", - YEAR = 1990, VOLUME = 166, PAGES = "193-205", - ABSTRACT = {Two kinds of multi-spin-flip discrete-time dynamics of the -Ising chain are solved analytically. One dynamics is the two sublattice -type flip and each sublattice contains {\em n} sequential spins -alternately. The other has the overlapped multi-spin-flip sequence. The -state of {\em n} spins at the next time step is selected from ${2}^{n}$ -states using the heat-bath type transition probability. These dynamics of -the Ising chain are equivalent to the statics of the square-lattice Ising -model with a 1 x 2 unit cell or of the triangular-lattice Ising model. -The analytic solutions of the single spin relaxation time of these -dynamics are obtained using these equivalences.}} - -@ARTICLE{Ito:90a, - AUTHOR = "Nobuyasu Ito", - TITLE = "Discrete-Time and Single-Spin-Flip Dynamics of the {Ising} Chain", - JOURNAL = "Progress of Theoretical Physics", - YEAR = 1990, VOLUME = 83, NUMBER = 4, PAGES = "682-692", MONTH = "April", - ABSTRACT = {Some stochastic dynamics of the Ising chain are discussed -analytically and their flip-sequence dependences are studied in the -present paper. The dynamics are the discrete-time and single-spin-flip -dynamics. The flip sequence is of sequential or sublattice-type. Their -relaxation times of single spin expectation functions are calculated. The -sequential-flip dynamics of {\em n}-site chain has the same correlation -time as the {\em n}-sublattice dynamics. The relaxation becomes slow when -this {\em n} is made large. The static models equivalent to these dynamic -models are the Ising models on a triangular lattice with a skew boundary -condition which has the same couplings in two directions. Spin-spin -correlation lengths in the direction perpendicular to the anisotropic -direction are obtained for these equivalent models. They depend only on -the ratio of the lattice width to boundary skew.}} - -@ARTICLE{Ito:94, - AUTHOR = "Masaaki Ito", - TITLE = "{SYMCD} - a {REDUCE} package for finding symmetries and conserved -densitites of systems of nonlinear evolution equations", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1994, VOLUME = 79, NUMBER = 3, PAGES = "547-554", MONTH = "May"} - -@ARTICLE{Jansen:86, - AUTHOR = "Paul Jansen and Peter Weidner", - TITLE = "High-Accuracy Arithmetic Software--Some Tests of the -{ACRITH} Problem-Solving Routines", - JOURNAL = "{ACM} {TOMS}", - YEAR = 1986, VOLUME = 12, NUMBER = 1, PAGES = "62-70", MONTH = "March", - COMMENT = {A criticism of {ACRITH}, shows {REDUCE} bigfloats are more -accurate and comparable in speed.}} - -@ARTICLE{Janssen:87, - AUTHOR = "M. H. M. Janssen and D. H. Parker and S. Stolte", - TITLE = "Saturation in Laser-Induced Fluorescence: Effects on -Alignment Parameters", - JOURNAL = "Chemical Phys.", - YEAR = 1987, VOLUME = 113, PAGES = "357-382", - COMMENT = {"Computer algebra programs are used to generate simple analytical -expressions which account for the influence of saturation on -determining alignment parameters." The system is {REDUCE}.}} - -@ARTICLE{Jeffrey:84, - AUTHOR = "D. J. Jeffrey and Y. Onishi", - TITLE = "The Forces and Couples Acting on Two Nearly Touching Spheres -in Low-{Reynolds}-Number Flow", - JOURNAL = "Z. Ang. Math. Phys.", - YEAR = 1984, VOLUME = 35, PAGES = "634-641", - COMMENT = {Extends previous result from linear term to -O$\epsilon$ in $\epsilon$. "Otherwise the only new principle in the -calculation is the handling of long algebraic expressions, which was -accomplished by using the computer algebra systems {CAMAL} and {REDUCE}."}} - -@ARTICLE{Kadlecsik:88, - AUTHOR = "J. Kadlecsik", - TITLE = "New Approaches to the Axisymmetric Vacuum", - JOURNAL = "Zeitschrift {f\"{u}r} Physik C. Particles and Fields", - YEAR = 1988, VOLUME = 41, PAGES = "265-269"} - -@TECHREPORT{Kadlecsik:92, - AUTHOR = "Jo{\'o}zsef Kadlecsik", - TITLE = "Tensor Manipulation Package for General Relativity Calculations", - INSTITUTION = "Central Research Institute for Physics, Budapest", - YEAR = 1992, TYPE = "Preprint", NUMBER = "KFKI-1992-05/B+M", - ABSTRACT = {An experimental computer program is presented, which manipulates -tensor expressions symbolically in general relativity calculations.}} - -@ARTICLE{Kagan:85, - AUTHOR = "Y. Y. Kagan and L. Knopoff", - TITLE = "The First-Order Statistical Moment of the Seismic Moment Tensor", - JOURNAL = "Geophys. J. R. Astron. Soc.", - YEAR = 1985, VOLUME = 81, PAGES = "429-444"} - -@ARTICLE{Kagan:88, - AUTHOR = "Y. Y. Kagan", - TITLE = "Static Sources of Elastic Deformation in a Homogeneous -Half-Space", - JOURNAL = "J. Geophys. Res.", - YEAR = 1988, VOLUME = 93, NUMBER = "B9", PAGES = "10,560-10,574", - MONTH = "September"} - -@TECHREPORT{Kahn:69, - AUTHOR = "M. E. Kahn", - TITLE = "The Near-Minimum-Time Control of Open Loop Articulated -Kinematic Chains", - INSTITUTION = "Stanford University, Computer Science Dept.", - YEAR = 1969, TYPE = "Report", NUMBER = "AIM-106"} - -@TECHREPORT{Kamal:81, - AUTHOR = "A. N. Kamal and J. Kodaira and T. Muta", - TITLE = "Gluon Jets From Heavy Paraquarkonium", - INSTITUTION = "University of Alberta, Canada and Stanford -University, California and Fermi National Accelerator -Laboratory, Illinois", - YEAR = 1981, NUMBER = "SLAC-PUB-2725", MONTH = "April"} - -@TECHREPORT{Kamel:69, - AUTHOR = "A. A. Kamel", - TITLE = "Perturbation Method in the Theory of Non-Linear Oscillations", - INSTITUTION = "Stanford University, Dept. of Aeronautics -and Astronautics", YEAR = 1969, TYPE = "Report"} - -@TECHREPORT{Kamel:69a, - AUTHOR = "A. A. Kamel", - TITLE = "Perturbation Theory Based on {Lie} Transforms and Its -Application to the Stability of Motion Near {Sun}-Perturbed -{Earth-Moon} Triangular Libration Points", - INSTITUTION = "Stanford University, Dept. of Aeronautics and -Astronautics", YEAR = 1969, TYPE = "Report", NUMBER = "391"} - -@INPROCEEDINGS{Kamel:78, - AUTHOR = "A. A. Kamel", - TITLE = "Synchronous Satellite Ephemeris Due to Earth's -Triaxiality and Luni-Solar Effects", - YEAR = 1978, MONTH = "August", - BOOKTITLE = "{AIAA/AAS} Astrodynamics Conference, -Palo Alto, CA", - COMMENT = {Synchronous satellite ephemeris is developed in terms of -non-singular orbital elements.}} - -@ARTICLE{Kanada:81, - AUTHOR = "Yasumasa Kanada and Tateaki Sasaki", - TITLE = "{LISP-based} {big-float} system is not slow", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1981, VOLUME = 15, NUMBER = 2, PAGES = "13-19", MONTH = "May"} - -@TECHREPORT{Kanada:75, - AUTHOR = "Y. Kanada", - TITLE = "Implementation of {HLISP} and Algebraic Manipulation -Language {REDUCE} 2", - INSTITUTION = "University of Tokyo Information Science Lab", - YEAR = 1975, TYPE = "Report", NUMBER = "75-01"} - -@ARTICLE{Kaneko:89, - AUTHOR = "Toshiaki Kaneko and Setsuya Kawabata", - TITLE = "A Preprocessor for {Fortran} Source Code Produced by {REDUCE}", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1989, VOLUME = 55, NUMBER = 2, PAGES = "141-147", - MONTH = "September", PUBLISHER = "North Holland Publishing Company"} - -@ARTICLE{Kaps:85, - AUTHOR = "P. Kaps and S. W. H. Poon and T. D. Bui", - TITLE = "Rosenbrock Methods for Stiff {ODEs}: A Comparison of {Richardson} -Extrapolation and Embedding Techniques", - JOURNAL = "Computing", - YEAR = 1985, VOLUME = 34, PAGES = "17-40", - COMMENT = {Reference to {REDUCE} but not in text.}} - -@INPROCEEDINGS{Karr:85, - AUTHOR = "Michael Karr", - TITLE = "Canonical Form for Rational Exponential Expressions", - BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes -in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "585-594", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Katsura:85, - AUTHOR = "Shigetoshi Katsura", - TITLE = "Application of the Formula Manipulating System to Statistical - Mechanics", YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "155-180"} - -@PHDTHESIS{Kauffman:73, - AUTHOR = "S. K. Kauffman", - TITLE = "Ortho-Positronium Annihilation: Steps Toward Computing -the First Order Radiative Corrections", - SCHOOL = "California Institute of Technology", - YEAR = 1973} - -@INPROCEEDINGS{Kazasov:87, - AUTHOR = "C. Kazasov", - TITLE = "Laplace Transformations in {REDUCE} 3", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "132-133", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Keady:85, - AUTHOR = "Grant Keady", - TITLE = "The Power Concavity of Solutions of Some Semilinear Elliptic -{Boundary-Value} Problems", - JOURNAL = "Bull. Austral. Math. Soc.", - YEAR = 1985, VOLUME = 31, PAGES = "181-184"} - -@ARTICLE{Keener:83, - AUTHOR = "James P. Keener", - TITLE = "Oscillatory coexistence in the {chemostat:} a codimension two -unfolding", - JOURNAL = "{SIAM} J. Appl. Math.", - YEAR = 1983, VOLUME = 43, NUMBER = 5, PAGES = "1005-1018"} - -@ARTICLE{Keener:85, - AUTHOR = "James P. Keener", - TITLE = "Oscillatory coexistence in a food chain model with competing -predators", - JOURNAL = "J. Math. Biology", - YEAR = 1985, VOLUME = 22, PAGES = "123-135"} - -@ARTICLE{Keener:89, - AUTHOR = "James P. Keener", - TITLE = "Knotted scroll wave filaments in excitable media", - JOURNAL = "Physica D 34", - YEAR = 1989, PAGES = "378-390"} - -@ARTICLE{Keener:90, - AUTHOR = "James P. Keener", - TITLE = "Knotted vortex filaments in an ideal fluid", - JOURNAL = "J. Fluid Mech.", - YEAR = 1990, VOLUME = 211, PAGES = "629-651"} - -@ARTICLE{Kendall:88, - AUTHOR = "W. S. Kendall", - TITLE = "Symbolic Computation and the Diffusion of Shapes of Triads", - JOURNAL = "Adv. Appl. Prob.", - YEAR = 1988, VOLUME = 20, PAGES = "775-797"} - -@TECHREPORT{Kendall:89, - AUTHOR = "W. S. Kendall", - TITLE = "The Diffusion of {Euclidean} Shape", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1989, - TYPE = "Research Report", NUMBER = 161} - -@TECHREPORT{Kendall:89a, - AUTHOR = "W. S. Kendall", - TITLE = "Probability, Convexity, and Harmonic Maps with Small Image I: -Uniqueness and Fine Existence", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1989, - TYPE = "Research Report", NUMBER = 162} - -@ARTICLE{Kendall:90, - AUTHOR = "W. S. Kendall", - TITLE = "Computer Algebra and Stochastic Calculus", - JOURNAL = "Notices A.M.S.", - YEAR = 1990, VOLUME = 37, PAGES = "1254-1256"} - -@TECHREPORT{Kendall:91, - AUTHOR = "Wilfred S. Kendall", - TITLE = "Computer Algebra and Stochastic Calculus", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1991, - TYPE = "Research Report", NUMBER = 203} - -@TECHREPORT{Kendall:91a, - AUTHOR = "Wilfred S. Kendall", - TITLE = "Symbolic {It\^{o}} Calculus: An Introduction", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1991, - TYPE = "Research Report", NUMBER = 217} - ABSTRACT = {The ito procedures are an implementation of stochastic calculus -for the computer algebra package {REDUCE}. In this paper it is explained -how the implementation of ito grows naturally out of the formulation of -stochastic calculus using modules of stochastic differentials. Two examples -are given of ito in action: a simple example concerning various exponential -martingales and a more involved example concerning the escape rate of the -Bessel process of dimension exceeding 2. A basic subset of the ito -procedures is listed in six appendices; details are given of how to obtain -the full set from the author.}} - -@TECHREPORT{Kendall:93a, - AUTHOR = "Wilfred S. Kendall", - TITLE = "Probability, Convexity, and Harmonic Maps II: Smoothness via -Probabilistic Gradient Inequalities", - INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1993, - MONTH = "October", TYPE = "Research Report", NUMBER = 260, - ABSTRACT = {A conformal change of metric is used to construct a coupling -of two time-changed Riemannian Brownian motions, such that there is an -upper bound on the prabability of no coupling before either process leaves -a small geodesic ball, with the bound being linear in the distance between -the two starting points. This coupling is a more geometric (and -probabilistically less technical) alternative to that introduced by -Cranston (1991). Together with some modifications it is used to provide a -probabilistic approach to the regularity of harmonic maps, thus completing -the probabilistic construction of solutions to small-image harmonic map -Dirichlet problems described in Kendall (1990). The approach includes a -mild generalization to the case of harmonic maps defined using -non-Riemannian connections in the target manifold and smooth strictly -elliptic second-order differential operators in the domain.}} - -@INPROCEEDINGS{Kerner:75, - AUTHOR = "W. Kerner and R. C. Grimm", - TITLE = "{MHD} Spectra for {Tokamaks} with Non-circular Cross Sections", - YEAR = 1975, - BOOKTITLE = "Proc. Seventh Conference on -Numerical Simulation of Plasmas, Courant Institute, {NYU}"} - -@ARTICLE{Kersten:83, - AUTHOR = "P. H. M. Kersten", - TITLE = "Infinitesimal Symmetries and Conserved Currents for Nonlinear -{Dirac} Equation", - JOURNAL = "J. Math. Phys.", - YEAR = 1983, VOLUME = 24, PAGES = "2374-2376", - COMMENT = {Harrison-Estabrook and computer algebra, in {REDUCE}. Very like -{EXCALC} but predates it.}} - -@ARTICLE{Kersten:84, - AUTHOR = "P. Kersten and R. Martini", - TITLE = "The Harmonic Map and Killing Fields for Self-Dual {SU(3)} -{Yang-Mills} Equations", - JOURNAL = "J. Phys. A", - YEAR = 1984, VOLUME = 17, PAGES = "L227-L230", - COMMENT = {%"{\ldots}and the determination of the general solution of the -killing fields have been achieved by symbolic computations in a semi-automatic -way using software developed in the symbolic language {REDUCE}{\ldots}"}} - -@ARTICLE{Kersten:86, - AUTHOR = "P. H. M. Kersten", - TITLE = "Creating and Annihilating {Lie-B\"acklund} Transformations -of the {Federbush} Model", - JOURNAL = "J. Math. Phys.", - YEAR = 1986, VOLUME = 27, PAGES = "1139-1144", - COMMENT = {"We want to stress that all computations have been worked out on -a {DEC-20} computer using {REDUCE} and a software package to do these -calculations." Lie algebra and Gragert's package.}} - -@ARTICLE{Kersten:86a, - AUTHOR = "P. H. M. Kersten and H. M. M. Ten Eikelder", - TITLE = "Infinite Hierarchies of t-independent and t-dependent -Conserved Functionals of the {Federbush} Model", - JOURNAL = "J. Math. Phys.", - YEAR = 1986, VOLUME = 27, PAGES = "2140-2145", - COMMENT = {"We want to stress that all computations have been worked out on -a {DEC-20} computer using {REDUCE} and a software package to do these -calculations."}} - -@ARTICLE{Kersten:86b, - AUTHOR = "P. H. M. Kersten and H. M. M. Ten Eikelder", - TITLE = "An Infinite Number of Infinite Hierarchies of Conserved -Quantities of the {Federbush} Model", - JOURNAL = "J. Math. Phys.", - YEAR = 1986, VOLUME = 27, PAGES = "2791-2796"} - -@ARTICLE{Killalea:80, - AUTHOR = "M. K. Killalea and B. J. McCoy", - TITLE = "Concentration Distribution and Spatial Moments of -Moving Macromolecules Undergoing Isomerization", - JOURNAL = "Biopolymers", - YEAR = 1980, VOLUME = 19, PAGES = "1875-1886"} - -@TECHREPORT{Kinoshita:72, - AUTHOR = "T. Kinoshita and P. Cvitanovic", - TITLE = "Sixth Order Radiative Corrections to the Electron Magnetic Moment", - INSTITUTION = "Cornell Lab. for Nuclear Studies", YEAR = 1972, - TYPE = "Report", NUMBER = "CLNS-197", MONTH = "October"} - -@TECHREPORT{Kinoshita:73, - AUTHOR = "T. Kinoshita and P. Cvitanovic", - TITLE = "Feynman-{Dyson} Rules in Parametric Space", - INSTITUTION = "Cornell Lab. for Nuclear Studies", YEAR = 1973, - TYPE = "Report", NUMBER = "CLNS-209", MONTH = "January"} - -@ARTICLE{Kitatani:86, - AUTHOR = "H. Kitatani and S. Miyashita and M. Suzuki", - TITLE = "Reentrant Phenomena in Some {Ising} Spin Systems - Rigorous -Results and Effects of an External Field", - JOURNAL = "J. Phys. S. Japan", - YEAR = 1986, VOLUME = 55, NUMBER = 3, PAGES = "865-876", - COMMENT = {{REDUCE} used to calculate formula before numerical -calculation.}} - -@ARTICLE{Klimov:93, - AUTHOR = "D. M. Klimov and V. V. Leonov and V. M. Rudenko", - TITLE = "The Study of Motion for a Gyroscope with Gimbal Suspension: -Obtaining the Highest Approximations for a Drift of Magnus", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "73-78", MONTH = "January", - COMMENT = {Here we give a solution to the classic problem of the applied -mechanics of the gyroscope. The problem is reduced to using the computer -algebra system {REDUCE}. We show that symbolic computation is very -convenient for applied mechanics.}} - -@TECHREPORT{Kobayashi:84, - AUTHOR = "Hidestune Kobayashi", - TITLE = "Weierstrass Points on a Curve, $X^{7}_{0}+X^{7}_{1} -+X^{7}_{2}=0$", - INSTITUTION = "Research Institute of Science and Technology, Nihon -University", YEAR = 1984, TYPE = "Preprint", NUMBER = 28, MONTH = "March"} - -@INPROCEEDINGS{Kobayashi:88, - AUTHOR = "H. Kobayashi and S. Moritsugu and R. W. Hogan", - TITLE = "Solving Systems of Algebraic Equations", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "139-149"} - -@INPROCEEDINGS{Kodaira:85, - AUTHOR = "Hiroshi Kodaira and Hiroshi Toshima", - TITLE = "Gini Coefficient of Wealth in Life Cycle Model", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "119-151"} - -@ARTICLE{Koh:82, - AUTHOR = "I. G. Koh and Y. D. Kim and Y. J. Park and C. H. Kim and -Y. S. Kim", - TITLE = "Complete Set of {SU(5)} Monopole Solution", - JOURNAL = "J. Math. Phys.", - YEAR = 1982, VOLUME = 23, PAGES = "1210-1212", - COMMENT = {Calculation checked by {REDUCE} after hand calculation.}} - -@ARTICLE{Koelbig:81, - AUTHOR = "K. S. K{\"o}lbig and F. Schwarz", - TITLE = "On Positive Function Series", - JOURNAL = "Computing", - YEAR = 1981, VOLUME = 27, PAGES = "319-337", - COMMENT = {{REDUCE} for algebra on constraints on a functional form and -Jacobi polynomials.}} - -@ARTICLE{Koelbig:81b, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "A Program for Computing the Conical functions of the -First Kind ${P}^{m}_{-1/2+i\tau}(x)$ for $m = 0$ and $m = 1$", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1981, VOLUME = 23, PAGES = "51-61", - PUBLISHER = "North Holland Publishing Company"} - -@ARTICLE{Koelbig:82, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "Closed Expressions for $\int_{0}^{1} t^{-1} $log$^{n-1}t\, - $log$^{p}(1 - t) dt$", - JOURNAL = "Math. Comp.", - YEAR = 1982, VOLUME = 39, NUMBER = 160, PAGES = "647-654", - MONTH = "October", - COMMENT = {Closed form of integral for easy calculation. Used {REDUCE} for -manipulations. This class includes dilog, Spence functions etc. -Remarks that {REDUCE} is easier than {FORTRAN}.}} - -@ARTICLE{Koelbig:82a, - AUTHOR = "K. S. K{\"o}lbig and W. R{\"u}hl", - TITLE = "Complex Zeros of the Partition Function for -Two-Dimensional {U(N)} Lattice Gauge Theories", - JOURNAL = "Z. Phys. C - Particles and Fields", - YEAR = 1982, VOLUME = 12, PAGES = "135-143", - COMMENT = {The Complex Zeros of the Partition Function for Two-Dimensional -U(N) Lattice Gauge Theories.}} - -@ARTICLE{Koelbig:83, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "On the Integral $\int_{0}^{\pi/2} $log$^{n}$cos$\,x\,$ -log$^{p}$sin$\,x\,dx$", - JOURNAL = "Math. Comp.", - MONTH = "April", - YEAR = 1983, VOLUME = 40, PAGES = "565-570", - COMMENT = {A formula is derived for the integral in the title which allows -easy evaluation by formula manipulation on a computer.}} - -@ARTICLE{Koelbig:83a, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "On the Integral $\int_{0}^{\infty} e^{-\mu t} t^{\nu -1} - $log$^{m} t dt$", - JOURNAL = "Math. Comp.", - YEAR = 1983, VOLUME = 41, PAGES = "171-182", - COMMENT = {A recurrence relation is given for the integral in the title.}} - -@ARTICLE{Koelbig:84, - AUTHOR = "K. S. K{\"o}lbig and B. Schorr", - TITLE = "Asymptotic Expansions for the {Landau} Density and -Distribution Function", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1984, VOLUME = 32, PAGES = "121-131"} - -@ARTICLE{Koelbig:84a, - AUTHOR = "K. S. K{\"o}lbig and B. Schorr", - TITLE = "A Program Package for the {Landau} Distribution", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1984, VOLUME = 31, PAGES = "97-111"} - -@TECHREPORT{Koelbig:84b, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "Some Problems Involving Special Functions -Arising From Physics at {CERN}", - INSTITUTION = "CERN, Data Handling Division", - YEAR = 1984, NUMBER = "DD 84-14", MONTH = "September"} - -@TECHREPORT{Koelbig:85, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "On the Integral $\int_{0}^{1} x^{\nu -1} (1 - x)^{-\lambda} - $ln$^{m} x dx$", - INSTITUTION = "CERN, Data Handling Division", - YEAR = 1985, NUMBER = "DD/85/18", MONTH = "September"} - -@ARTICLE{Koelbig:85a, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "Explicit Evaluation of Certain Definite Integrals Involving -Powers of Logarithms", - JOURNAL = "J. Symbolic Computation", - YEAR = 1985, VOLUME = 1, NUMBER = 1, PAGES = "109-114", MONTH = "March"} - -@ARTICLE{Koelbig:86, - AUTHOR = "K. S. K{\"o}lbig", - TITLE = "On the Integral $\int_{0}^{\infty} x^{\nu -1} - (1 + \beta x)^{-\lambda} $ln$^{m} x dx$", - JOURNAL = "Journal of Comp. and Appl. Math.", - YEAR = 1986, VOLUME = 14, PAGES = "319-344"} - -@TECHREPORT{Koepf:94, - AUTHOR = "Wolfram Koepf and Dieter Schmersau", - TITLE = "Spaces of Functions Satisfying Simple Differential Equations", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1994, MONTH = "March", TYPE = "Preprint", NUMBER = "TR 94-2"} - -@TECHREPORT{Koepf:94a, - AUTHOR = "Wolfram Koepf", - TITLE = "Algebraische Darstellung transzendenter Funktionen (in {German})", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1994, MONTH = "October", TYPE = "Preprint", NUMBER = "SC 94-24"} - -@TECHREPORT{Koepf:94b, - AUTHOR = "Wolfram Koepf", - TITLE = "Algorithms for the Indefinite and Definite Summation", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1994, MONTH = "December", TYPE = "Preprint", NUMBER = "SC 94-33"} - -@ARTICLE{Koepf:95, - AUTHOR = "Wolfram Koepf", - TITLE = "{REDUCE} package for the Indefinite and Definite Summation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1995, VOLUME = 29, NUMBER = 1, PAGES = "14-30", MONTH = "January", -Abstract ={The {REDUCE} package {ZEILBERG} is a careful implementation of -the Gosper and Zeilberger algorithms for indefinite, and definite -summation of hypergeometric terms respectively. An expression $a_k$ is -called a hypergeometric term (or closed form) if $a_k/a_{k-1}$ is a -rational function with respect to $k$. Typical hypergeometric terms are -ratios of products of powers, factorial, Gamma function terms, binomial -coefficients, and shifted factorials (Pochhammer symbols) that are -integer-linear in their arguments. The package covers further extensions -of both Gosper's and Zeilberger's algorithms.}} - -@TECHREPORT{Koepf:95a, - AUTHOR = "Wolfram Koepf", - TITLE = "Identities for families of orthogonal polynomials and special -functions", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1995, MONTH = "January", TYPE = "Preprint", NUMBER = "SC 95-1", - ABSTRACT = {In this article we present new results for families of -orthogonal polynomials and special functions, that are determined by -algorithmical approaches. - -In the first section, we present new results, especially for discrete -families of orthogonal polynomials, obtained by an application of the -celebrated Zeilberger algorithm. - -Next, we present algorithms for holonomic families $f(n,x)$ of special -functions which possess a derivative rule. We call those families -admissible. A family $f(n,x)$ is holonomic if it satisfies a holonomic -recurrence equation with respect to n, and a holonomic differential -equation with respect to x, i.e. linear homogeneous equations with -polynomial coefficients. - -The rather rigid property of admissibility has many interesting -consequences, that can be used to generate and verify identities for these -functions by linear algebra techniques. On the other hand, many families -of special functions, in particular families of orthogonal polynomials, are -admissible. We moreover present a method that generates the derivative -rule from the holonomic representation of a holonomic family. - -As examples, we find new identities for the Jacobi polynomials and for the -Whittaker functions, and for families of discrete orthogonal polynomials by -the given approach. - -Finally, we present representations for the parameter derivatives of the -Gegenbauer and the generalized Laguerre polynomials.}} - -@ARTICLE{Koike:92, - AUTHOR = "F. Koike", - TITLE = "Explicit formulae of angular momentum coupling coefficients", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1992, VOLUME = 72, NUMBERS = "2 and 3", PAGES = "154-164", - MONTH = "November", - COMMENT = {A program has been developed to generate algebraic formulae of -the coupling coefficients of angular momenta. The algebraic programming -system {REDUCE} version 3.3 is used for programming. The program -consists of several {REDUCE} prefix operators. They carry out symbolic -reductions of Clebsch-Gordan coefficients. Racah coefficients, -X-coefficients, and related coefficients. Both variables and values of -angular momentum can be their arguments. The program allows one to use -these operators in the same way as the {REDUCE} built-in operators.}} - -@ARTICLE{Kolar:90, - AUTHOR = "M. Kol{\'a}\u{r} and M. K. Ali", - TITLE = "Trace maps associated with general {two-letter} substitution -rules", - JOURNAL = "Physical Review {A}", - YEAR = 1990, VOLUME = 42, NUMBER = 12, PAGES = "7112-7124", - MONTH = "December", - ABSTRACT = {Spectral properties, as determined by trace maps, of the -one-dimensional chains (layered structures) constructed according to -general two-letter substitution rules are investigated. In all trace maps -thus obtained an important role is played by the quantity -$I=x^{2}+y^{2}+z^{2}-xyz-4$ However, only a very small fraction of all -such trace maps are similar to the Fibonacci golden-mean trace map in that -I is their invariant. In addition to the known case of the precious-mean -lattices (precious means are ratios of the form -$^{1}_{2}[m+(m^{2}+4)^{1/2}]$, m being any positive integer; m=1 gives the -golden mean), we have identified two new large clases of substitution -rules that give trace maps with invariant I. One of them is a superset of -the precious-mean lattices. All other cases represent a vast assortment -of different trace maps (and thus the potential for various hitherto -unexplored spectral properties) with a unifying feature that the set I=0 -plays the role of an attractor in the trace space. In most (but not all) -cases, two chains with identical trace maps (and thus identical spectra) -are locally isomorphic. Generally, local isomorphism equivalence classes -seem to be subsets of identical spectrum equivalence classes.}} - -@TECHREPORT{Kornyak:87, - AUTHOR = "V. V. Kornyak and R. N. Fedorova", - TITLE = "A {REDUCE} Program to Calculate Determining Equations of -{Lie-Baecklund} Symmetries of Differential Equations", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1987, NUMBER = "P11-87-19"} - -@ARTICLE{Kotorynski:86, - AUTHOR = "W. P. Kotorynski", - TITLE = "Steady Laminar Flow Through a Twisted Pipe of Elliptical -Cross-Section", - JOURNAL = "Computers and Fluids", - YEAR = 1986, VOLUME = 14, PAGES = "433-444", - COMMENT = {Used {REDUCE} to perform the calculations for steady flow through -twisted pipes, but who also remarked that the techniques he developed -for this problem are applicable to a variety of other pipe flow tasks.}} - -@ARTICLE{Krack:82, - AUTHOR = "K. Krack", - TITLE = "Rechnerunterst{\"u}tzte {Entwicklung} der {Mittelbreitenformeln} -und Absch{\"a}tzung ihrer ellipsoidischen {Anteile} zur L{\"o}sung der -zweiten geod{\"a}tischen {Hauptaufgabe} auf dem {Rotationsellipsoid}", - JOURNAL = "Z. Vermessungswes.", - YEAR = 1982, VOLUME = 107, PAGES = "502-513", - COMMENT = {(In German) Used {REDUCE} to develop the Gauss mid-latitude -formulae for inverse positioning to the 7th order (Geodesy).}} - -@PHDTHESIS{Kraus:73, - AUTHOR = "J. Kraus", - TITLE = "Delbr{\"u}ckstreuung und Pr{\"u}fung der -Quantenelektrodynamik", - SCHOOL = "Ludwig-Maximilians-Universit{\"a}t zu M{\"u}nchen", - YEAR = 1973} - -@ARTICLE{Kredel:88, - AUTHOR = "Heinz Kredel", - TITLE = "Admissible termorderings used in Computer Algebra Systems", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1988, VOLUME = 22, NUMBER = 1, PAGES = "28-31", MONTH = "January"} - -@ARTICLE{Kruse:83, - AUTHOR = "Hans-Guenther Kruse and Karin Ohlsen", - TITLE = "About the Realization of an Extended, but Really Interactive -{REDUCE} by Integration of a Small Editing and Executing System", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "21-25", MONTH = "February"} - -@TECHREPORT{Kryukov, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", - TITLE = "Usage of {REDUCE} for Computations of Group-Theoretical Weight of -{Feynman} Diagrams in Non-Abelian Gauge Theories", - INSTITUTION = "Institute of Nuclear Physics, Moscow, USSR", YEAR = "TBD"} - -@ARTICLE{Kryukov:84, - AUTHOR = "A. P. Kryukov", - TITLE = "An Antitranslator of the {RLISP} Language", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1984, VOLUME = 18, NUMBER = 3, PAGES = "12-15", MONTH = "August"} - -@ARTICLE{Kryukov:85, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", - TITLE = "Dynamic-Debugging System for the {REDUCE} Programs", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "34-37", MONTH = "May"} - -@ARTICLE{Kryukov:85a, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", - TITLE = "Interactive {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "43-45", MONTH = "August"} - -@TECHREPORT{Kryukov:87, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and V. A. Rostovtsev", - TITLE = "Pattern Compilation in {REDUCE}", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1987, NUMBER = "P11-87-302"} - -@INPROCEEDINGS{Kryukov:87a, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", - TITLE = "{CTS} - Algebraic Debugging System for {REDUCE} Programs", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "233-243", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Kryukov:88, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and V. A. Rostovtsev", - TITLE = "New Programming Tools for Computing Substitution -Rules in {REDUCE} System", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1988, NUMBER = "P11-88-402", - COMMENT = {New programming tools allowing to compile patterns in -{REDUCE} system are described. A guide for using -these tools and examples of their working are presented.}} - -@ARTICLE{Kryukov:88a, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", - TITLE = "Program {``COLOR''} for Computing the Group-Theoretic Weight -of {Feynman} Diagrams in {Non-Abelian} Gauge Theories", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1988, VOLUME = 48, NUMBER = 2, PAGES = "327-334", MONTH = "February"} - -@TECHREPORT{Kryukov:88b, - AUTHOR = "A. P. Kryukov and D. A. Slavnov", - TITLE = "The Role of the $gg \rightarrow c\overline{c}g$ Process in the -Cross Section of Production of Charmed Particles (in {Russian})", - INSTITUTION = "Moscow State University", - YEAR = 1988, NUMBER = "88-49/70", TYPE = "Preprint"} - -@BOOK{Kryukov:91, - AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and A. Yu. Taranov and -E. Shablygin", - TITLE = "Programming in R-Lisp", - PUBLISHER = "Radio and Connective Publishers, Moscow", YEAR = 1991, - ABSTRACT = {Various Lisp dialects become more and more popular as -high-level programming languages. In this book basic Lisp concepts, its -data structures and build in functions are introduced using R-Lisp. -R-Lisp is the implementation language of a famous REDUCE computer algebra -system. All concepts are illustrated by simple but by no means trivial -programming examples. The description of compiler and full function -reference are included. The book will be interesting for beginners as -well as Lisp programmers. In Russian}} - -@TECHREPORT{Kuppers:71, - AUTHOR = "G. Kuppers and D. Pfirsch and H. Tasso", - TITLE = "{M.H.D.} - Stability of Axisymmetric Plasmas", - INSTITUTION = "Max-Planck-Institut fuer Plasmaphysik", - YEAR = 1971, TYPE = "Report", NUMBER = "CN -28/F-14"} - -@ARTICLE{Lambin:84, - AUTHOR = "P. Lambin and J. P. Vigneron", - TITLE = "Computation of Crystal {Green's} Functions in the Complex-Energy -Plane with the Use of the Analytical Tetrahedron Method", - JOURNAL = "Phys. Rev. B", - YEAR = 1984, VOLUME = 29, NUMBER = 6, PAGES = "3430-3437", - COMMENT = {Crystallography, {REDUCE}, quantum theory.}} - -@TECHREPORT{Lang:79, - AUTHOR = "C. B. Lang and W. Porod", - TITLE = "Symmetry Breaking and $\pi$ {K} Amplitudes in the Unphysical -Region", - INSTITUTION = "Institut f{\"u}r Theor. Physik, Univ. Graz", - YEAR = 1979, TYPE = "Report", NUMBER = "UNIGRAZ-UTP 08/79", - ABSTRACT = {We apply two different methods of analytic continuation -(fixed-t and hyperbolic dispersion relations with discrepancy) to -determine the expansion parameters of the pi K amplitudes in the -unphysical region near the symmetry point.}, - COMMENT = {To be published in Phys. Rev. D, September, 1979.}} - -@TECHREPORT{Laursen:79, - AUTHOR = "M. L. Laursen and M. A. Samuel", - TITLE = "The n-Bubble Diagram Contribution to the g-2 of the Electron - -{Mathematical} Structure of the Analytical Expression", - INSTITUTION = "Oklahoma State Univ. Quantum Theoretical Research Group", - YEAR = 1979, TYPE = "Research Note", NUMBER = "96", - ABSTRACT = {We obtain an exact integrated expression for the contribution -of the mass-independent n-bubble diagram to the leptonic g-2.}} - -@TECHREPORT{Laursen:80, - AUTHOR = "Morten L. Laursen and Mark A. Samuel", - TITLE = "Borel Transform Technique and the {n-Bubble} Diagram -Contribution to the Lepton Anomaly", - INSTITUTION = "Oklahoma State Univ. Quantum Theoretical Research Group", - YEAR = 1980, TYPE = "Research Note", NUMBER = 10, MONTH = "August", - ABSTRACT = {By using the {Borel} transform technique we calculate -analytically the muon anomaly from the mass-dependent n-bubble diagram in the -limit where the mass ratio is large.}} - -@ARTICLE{Laursen:81, - AUTHOR = "M. L. Laursen and M. A. Samuel", - TITLE = "The n-bubble Diagram Contribution to g-2", - JOURNAL = "J. Maths. Phys.", - YEAR = 1981, VOLUME = 22, PAGES = "1114-1126", - COMMENT = {Exact integration for contribution to mass indep. {n-bubble} -diagram to {leptonic g-2}. {REDUCE} used to calculate explicitly to {n=13}, -involves summing series and rational coefficients.}} - -@ARTICLE{Lecourtier:85, - AUTHOR = "Y. Lecourtier and A. Raksanyi", - TITLE = "Algebraic Manipulation Routines for Testing Structural Properties", - JOURNAL = "IFAC Identification and System Parameter Estimation", - YEAR = 1985, PAGES = "543-549"} - -@ARTICLE{Lee:85, - AUTHOR = "H-C Lee and M. S. Milgram", - TITLE = "On the Axial Gauge: Ward Identities and the Separation of -Infrared and Ultraviolet Singularities by Analytical Regularization", - JOURNAL = "J. Math. Phys.", - YEAR = 1985, VOLUME = 26, PAGES = "1793-1804", - COMMENT = {Yang-Mills theories on the axial gauge. Uses {SCHOONSCHIP} and -{REDUCE}.}} - -@ARTICLE{Leler:85, - AUTHOR = "Wm Leler and Neil Soiffer", - TITLE = "An Interactive Graphical Interface for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "17-23", MONTH = "August"} - -@ARTICLE{Lepage:83, - AUTHOR = "G. P. Lepage and P. B. Mackenzie and K. H. Streng and -P. M. Zernas", - TITLE = "Multiphoton Decays of Positronium", - JOURNAL = "Phys. Rev. A", - YEAR = 1983, VOLUME = 28, PAGES = "3090-3091", - COMMENT = {Same as Adkins and Brown (1983) but independent of it.}} - -@INPROCEEDINGS{Levi:70, - AUTHOR = "I. Levi and N. Hoff", - TITLE = "Non-Symmetric Creep Buckling of Circular -Cylindrical Shells in Axial Compression", - YEAR = 1970, MONTH = "August", - BOOKTITLE = "Proc. Intern. Symp. in Creep Effect in Structures, -Gotenburg, Sweden"} - -@INPROCEEDINGS{Levi:71, - AUTHOR = "I. M. Levi", - TITLE = "Symbolic Algebra by Computer - Applications to -Structural Mechanics", - YEAR = 1971, MONTH = "April", - BOOKTITLE = "{AIAA/ASME} 12th Structures, Structural Dynamics -and Materials Conference, Anaheim, California"} - -@ARTICLE{Liebermann:75, - AUTHOR = "R. Liebermann", - TITLE = "Traces of High Energy Processes in Strong Magnetic Fields", - JOURNAL = "J. Comp. Phys.", - YEAR = 1975} - -@ARTICLE{Liska:84, - AUTHOR = "R. Liska", - TITLE = "Program for Stability and Accuracy Analysis of -Finite Difference Methods", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1984, VOLUME = 34, PAGES = "175-186"} - -@INPROCEEDINGS{Liska:87, - AUTHOR = "R. Liska and D. Drska", - TITLE = "Evaluation of Plasma Fluid Equations Collision Integrals Using -{REDUCE}", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = 178, - PUBLISHER = "Springer-Verlag"} - -@InProceedings{Liska90, - author = "R. Liska and L. Drska", - title = "{FIDE}: A {REDUCE} package for automation of {FI}nite - difference method for solving {pDE}", - booktitle = "Proceedings of the 1990 International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "169-176", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@INPROCEEDINGS{Liska:91, - AUTHOR = "Richard Liska and Michail Yu. Shashkov", - TITLE = "Algorithms for Difference Schemes Construction on Non-orthogonal -Logically Rectangular Meshes", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", - PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "419-426", - YEAR = 1991, - ABSTRACT = {The paper deals with the formalization of the basic operator -method for construction of difference schemes for the numerical solving -of partial differential equations. The strength of the basic operator -method lies on the fact that it produces fully conservative difference -schemes. The difference mesh can be non-orthogonal but has to be logically -orthogonal. Algorithms for working with grid functions and grid operators -in symbolic form which are necessary in the basic operator method are -described. The algorithms have been implemented in the computer algebra -system REDUCE.}} - -@ARTICLE{Lloyd:90, - AUTHOR = "N. G. Lloyd and J. M. Pearson", - TITLE = "{REDUCE} and the Bifurcation of Limit Cycles", - JOURNAL = "J. Symbolic Computation", - YEAR = 1990, VOLUME = 9, NUMBER = 2, PAGES = "215-224", MONTH = "February"} - -@INPROCEEDINGS{Loe:85, - AUTHOR = "Kia Fock Loe and Noritaka Ohsawa and Eiichi Goto", - TITLE = "Circuit Simulation Code Generation by Computer Algebra", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "87-103"} - -@INPROCEEDINGS{London:74, - AUTHOR = "R. London and D. R. Musser", - TITLE = "The Application of a Symbolic Mathematical System -to Program Verification", - YEAR = 1974, PAGES = "265-273", - BOOKTITLE = "Proc. {ACM} 74"} - -@ARTICLE{Loos:72, - AUTHOR = "R{\"u}diger Loos", - TITLE = "Analytic Treatment of Three Similar {Fredholm} Integral -Equations", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1972, VOLUME = 11, PAGES = "32-40", - ABSTRACT = {A {REDUCE} solution to {SIGSAM} Problem \#1 is presented.}} - -@INPROCEEDINGS{Lottati, - AUTHOR = "Itzhak Lottati and Isaac Elishakoff", - TITLE = "Refined Dynamical Theories of Beams, Plates -and Shells and Their Applications", - BOOKTITLE = "Proc. Euromech-Colloquium 219"} - -@ARTICLE{Louw:86, - AUTHOR = "J. A. Louw and F. Schwarz and W. H. Steeb", - TITLE = "First Integrals and {Yoshida} Analysis of {Nahm}'s Equation", - JOURNAL = "J. Phys. A", - YEAR = 1986, VOLUME = 19, PAGES = "L569-L573", - COMMENT = {Monopole solutions in Yang-Mills theories explicitely given in -special cases. {REDUCE} used for polynomial first integrals and -Kowalewski exponents. An application of spde.}} - -@ARTICLE{Luegger:73, - AUTHOR = "J. Luegger and H. Melenk", - TITLE = "Darstellung und {Bearbeitung} Umfangreicher {LISP-Programme}", - JOURNAL = "Angewandte Informatik", - YEAR = 1973, MONTH = "June", PAGES = "257-263"} - -@TECHREPORT{Luegger:91, - AUTHOR = "Joachim L{\"u}gger and Wolfgang Dalitz", - TITLE = "Verteilung mathematischer {Software} mittels elektronischer -{Netze:} {Die} elektronische {Softwarebibliothek} {eLib}", - INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", - YEAR = 1991, MONTH = "February", TYPE = "Preprint", NUMBER = "TR 91-2"} - -@TECHREPORT{Lukacs, - AUTHOR = "B. Luk{\'a}cs and Z. Perj{\'e}s and -A. Sebesty{\'e}n and A. Valentini", - TITLE = "Stationary Vacuum Fields with a Conformally Flat -Three-Space, II. Proof of Axial Symmetry", - INSTITUTION = "Central Research Institute for Physics, -Budapest, Hungary", - YEAR = 1982, NUMBER = "KFKI-1982-19"} - -@ARTICLE{Lukaszuk:87, - AUTHOR = "L. L{\'u}kaszuk and D. M. Siemienczuk and L. Szymanowski", - TITLE = "Evaluation of Helicity Amplitudes", - JOURNAL = "Phys. Rev. D", - YEAR = 1987, VOLUME = 35, PAGES = "326-329"} - -@PHDTHESIS{Lux:75, - AUTHOR = "Augustin Lux", - TITLE = "Etude d'un Modele Abstrait pour une Machine {LISP} et de -son Implantation", - SCHOOL = "Universit{\'e} Scientifique et Medicale de Grenoble", - YEAR = 1975, MONTH = "March", - COMMENT = {Thesis presented to Universit{\'e} Scientifique et Medicale de -Grenoble, Institut National Polytechnique de Grenoble.}} - -@BOOK{MacCallum:86, - AUTHOR = "M. A. H. MacCallum", - TITLE = "Dynamical Spacetimes and Numerical Relativity", - PUBLISHER = "Cambridge University Press", YEAR = 1986} - -@TECHREPORT{MacCallum:86a, - AUTHOR = "M. A. H. MacCallum", - TITLE = "Algebraic Computing in Relativity", - INSTITUTION = "Queen Mary College, University of London", - YEAR = 1986, NUMBER = "TAU 86-04"} - -@INPROCEEDINGS{MacCallum:87, - AUTHOR = "M. A. H. MacCallum", - TITLE = "Symbolic Computation in Relativity Theory", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "34-43", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{MacCallum:88, - AUTHOR = "M. A. H. MacCallum", - TITLE = "An Ordinary Differential Equation Solver for {REDUCE}", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "196-205"} - -@ARTICLE{MacCallum:89, - AUTHOR = "Malcolm A. H. MacCallum", - TITLE = "Comments on the performance of algebra systems in general -relativity and a recent paper by {Nielsen} and {Pedersen}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1989, VOLUME = 23, NUMBER = 2, PAGES = "22-25", MONTH = "April"} - -@BOOK{MacCallum:91, - AUTHOR = "Malcolm MacCallum and Francis Wright", - TITLE = "Algebraic Computing with {REDUCE}", - PUBLISHER = "Oxford University Press", YEAR = 1991, - ISBN = "0-19-853444-2, 0-19-853443-4 (paperback)"} - -@ARTICLE{MacCallum:92, - AUTHOR = "M. A. H. MacCallum and S. T. C. Siklos", - TITLE = "Algebraically special hypersurface-homogeneous {Einstein} spaces -in general relativity", - JOURNAL = "Journal of Geometry and Physics", - YEAR = 1992, VOLUME = 8, PAGES = "221-242"} - -@BOOK{MacDonald:94, - AUTHOR = "N. MacDonald", - TITLE = "{REDUCE} for Physics", - PUBLISHER = "Institute of Physics Publishing", - ADDRESS = "Bristol, England", - YEAR = 1994, MONTH = "March", - NOTE = "ISBN 0 7503 0277 1", - COMMENT = {This book provides an introduction to {REDUCE} with the needs -of physicists primarily in mind. Each chapter introduces some aspects of -{REDUCE} and illustrates them with applications from various branches of -physics including mechanics, dynamics, dimensional analysis, quantum -mechanics, plasma physics. Exercises to test understanding are included -throughout. The emphasis is on hands-on working with {REDUCE} as a tool to -tackle real physical problems. The book takes account of changes to -{REDUCE} for Version 3.4. -Students and researchers in the physical sciences and engineering using -{REDUCE} for the first time should find this book useful.}} - -@PHDTHESIS{Mack:73, - AUTHOR = "D. Mack", - TITLE = "Nichtnumerische Verfahren und deren Anwendung -in der Elementarteilchen-Physik", - SCHOOL = "University of Tuebingen", - YEAR = 1973} - -@ARTICLE{Mack:73a, - AUTHOR = "D. Mack and H. Mitter", - TITLE = "Calculation of Electron-Electron-Bremsstrahlung Cross-Sections", - JOURNAL = "Phys. Lett.", - YEAR = 1973, VOLUME = "44A", PAGES = "71-72"} - -@ARTICLE{Maclaren:89, - AUTHOR = "N. M. Maclaren", - TITLE = "The Generation of Sequences of Multiple Independent Sequences -of Pseudorandom Numbers", - JOURNAL = "Applied Statistics {JRSS Series C}", - YEAR = 1989, VOLUME = 38, NUMBERS = 2, PAGES = "351-359"} - -@MASTERSTHESIS{Maguire:81, - AUTHOR = "Gerald Quentin {Maguire Jr.}", - TITLE = "Program Transformation in {REDUCE} Using Rule Sequencing", - SCHOOL = "Department of Computer Science, The University of Utah", - YEAR = 1981, MONTH = "March"} - -@INPROCEEDINGS{Malm:82, - AUTHOR = "Bengt Malm", - TITLE = "A Program in {REDUCE} for Finding Explicit Solutions", - BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes -in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "289-293", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Man:93, - AUTHOR = "Yiu-Kwong Man", - TITLE = "On Computing Closed Forms for Indefinite Summations", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, MONTH = "October", VOLUME = 16, NUMBER = 4, PAGES = "355 - 376", - COMMENT = {A decision procedure for finding closed forms for indefinite -summation of polynomials, rational functions, quasipolynomials and -quasirational functions is presented. It is also extended to deal with -some non-hypergeometric sums with rational inputs, which are not summable -by means of Gosper's algorithm. Discussion of its implementation, analysis -of degree bounds and some illustrative examples are included.}} - -@ARTICLE{Man:93a, - AUTHOR = "Yiu-Kwong Man", - TITLE = "Computing Closed Form Solutions of First Order {ODE}s Using the -{Prelle-Singer} Procedure", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, MONTH = "November", VOLUME = 16, NUMBER = 5, PAGES = "423 - 443", - COMMENT = {The {Prelle-Singer} procedure is an important method for formal -solution of first order ODEs. Two different REDUCE implementations (PSODE -versions 1 & 2) of this procedure are presented in this paper. The aim is -to investigate which implementation is more efficient in solving different -types of ODEs (such as exact, linear, separable, linear in coefficients, -homogeneous or Bernoulli equations). The test pool is based on Kamke's -collection of first order and first degree ODEs. Experimental results, -timings and comparison of efficiency and solvability with the present -REDUCE differential equation solver (ODESOLVE) and a MACSYMA implementation -(ODEFI) of the {Prelle-Singer} procedure are provided. Discussion of -technical difficulties and some illustrative examples are also included.}} - -@InProceedings{Man:94, - author = {Yiu-Kwong Man and Francis J. Wright}, - title = {Fast Polynomial Dispersion Computation and its - Application to Indefinite Summation}, - booktitle = {Symbolic and Algebraic Computation}, - editor = {}, - series = {ISSAC}, - year = {1994}, - organization = {SIGSAM}, - publisher = {ACM}, - pages = {175--180} -} - -@ARTICLE{Marti:78, - AUTHOR = "Jed Marti", - TITLE = "The {META/REDUCE} Translator Writing System", - JOURNAL = "Sigplan Notices", - YEAR = 1978, VOLUME = 13, PAGES = "42-49", - COMMENT = {The {META/REDUCE} translator writing system operates in a -{LISP} and {REDUCE} syntax. The language supports: {BNF} like syntax, -recursive descent parsing schemes, lexical primitives, symbol table -primitives and automatic syntax error message generation.}} - -@ARTICLE{Marti:79, - AUTHOR = "J. B. Marti and A. C. Hearn and M. L. Griss and C. Griss", - TITLE = "Standard {Lisp} Report", - JOURNAL = "Sigplan Notices, ACM", - YEAR = 1979, VOLUME = 14, NUMBER = 10, PAGES = "48-68", - ABSTRACT = {A description of Standard {LISP} primitive data structures and -functions is presented.}} - -@ARTICLE{Marti:80, - AUTHOR = "J. Marti and A. C. Hearn and M. L. Griss and C. Griss", - TITLE = "Standard {Lisp} Report", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1980, VOLUME = 14, NUMBER = 1, PAGES = "23-41", MONTH = "February"} - -@ARTICLE{Marti:83, - AUTHOR = "Jed Marti and John Fitch", - TITLE = "{REDUCE} 2 for {CP/M}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "26-27", MONTH = "February"} - -@ARTICLE{Marti:85, - AUTHOR = "Jed B. Marti and Anthony C. Hearn", - TITLE = "{REDUCE} as a {LISP} Benchmark", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "8-16", MONTH = "August"} - -@INPROCEEDINGS{Marti:85a, - AUTHOR = "Jed B. Marti", - TITLE = "The Role of Explanation in Symbolic Computation", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "13-34"} - -@INPROCEEDINGS{Marti:88, - AUTHOR = "J. Marti", - TITLE = "A Graphics Interface to {REDUCE}", - BOOKTITLE = "Proc. {AAECC-6} 1988, Lecture Notes in Computer Science", - YEAR = 1988, VOLUME = 357, PAGES = "274-296", - PUBLISHER = "Springer-Verlag"} - -@BOOK{Marti:93a, - AUTHOR = "Jed Marti", - TITLE = "{RLISP} '88 An Evolutionary Approach to Program Design and Reuse", - PUBLISHER = "World Scientific", - ADDRESS = "Singapore", - YEAR = 1993, - NOTE = "SBN 981-02-14790"} - -@INPROCEEDINGS{Marzinkewitsch:91, - AUTHOR = "Reiner Marzinkewitsch", - TITLE = "Operating Computer Algebra Systems by Handprinted Input", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "411-413", YEAR = 1991, - ABSTRACT = {A prototype of a workstation is presented for calculation -with mathematical formulas by hand and support by computer algebra systems. -Keywords: Character recognition, neural network, computer algebra system, -context free grammar, parsing of two dimensional structures.}} - -@ARTICLE{Matveev:87, - AUTHOR = "V. A. Matveev and Ya. Z. Darbaidze and -Z. V. Merebashvili and L. A. Slepchenko", - TITLE = "Gluon Fusion in {SUSY QCD}", - JOURNAL = "Phys. Lett. B", - YEAR = 1987, VOLUME = 191, NUMBER = "1 and 2", PAGES = "179-181", - MONTH = "June"} - -@ARTICLE{Maurer:86, - AUTHOR = "M. Maurer and A. Hayd and H. J. Kaeppeler", - TITLE = "Quasi-Analytical Method for Solving Nonlinear Differential -Equations for Turbulent Self-Confined Magneto-Plasma", - JOURNAL = "J. Comp. Phys.", - YEAR = 1986, VOLUME = 66, PAGES = "151-172", - COMMENT = {Mixed {REDUCE} and {FORTRAN}. Enthusiastic about this style of -mixed working.}} - -@TECHREPORT{Mazepa:85, - AUTHOR = "N. E. Mazepa and S. I. Serdyukova", - TITLE = "The Stability Investigation of Some Difference Boundary Problem -with the Application of Symbolic Computation System", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1985, NUMBER = "E5-85-39"} - -@ARTICLE{Mazzarella:85, - AUTHOR = "Giuseppe Mazzarella", - TITLE = "Improved Simplification of Odd and Even Functions in {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "29-30", MONTH = "May"} - -@ARTICLE{McCrea:81, - AUTHOR = "J. D. McCrea", - TITLE = "The {Petrov} Type of a Static Vacuum Spacetime Near a -Normal-Dominated Singularity", - JOURNAL = "J. Phys.", - YEAR = 1981, VOLUME = "A14", PAGES = "1351-1356"} - -@ARTICLE{McCrea:82, - AUTHOR = "J. D. McCrea", - TITLE = "A Stationary Cylindrically Symmetric Electrovac Spacetime", - JOURNAL = "J. Phys.", - YEAR = 1982, VOLUME = "A15", PAGES = "1587-1590"} - -@ARTICLE{McCrea:83, - AUTHOR = "J. D. McCrea", - TITLE = "Static, Vacuum, Cylindrical and Plane Symmetric Solutions -of the Quadratic {Poincar{\'e}} Gauge Field Equations", - JOURNAL = "J. Phys.", - YEAR = 1983, VOLUME = "A16", PAGES = "997-1004"} - -@ARTICLE{McCrea:84, - AUTHOR = "J. D. McCrea", - TITLE = "A {NUT}-Like Solution of the Quadratic-{Poincar{\'e}} Gauge -Field Equations", - JOURNAL = "Phys. Lett.", - YEAR = 1984, VOLUME = "100A", PAGES = "397-399"} - -@INPROCEEDINGS{McCrea:84a, - AUTHOR = "J. D. McCrea", - TITLE = "The Use of {REDUCE} in Finding Exact Solutions of the -Quadratic {Poincar{\'e}} Gauge Field Equations", - BOOKTITLE = "Classical General Relativity", - PUBLISHER = "Cambridge University", YEAR = 1984, PAGES = "173-182"} - -@INPROCEEDINGS{McCrea:87, - AUTHOR = "J. D. McCrea", - TITLE = "{Poincar{\'e}} Gauge Theory of Gravitation: Foundations, -Exact Solutions and Computer Algebra", - YEAR = 1987, PAGES = "16", - BOOKTITLE = "Differential Geometric Methods in Mathematical -Physics, Proc. {14th} International Conference, -Salamanca, 1985 (Springer Lecture Notes in Mathematics, No. 1251)"} - -@ARTICLE{McCrea:87a, - AUTHOR = "J. D. McCrea and P. Baekler and M. Guerses", - TITLE = "A {Kerr}-Like Solution of the {Poincar{\'e}} Gauge Field -Equations", - JOURNAL = "Il Nuovo Cim", - YEAR = 1987, VOLUME = "99B", PAGES = "171-177"} - -@ARTICLE{McCrea:88, - AUTHOR = "J. D. McCrea and E. W. Mielke and F. W. Hehl", - TITLE = "A Remark on the Axisymmetric {Chen} et al. Solution of the -{Poincar{\'e}} Gauge Theory", - JOURNAL = "Phys. Lett.", - YEAR = 1988, VOLUME = "127A", PAGES = "65-69"} - -@ARTICLE{McIsaac:85, - AUTHOR = "Kevin McIsaac", - TITLE = "Pattern Matching Algebraic Identities", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "4-13", MONTH = "May"} - -@TECHREPORT{Melenk:88, - AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", - TITLE = "On {Gr{\"o}bner} Bases Computation on a Supercomputer -Using {REDUCE}", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik -Berlin", - YEAR = 1988, TYPE = "Preprint", NUMBER = "SC 88-2", MONTH = "January"} - -@ARTICLE{Melenk:89, - AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", - TITLE = "Symbolic Solution of Large Stationary Chemical -Kinetics Problems", - JOURNAL = "Impact of Computing in Science and Engineering", - YEAR = 1989, VOLUME = 1, NUMBER = 2, PAGES = "138-167", MONTH = "June"} - -@TECHREPORT{Melenk:89a, - AUTHOR = "Herbert Melenk and Winfried Neun", - TITLE = "Implementation of {Portable Standard LISP} for the {SPARC} -Processor", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1989, TYPE = "Preprint", NUMBER = "SC 89-6", MONTH = "July"} - -@ARTICLE{Melenk:89b, - AUTHOR = "Herbert Melenk and Winfried Neun", - TITLE = "Parallel Polynomial Operations in the Large {Buchberger} -Algorithm", - JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora -and J. Fitch", - YEAR = 1989, PAGES = "143-158", PUBLISHER = "Academic Press, London"} - -@ARTICLE{Melenk:90, - AUTHOR = "H. Melenk", - TITLE = "Solving Polynomial Equation Systems by {Groebner} Type Methods", - JOURNAL = "CWI Quarterly", - YEAR = 1990, VOLUME = 3, NUMBER = 2, PAGES = "121-136", MONTH = "June"} - -@INPROCEEDINGS{Melenk:91, - AUTHOR = "H. Melenk", - TITLE = "Practical Application of {Gr{\"o}bner} Bases for the Solution - of Polynomial Equation Systems", - BOOKTITLE = "IV. International Conference on Computer Algebra in - Physical Research, 1990", - EDITOR = "D. V. Shirkov, V. A. Tostovtsev, V. P. Gerdt", - YEAR = "1991", PAGES = "230-235", PUBLISHER="World Scientific", - ADDRESS="Singapore"} - -@TECHREPORT{Melenk:93, - AUTHOR = "Herbert Melenk", - TITLE = "Algebraic Solution of Nonlinear Equation Systems in {REDUCE}", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1993, TYPE = "Preprint", NUMBER = "TR 93-2", MONTH = "January"} - -@InProceedings{Melenk:93a, - author = "H. Melenk", - title = "Automatic Symbolic Solution of Nonlinear Equation Systems in - {REDUCE}", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "175-180", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - comment = {Mathematical background and algorithmic structure of the - nonlinear system part of the {REDUCE} 3.4.1 SOLVE package.} -} - -@TECHREPORT{Melenk:94, - AUTHOR = "Herbert Melenk", - TITLE = "The Complexity Barrier in {REDUCE} a Case Study", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1994, TYPE = "Preprint", NUMBER = "TR 94-6", MONTH = "January"} - -@ARTICLE{melfo:92, - AUTHOR = "A. Melfo and L. A. N\'u\~nez", - TITLE = "Checking Collineation Vectors with {REDUCE}", - JOURNAL = "Gen. Rel. Grav.", - YEAR = "1992", - VOLUME = "24", - NUMBER = "11", - PAGES = "1125--1129", - NOTE = "A package of programs for writing and checking the solutions -to the equations for various types of collineations (symmetries of the -metric, christoffel, riemman and ricci tensors) is presented. Some -examples of previously found collineations that have been checked are -given, and new results reported."} - -@ARTICLE{Mirie:84, - AUTHOR = "R. M. Mirie and C. H. Su", - TITLE = "Internal Solitary Waves and Their Head-On Collision Part I", - JOURNAL = "J. Fluid Mechanics", - YEAR = 1984, VOLUME = 147, PAGES = "213-231", - COMMENT = {Lengthy calculation "acknowledge the use of {REDUCE-2}." -Perturbation and integration.}} - -@INPROCEEDINGS{Molenkamp:91, - AUTHOR = "J.H.J. Molenkamp and V.V. Goldman and J.A. van Hulzen", - TITLE = "An Improved Approach to Automatic Error Cumulation Control", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "414-418", YEAR = 1991, - ABSTRACT = {For evaluation of arithmetical expressions using multiple -precision floating-point arithmetic, a method is given to automatically -perform error cumulation control prior to the actual computations. -Individual errors and their effects are identified, and it is shown how to -compute these effects efficiently via automatic differentiation. In the -presented approach these effects are used to determine which precisions have -to be chosen during the real computations, in order to limit error cumulation -to admissible, user chosen error bounds.}} - -@TECHREPORT{Moller:89, - AUTHOR = "H. Michael M{\"o}ller", - TITLE = "Multivariate Rational Interpolation Reconstruction of Rational -Functions", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik -Berlin", - YEAR = 1989, TYPE = "Preprint", NUMBER = "SC 89-4", MONTH = "July"} - -@TECHREPORT{Moller:92, - AUTHOR = "H. Michael M{\"o}ller", - TITLE = "On Decomposing Systems of Polynomial Equations With Finitely -Many Solutions", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik -Berlin", - YEAR = 1992, TYPE = "Preprint", NUMBER = "SC 92-15", MONTH = "June"} - -@INPROCEEDINGS{Moritsugu:85, - AUTHOR = "S. Moritsugu and N. Inada and E. Goto", - TITLE = "Symbolic {Newton} Iteration and its Application", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "105-117"} - -@TECHREPORT{Moritsugu:88, - AUTHOR = "S. Moritsugu and E. Goto", - TITLE = "A Proposal for Improvement of Facilities of {REDUCE}", - INSTITUTION = "Department of Information Science, -University of Tokyo, Japan", - YEAR = 1988, MONTH = "December"} - -@ARTICLE{Moritsugu:89, - AUTHOR = "Shuichi Moritsugu and Eiichi Goto", - TITLE = "A Note on the Preconditioning for Factorization of Homogeneous -Polynomials", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1989, VOLUME = 23, NUMBER = 1, PAGES = "9-12", MONTH = "January"} - -@ARTICLE{Moritsugu:89a, - AUTHOR = "Shuichi Moritsugu and Makoto Matsumoto", - TITLE = "A Note on the Numerical Evaluation of Arctangent Function", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1989, VOLUME = 23, NUMBER = 3, PAGES = "8-12", MONTH = "July"} - -@ARTICLE{Muroa:91, - AUTHOR = "Hirokazu Murao", - TITLE = "Vectorization of symbolic determinant calculation", - JOURNAL = "Supercomputer", - YEAR = 1991, VOLUME = "43,VIII-3", PAGES = "36-48"} - -@ARTICLE{Mueller:81, - AUTHOR = "R. M{\"u}ller and H. J. W. M{\"u}ller-Kirsten", - TITLE = "Iteration of Single- and Two-Channel {Schr{\"o}dinger} Equations", - JOURNAL = "J. Math. Phys.", - YEAR = 1981, VOLUME = 22, PAGES = "733-749", - ABSTRACT = {{\dots} we describe an iteration procedure which has already -been applied to a large number of other problems. With the help of -{REDUCE} it is now possible to do these algebraic computations on the -computer, so that the necessary expressions are obtained within a -reasonable time.}} - -@InProceedings{Mueller-Hoissen:93, - author = "F. Mueller-Hoissen", - title = "Noncommutative Differential Calculus, Quantum Groups and - Computer Algebra", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "97-102", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France" -} - -@ARTICLE{Murzin:85, - AUTHOR = "F. A. Murzin", - TITLE = "Syntactic Properties of the {REFAL} Language", - JOURNAL = "Int. J. Computer Maths.", - YEAR = 1985, VOLUME = 17, PAGES = "123-139", - COMMENT = {{SNOBOL-like} special purpose algebra system. Designed for -Cartan work. "{REFAL} is rather an unusual programming language. It is -natural to ask in which situations it is useful." Concludes {MACSYMA} -or {REDUCE} for standard manipulations, {REFAL} for nonstandard.}} - -@TECHREPORT{Nagata:82, - AUTHOR = "Morio Nagata and Makoto Shibayama", - TITLE = "{COSMOS:} A Conversational Algebraic System", - INSTITUTION = "Department of Administration Engineering, -Keio University", - YEAR = 1982, TYPE = "Technical Report", NUMBER = "No. 8201", - MONTH = "March"} - -@INPROCEEDINGS{Nagata:85, - AUTHOR = "Morio Nagata and Makoto Shibayama", - TITLE = "An Interactive Algebraic System for Personal Computing", - YEAR = 1985, - BOOKTITLE = "IEEE International Symposium on New Directions -in Computing"} - -@BOOK{Nakamura:89, - AUTHOR = "Hideharu Nakamura and Shouichi Matsui", - TITLE = "Symbolic Computation in Structural Mechanics using {REDUCE}", - PUBLISHER = "Gihodo Shuppan Company Ltd.", ADDRESS = "1-11-41, -Akasaka, Minato-Ku, 107 Tokyo, {Japan}", YEAR = 1989} - -@ARTICLE{Nakashima:84, - AUTHOR = "T. T. Nakashima and R. E. D. McClung and B. K. John", - TITLE = "A Simple Method for the Determination of the Deuterium -Decoupler Pulse Angle", - JOURNAL = "J. Magnetic Resonance", - YEAR = 1984, VOLUME = 56, PAGES = "262-274", - COMMENT = {{REDUCE} used in theoretical part. "All density matrix -calculations presented here were performed on a digital computer using -REDUCE-2." Essentially matrix products.}} - -@ARTICLE{Nakashima:84a, - AUTHOR = "T. T. Nakashima and R. E. D. McClung and B. K. John", - TITLE = "Experimental and Theoretical Investigation of -$_{2}D-_{13}C$ DEPT Spectra on $CD_{N}$", -JOURNAL = "J. Magnetic Resonance", - YEAR = 1984, VOLUME = 58, PAGES = "27-36", - COMMENT = {"All calculations were performed using {REDUCE-2}."}} - -@ARTICLE{Namba:86, - AUTHOR = "Kenji Namba", - TITLE = "Some Improvements on {Utah} {Standard} {Lisp}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "29-36", - MONTH = "February and May"} - -@ARTICLE{Nemeth:82, - AUTHOR = "G. N{\'e}meth and M. Zim{\'a}nyi", - TITLE = "Polynomial Type {Pad\'e} Approximants", - JOURNAL = "Math. Comp.", - YEAR = 1982, VOLUME = 38, PAGES = "553-565", - COMMENT = {Looking for approximants where $R_{n}(x)$ is -$P_{n}(x)$/P_{n-1}(x)$. Applied in special functions. Used -REDUCE and FORMAC mainly for bignum calculations.}} - -@INPROCEEDINGS{Nemeth:87, - AUTHOR = "G. N{\'e}meth and M. Zim{\'a}nyi", - TITLE = "Computation of Generalized {Pad\'e} Approximants", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "450-451", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Neun:89, - AUTHOR = "W. Neun and H. Melenk", - TITLE = "Implementation of the {LISP-}Arbitrary Precision Arithmetic -for a vector Processor", - JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora -and J. Fitch", - YEAR = 1989, PAGES = "75-89", PUBLISHER = "Academic Press, London"} - -@ARTICLE{Neutsch:85, - AUTHOR = "W. Neutsch and E. Schr{\"u}fer and A. Jessner", - TITLE = "Note on Efficient Integration on the Hypersphere", - JOURNAL = "J. Comp. Phys.", - YEAR = 1985, VOLUME = 59, PAGES = "167-175", - COMMENT = {{REDUCE} used for integration on 4-D hypersphere. {REDUCE} -use rather small.}} - -@ARTICLE{Neutsch:86, - AUTHOR = "W. Neutsch and E. Schr{\"u}fer", - TITLE = "Simple Integrals for Solving {Kepler}'s Equation", - JOURNAL = "Astrophysics and Space Science", - YEAR = 1986, VOLUME = 125, PAGES = "77-83", - COMMENT = {Uses {REDUCE} to verify calculations to give integral form which -is numerically good, involving only rationals and exponentials.}} - -@ARTICLE{Ng:89, - AUTHOR = "Tze Beng Ng", - TITLE = "Computation of the Cohomology of ${B\hat{S}O_{n}<16>}$ for -$23 \leq n \leq 26$ using {REDUCE}", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 7, NUMBER = 1, PAGES = "93-99", MONTH = "January"} - -@ARTICLE{Niki:84, - AUTHOR = "Naoto Niki and Sadanori Konishi", - TITLE = "Higher Order Asymptotic Expansions for the -Distribution of the Sample Correlation Coefficient", - JOURNAL = "Comm. Statist.-Simula. Comp.", - YEAR = 1984, VOLUME = 13, NUMBER = 2, PAGES = "169-182"} - -@TECHREPORT{Nikityuk:87, - AUTHOR = "N. M. Nikityuk", - TITLE = "Some Questions of Using Coding Theory and Analytical -Calculation Methods on Computers", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1987, NUMBER = "E11-87-10"} - -@ARTICLE{Noor:79, - AUTHOR = "A. K. Noor and C. M. Andersen", - TITLE = "Computerized Symbolic Manipulation in Structural Mechanics - -Progress and Potential", - JOURNAL = "Computers and Structures", - YEAR = 1979, VOLUME = 10, PAGES = "95-118", - COMMENT = {Concentrates on {MACSYMA} but mentions {FORMAC} and {REDUCE} -as also having been used in structures. Mainly finite elements. Includes -program and output.}} - -@INPROCEEDINGS{Norman:77, - AUTHOR = "A. C. Norman and P. M. A. Moore", - TITLE = "Implementing the New {Risch} Integration Algorithm", - YEAR = 1977, MONTH = "March", - BOOKTITLE = "Proc. of the Fourth Colloquium on Advanced Comp. -Methods in Theor. Phys., St. Maximin, France"} - -@ARTICLE{Norman:78, - AUTHOR = "Arthur Norman", - TITLE = "Towards a {REDUCE} solution to {SIGSAM} Problem 7", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1978, VOLUME = 12, NUMBER = 4, PAGES = "14-18", MONTH = "November"} - -@INPROCEEDINGS{Norman:79, - AUTHOR = "A. C. Norman and J. H. Davenport", - TITLE = "Symbolic Integration - The Dust Settles?", - BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes -in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "398-407", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Norman:83, - AUTHOR = "Arthur C. Norman and Paul S. Wang", - TITLE = "A Comparison of {Vaxima} and {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "28-30", - MONTH = "February"} - -@InProceedings{Norman90, - author = "A. C. Norman", - title = "A Critical-Pair/Completion based Integration Algorithm", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "201-205", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@INPROCEEDINGS{Norman:93, - AUTHOR = "A. C. Norman", - TITLE = "Compact Delivery Support for {REDUCE}", - BOOKTITLE = "Proc. {DISCO '93}, Lecture Notes on Comp. Science", - YEAR = 1993, VOLUME = 722, PAGES = "331-340", - PUBLISHER = "Springer-Verlag", - ABSTRACT = {The {CSL} Lisp system is one designed primarily for delivering -Lisp applications to users. It thus emphasises robustness, portability and -small size rather than support for an integrated programming environment. -Both portability and compactness are served by making CSL compile the bulk -of applications code into a compact byte-code instruction set which is then -emulated. The speed penalities inherent in this are offset by providing -instrumentation that makes it easy to identify code hot-spots, and a second -compiler that translates critical parts of the original Lisp into C for -incorporation in the CSL kernel. For use with REDUCE it is found that -compiling about 5% of the source code into C led to overall performance -competetive with other Lisp implementations.}} - -@ARTICLE{Norman:95, - AUTHOR = "A.C. Norman", - TITLE = "Compact Delivery Support for {REDUCE}", - JOURNAL = "Journ. Symbolic Computation", - YEAR = 1995, VOLUME=19, PAGES = "133-143", - ABSTRACT = "{CSL} is a {Lisp} system specifically designed to support the -{REDUCE} algebra system. This paper views the {Lisp} system upon which a -{Lisp-coded} algebra system is coded as in effect a micro-kernel -- it -provides basic compilation, storage management and extended arithmetic -capabilities that algebra needs, but is not much concerned with higher level -algebraic algorithms or with user interfaces. The description of {CSL} -given here discusses the major design decisions embodied in the system, and -shows the extent to which it has been possible to resolve conflicting goals -of simplicity, small size, portability and high performance."} - -@ARTICLE{Norton:80, - AUTHOR = "Lewis M. Norton", - TITLE = "A Note About {Laplace} Transform Tables for Computer Use", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1980, VOLUME = 14, NUMBER = 2, PAGES = "30-31", MONTH = "May"} - -@TECHREPORT{Nucci:90, - AUTHOR = "M. C. Nucci", - TITLE = "Interactive {REDUCE} Programs for Calculating Classical, -Non-Classical and {Lie-B{\"a}cklund} Symmetries of Differential Equations", - INSTITUTION = "Georgia Institute of Technology, School of Mathematics", - YEAR = 1990, TYPE = "Preprint", NUMBER = "Math: 062090-051"} - -@BOOK{Ochiai:90, - AUTHOR = "Mitsuyuki Ochiai and Kiyokazu Nagatomo", - TITLE = "Linear Algebra using {REDUCE}", - PUBLISHER = "Kindai Kagaku sha, Tokyo", MONTH = "January", YEAR = 1990, - COMMENT = {In Japanese.}} - -@ARTICLE{Ogilvie:82, - AUTHOR = "J. F. Ogilvie", - TITLE = "Applications of Computer Algebra in Physical Chemistry", - JOURNAL = "Computers in Chemistry", - YEAR = 1982, VOLUME = 6, NUMBER = 4, PAGES = "169-172", - COMMENT = {After distinguishing between algebraic and numerical -computing, the author outlines the facilities of some -algebraic or symbolic processors and provides some -instances of how some important features can be applied -to problems in physical chemistry.}} - -@ARTICLE{Ogilvie:89, - AUTHOR = "J. F. Ogilvie", - TITLE = "Computer algebra in modern physics", - JOURNAL = "Computers in Physics", - YEAR = 1989, MONTH = "January/February", PAGES = "66-74"} - -@TECHREPORT{Ono:1979, - AUTHOR = "Kiyoshi Ono", - TITLE = "{BFORT} -- A {Fortran} System with Arbitrary -Precision Integer and Real Arithmetic", - INSTITUTION = "Department of Physics, University of Tokyo", - YEAR = 1979, MONTH = "January"} - -@TECHREPORT{Ozieblo, - AUTHOR = "A. Ozieblo", - TITLE = "Application of {REDUCE 2} in General Theory of Relativity", - INSTITUTION = "Cyfronet - Krakow, Poland", - COMMENT = {Application of {REDUCE 2} in all calculations typical for -General Theory of Relativity is shown here. The most -spectacular usage of {REDUCE 2} appears to be in various -aspects of tensor calculus including differentiation -operations.}} - -% REDUCE BIBLIOGRAPHY - -% Part 4: P-Z - -% Copyright (c) 1993 RAND. All Rights Reserved. - -% Additions and corrections are solicited. Please send them, in the -% same format as these entries if possible, to reduce at rand.org. - - -@InProceedings{Padget90, - author = "Julian Padget and Alan Barnes", - title = "Univariate Power Series Expansions in {REDUCE}", - booktitle = "Proceedings of the International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "82-87", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@ARTICLE{Pankau:73, - AUTHOR = "E. Pankau and W. Nakel", - TITLE = "Measurement of the Absolute Cross Section of the -Elementary Process of Electron-Electron Bremsstrahlung at 300 {keV}", - JOURNAL = "Phys. Lett.", - YEAR = 1973, VOLUME = "44A", PAGES = "65-67"} - -@ARTICLE{Pankau:73a, - AUTHOR = "E. Pankau and W. Nakel", - TITLE = "Eine {Koinzidenzmessung} zum {Elementarprozess} -der {Elektron-Elektron-Bremsstrahlung} bei 300 {keV}", - JOURNAL = "Z. Physik", - YEAR = 1973, VOLUME = 264, PAGES = "139-153"} - -@ARTICLE{Parsons:68, - AUTHOR = "R. G. Parsons", - TITLE = "An Estimate of the Sixth Order Contribution to the -Anomalous Magnetic Moment of the Electron", - JOURNAL = "Phys. Rev.", - YEAR = 1968, VOLUME = 168, PAGES = "1562-1567"} - -@TECHREPORT{Parsons:71, - AUTHOR = "R. G. Parsons", - TITLE = "S-Channel Transformation Matrices for Helicity and -Invariant Amplitudes for lambda + N to O + B", - INSTITUTION = "Center for Particle Theory, University of Texas", - YEAR = 1971, TYPE = "Memo", NUMBER = "CPT-88", MONTH = "January"} - -@ARTICLE{Pasini:91, - AUTHOR = "P. Pasini and F. Semeria and C. Zannoni", - TITLE = "Symbolic computation of orientational correlation function -moments", - JOURNAL = "J. Symbolic Computation", - YEAR = 1991, VOLUME = 12, NUMBER = 2, PAGES = "221-231", MONTH = "August"} - COMMENTS = {Symbolic manipulation (REDUCE and SCHOONSCHIP) has been -applied to the analytic evaluation of the coefficients in the Taylor series -expansion of time-correlation functions. These expressions are derived -for cylindrically and biaxially symmetric particles reorienting in a -uniaxial fluid. The possibility of using computer algebra to determine -correlation-function moments should make it applicable to various problems -in statistical physics.}} - -@ARTICLE{Pattnaik:83, - AUTHOR = "P. C. Pattnaik and G. Fletcher and J. L. Fry", - TITLE = "Improved Numerical Stability for Norm-Conserving ion-{Ure} -Pseudopotentials", - JOURNAL = "Phys. Rev. B", - YEAR = 1983, VOLUME = 28, NUMBER = 6, PAGES = "3364-3365", - COMMENT = {{REDUCE} and {FORTRAN}; inverting a matrix algebraically would -be more accurate than a numerical inverse, and used {REDUCE} for this part of -their work.}} - -@ARTICLE{Pearce:81, - AUTHOR = "P. D. Pearce and R. J. Hicks", - TITLE = "The Application of Algebraic Optimisation Techniques to -Algebraic Mode Programs for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1981, VOLUME = 15, NUMBER = 4, PAGES = "15-22", - MONTH = "November"} - -@ARTICLE{Pearce:83, - AUTHOR = "P. D. Pearce and R. J. Hicks", - TITLE = "Data Structures and Execution Times of Algebraic Mode -Programs for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "31-37", MONTH = "February"} - -@ARTICLE{Perjes:84, - AUTHOR = "Z. Perj{\'e}s", - TITLE = "Stationary Vacuum Fields with a Conformally Flat -Three-Space. {III}. {Complete} Solution", - JOURNAL = "General Relativity and Gravitation", - YEAR = 1984, VOLUME = 18, PAGES = "531-547", - COMMENT = {{REDUCE} used to perform the necessary calculations.}} - -@ARTICLE{Perjes:84a, - AUTHOR = "Z. Perj{\'e}s and B. Luk{\'a}cs and A. Sebesty{\'e}n -and A. Valentini", - TITLE = "Solution of the Stationary Vacuum Equations of -Relativity for Conformally Flat 3-Spaces", - JOURNAL = "Phys. Lett.", - YEAR = 1984, VOLUME = {100A}, NUMBER = 8, PAGES = "405-406", - MONTH = "February"} - -@TECHREPORT{Perjes:84b, - AUTHOR = "Z. Perj{\'e}s", - TITLE = "Improved Characterization of the {Kerr} Metric", - INSTITUTION = "Hungarian Academy of Sciences, Central -Research Institute for Physics", - YEAR = 1984, NUMBER = "KFKI-1984-115"} - -@TECHREPORT{Perjes:84c, - AUTHOR = "Z. Perj{\'e}s", - TITLE= "Stationary Vacuum Fields with a Conformally Flat Three-Space. -{IV}. {Complete} Solution", - INSTITUTE = "Institute for Nuclear Study, University of Tokyo", - YEAR = 1984, NUMBER = "INS-REP.-487", MONTH = "January"} - -@TECHREPORT{Perjes:86, - AUTHOR = "Z. Perj{\'e}s", - TITLE = "Ernst Coordinates", - INSTITUTION = "Hungarian Academy of Sciences, Central -Research Institute for Physics", - YEAR = 1986, TYPE = "Preprint", NUMBER = "KFKI-1986-33/B"} , - -@ARTICLE{Perjes:86a, - AUTHOR = "Z. Perj{\'e}s", - TITLE = "Stationary Vacuum Fields with a Conformally -Flat Three-Space. {II}. {Proof} of Axial Symmetry", - JOURNAL = "General Relativity and Gravitation", - YEAR = 1986, VOLUME = 18, NUMBER = 5, PAGES = "511-530", - MONTH = "May"} - -@ARTICLE{Perjes:88, - AUTHOR = "Z. Perj{\'e}s", - TITLE = "Approaches to Axisymmetry by Man and Machine", - JOURNAL = "Relativity Today", - YEAR = 1988, EDITOR = "Z. Perjes", PUBLISHER = "World Scientific, - Singapore"} - -@ARTICLE{Perlt:90, - AUTHOR = "H. Perlt and J. Ranft and J. Heinrich", - TITLE = "Calculation of {QED} graphs with the {Spinor} technique", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1990, VOLUME = 56, NUMBER = 3, PAGES = "385-390", MONTH = "January"} - -@TECHREPORT{Perrottet:78, - AUTHOR = "M. Perrottet", - TITLE = "Signature for {W} Boson Production From Jet Analysis -In e+e- $\rightarrow$ {W+W-} $\rightarrow$ Hadrons", - INSTITUTION = "CPT 2, CNRS, Marseille", YEAR = 1978, - TYPE = "Preprint", NUMBER = "78/P.1019", MONTH = "June", - ABSTRACT = {We have computed the ratio -o(e+e- $\rightarrow$ W+W- $\rightarrow$ Hadrons)/ o(e+e- $\rightarrow$ -G,Z $\rightarrow$ Hadrons) as a function of the {CM} energy in the -Weinberg-Salam model.}} - -@TECHREPORT{Pesic:73, - AUTHOR = "P. D. Pesic", - TITLE = "Two-Photon Cross Section for {W}-Pair Production -by Colliding Beams", - INSTITUTION = "Stanford University", YEAR = 1973, TYPE = "Report", -NUMBER = "SLAC-PUB-1188", - COMMENT = {Stanford University Linear Accelerator Report.}} - -@PHDTHESIS{Pictiaw:69, - AUTHOR = "Chen Pictiaw", - TITLE = "An Analytical Investigation of Infinitesimal Spatial -Motion Theory and its Application to Three-Dimensional Linkages", - SCHOOL = "Dept. of Mech. Eng., Stanford University", - YEAR = 1969, MONTH = "March"} - -@ARTICLE{Piessens:84, - AUTHOR = "R. Piessens", - TITLE = "A Series Expansion for the First Positive Zero of the {Bessel} -Function", - JOURNAL = "Math. Comp.", - YEAR = 1984, VOLUME = 42, PAGES = "195-197", - COMMENT = {Gives explicit series for first positive zero for 4 terms, using -{REDUCE}.}} - -@ARTICLE{Piessens:86, - AUTHOR = "R. Piessens and S. Ahmed", - TITLE = "Note on Approximation for the Turning Points of {Bessel} -Functions", - JOURNAL = "J. Comp. Phys.", - YEAR = 1986, VOLUME = 64, PAGES = "253-257", - COMMENT = {{REDUCE} used to differentiate and give expansions.}} - -@ARTICLE{Pignataro:85, - AUTHOR = "M. Pignataro and A. Luongo and N. Rizzi", - TITLE = "On the Effect of the Local Overall Interaction on the -Postbuckling of Uniformly Compressed Channels", - JOURNAL = "Thin-Walled Structures", - YEAR = 1985, VOLUME = 3, PAGES = "292-321", - COMMENT = {{REDUCE} generating {FORTRAN}, but also used to investigate the -form of the solutions.}} - -@MASTERSTHESIS{Podgorzak:84, - AUTHOR = "E. Podg{\'o}rak and I. Romanowska", - TITLE = "Application of {REDUCE} 2 to the Construction of -Recurrence Relations", - SCHOOL = "Institute of Computer Science, University of Wroclaw", - YEAR = "1984"} - -@ARTICLE{Price:84, - AUTHOR = "S. L. Price and A. J. Stone and M. Alderton", - TITLE = "Explicit Formulae for the Electrostatic Energy, Forces and -Torques Between a Pair of Molecules of Arbitrary Symmetry", - JOURNAL = "Molecular Phys.", - YEAR = 1984, VOLUME = 52, PAGES = "987-1001", - COMMENT = {"The substitution of the complex multipoles and the S -functions into the expression for the electrostatic energy was -facilitated by the use of the symbolic algebraic manipulation program -{REDUCE}." Involves heavy calculations.}} - -@TECHREPORT{Quarton, - AUTHOR = "D. C. Quarton and A. D. Garrad", - TITLE = "Some Comments on the Stability Analysis of Horizontal -Axis Wind Turbines", - INSTITUTION = "Wind Energy Group, Taylor Woodrow Construction Ltd."} - -@TECHREPORT{Quarton:84, - AUTHOR = "D. C. Quarton and A. D. Garrad", - TITLE = "Symbolic Computing as a Tool in Wind Turbine Dynamics", - INSTITUTION = "Wind Energy Group, Taylor Woodrow Construction Ltd.", - YEAR = 1984, - COMMENT = {Presented at the European Wind Energy Conference and Exhibition -22-26 Oct 1984, Hamburg.}} - -@MASTERSTHESIS{Rao:85, - AUTHOR = "R. H. Rao", - TITLE = "Deformation of a Fluid-Filled Cylindrical Membrane by a -Slow Viscous Shear Flow", - SCHOOL = "Washington University", - ADDRESS = "Dept. of Mech. Eng., Washington University, St. Louis", - YEAR = "1985", - COMMENT = {Draws attention to the use of classical perturbation -techniques combined with computer algebra as an alternative to -numerical calculation.}} - -@BOOK{Rayna:87, - AUTHOR = "G. Rayna", - TITLE = "{REDUCE}: A System for Computer Algebra", - PUBLISHER = "Springer-Verlag", - YEAR = 1987} - -@INPROCEEDINGS{Renner:91, - AUTHOR = "Friedrich Renner", - TITLE = "Nonlinear Evolution Equations and the {Painlev{\'e}} Analysis: -A constructive Approach with {REDUCE}", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "289-294", - ABSTRACT = {A number of necessary conditions for a class of nonlinear -partial differential equations to pass the Painlev{\'e} test with the -Kruskal ansatz is given. Using these we can (theoretically) construct all -evolution equations of certain form and this property with a computer algebra -package based on {REDUCE}.}} - -@ARTICLE{Renner:92, - AUTHOR = "Friedrich Renner", - TITLE = "A constructive {REDUCE} package based upon the {Painlev{\'e}} -analysis of nonlinear evolutions equations in Hamiltonian and/or normal -form", - JOURNAL = "Computer Physics Communications", - YEAR = 1992, VOLUME = 70, NUMBER = 2, PAGES = "409-416", MONTH = "June", - ABSTRACT = {A number of necessary conditions for scalar nonlinear evolution -equations of normal or certain Hamiltonian form to pass the {Painlev{\'e}} -test in one (or two) branches with the Kruskal ansatz is used to write a -{REDUCE} package able to construct (theoretically) all equations with this -property. Starting with a given leading order, a degree of homogeneity -and (in the Hamiltonian case) a skew-adjoint differential operator, the -system generates al admissible resonance patterns, adapts (if possible) -the free parameters of the equation according to the chosen pattern and the -constraints of the compatibility conditions. In the {Painlev{\'e}} case, -the general inhomogeneous equation is generated and also examined. For -help and further investigations a set of utility procedures is supplied.}} - -@ARTICLE{Reusch:86, - AUTHOR = "M. F. Reusch and G. H. Neilson", - TITLE = "Torodially Symmetric Polynomial Multipole Solutions -of the Vector {Laplace} Equation", - JOURNAL = "J. Comp. Phys.", - YEAR = 1986, VOLUME = 64, PAGES = "416-432", - COMMENT = {{REDUCE} (plasma MHD) algebraic form of multipoles, then -numerical.}} - -Marcelo Ribeiro -Departamento de Astrofisica -Observatorio Nacional - CNPq -Rua General Jose Cristino 77 -Rio de Janeiro, RJ 20921-400 -BRAZIL -;N arpa mbr obsn.on.br - -@PHDTHESIS{Rink:71, - AUTHOR = "R. A. Rink", - TITLE = "Application of a Digital Computer to Solve Analytically -Special Classes of Linear and Nonlinear Differential Equations", - SCHOOL = "Stanford University", - YEAR = 1971} - -@ARTICLE{Rizzi:85, - AUTHOR = "N. Rizzi and A. Tatone", - TITLE = "Symbolic Manipulation in Buckling and Postbuckling Analysis", - JOURNAL = "Computers and Structures", - YEAR = 1985, VOLUME = 21, PAGES = "691-700", - COMMENT = {Gives {REDUCE} program and output for generating {FORTRAN}.}} - -@ARTICLE{Rodionov:84, - AUTHOR = "A. Ya. Rodionov", - TITLE = "Work with {non-commutative} variables in the {REDUCE-2} -system for analytical calculations", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1984, VOLUME = 18, NUMBER = 3, PAGES = "16-19", MONTH = "August"} - -@ARTICLE{Rodionov:87, - AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", - TITLE = "Computation of Covariant Derivatives of the Geodetic -Interval within the Coincident Arguments", - JOURNAL = "Class. Quantum Grav.", - YEAR = 1987, VOLUME = 4, PAGES = "1767-1775", - COMMENT = {Used {REDUCE} to calculate the geodetic interval of the -Riemannian manifold by calculating the multiple covariant derivatives of -orders 7 and 8. Direct use of {REDUCE} was not sufficient, but some -investigations of the structure of the problem produced some -recurrence relations.}} - -@INPROCEEDINGS{Rodionov:87a, - AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", - TITLE = "Combinatorial Aspects of Simplification of Algebraic Expressions", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "192-201", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Rodionov:88, - AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", - TITLE = "{RTENSOR - Packet} for work with tensoric expressions", - INSTITUTION = "Moscow State University, Scientific Research Institute -of Nuclear Physics", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-29/50"} - -@INPROCEEDINGS{Roelofs:91, - AUTHOR = "Marcel Roelofs and Peter K.H. Gragert", - TITLE = "Implementation of multilinear operators in {REDUCE} and -applications in mathematics", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "390-396", - ABSTRACT = {In this paper we introduce and implement a concept for dealing -with mathematical bases of linear spaces and mappings (multi)linear with -respect to such bases, in {REDUCE}. Using this concept we give some -examples how to implement some well known (multi)linear mappings in -mathematics with very little effort. Moreover we implement a procedure -operatorcoeff similar to the standard {REDUCE} procedure coeff, but now -for linear spaces instead of polynomial rings.}} - -@BOOK{Rogers:89, - AUTHOR = "C. Rogers and W. F. Ames", - TITLE = "Nonlinear Boundary Value Problems in Science and Engineering", - PUBLISHER = "Academic Press, Inc.", - YEAR = 1989} - -@ARTICLE{Roque:88, - AUTHOR = "Waldir L. Roque and Renato P. dos Santos", - TITLE = "Computa\c{c}\~{a}o alg\'{e}brica: ``um assistente matem\~{a}tico''", - JOURNAL = "Ci\^{e}ncia e Cultura", - YEAR = 1988, VOLUME = 40, NUMBER = 9, PAGES = "843-852", MONTH = -"September", - ABSTRACT = {In this paper we discuss in a simple and -informative way the theme ``algebraic computing'' in an attempt to encourage -the Brasilian scientific community to make use of this new tool{\ldots}. Many -algebraic computing systems have been developed in a variety of research -fields. Some of these systems, their main characteristics and applications -will be discussed.}, - COMMENT = {In Portuguese}} - -@ARTICLE{Roque:91, - AUTHOR = "Waldir L. Roque and Renato P. dos Santos", - TITLE = "Computer algebra in spacetime embedding", - JOURNAL = "J. Symbolic Computation", - YEAR = 1991, VOLUME = 12, NUMBER = 3, PAGES = "381-389", MONTH = -"September", - ABSTRACT = {In this paper we describe an algorithm to determine the vectors -normal to a space-time ${V}_{4}$ embedded in a pseudo-Euclidean manifold -${M}_{4+N}$. An application of this algorithm is given considering the -Schwarzchild spacetime geometry embedded in a 6 dimensional pseudo-Euclidean -manifold, using the algebraic computing system REDUCE.}} - -@ARTICLE{Ronveaux:88, - AUTHOR = "A. Ronveaux and G. Thiry", - TITLE = "Polynomial Solution of Recurrence Relation and Differential -Equation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1988, VOLUME = 22, NUMBER = 4, PAGES = "9-19", MONTH = "October"} - -@ARTICLE{Ronveaux:89, - AUTHOR = "A. Ronveaux and G. Thiry", - TITLE = "Differential Equations of Some Orthogonal Families in {REDUCE}", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 8, NUMBER = 5, PAGES = "537-541", MONTH = "November"} - -@INPROCEEDINGS{Rudenko:91, - AUTHOR = "V.M. Rudenko and V.V. Leonov and A.F. Bragazin and -I.P Shmyglevsky", - TITLE = "Application of Computer Algebra to the Investigation of the -Orbital Satellite Motion", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "450-451"} - -@ARTICLE{Saez:83, - AUTHOR = "A. E. Saez and B. J. McCoy", - TITLE = "Transient Analysis of Packed-Bed Thermal Storage Systems", - JOURNAL = "Int. J. Heat Mass Transfer", - YEAR = 1983, VOLUME = 26, NUMBER = 1, PAGES = "49-54"} - -@ARTICLE{Sage:88, - AUTHOR = "Martin L. Sage", - TITLE = "An Algebraic Treatment of Quantum Vibrations", - JOURNAL = "J. Symbolic Computation", - YEAR = 1988, VOLUME = 5, NUMBER = 3, PAGES = "377-384", MONTH = "June"} - -@ARTICLE{Sarlet:92, - AUTHOR = "W. Sarlet and J. Vanden Bonne", - TITLE = "{REDUCE-}procedures for the study of adjoint symmetries of -second-order differential equations", - JOURNAL = "J. Symbolic Computation", - VOLUME = 13, NUMBER = 6, YEAR = 1992, MONTH = "June", PAGES = "683-693", - ABSTRACT = {Two {REDUCE} programs are presented which should be of -assistance in computing and studying so-called adjoint symmetries of -second-order ordinary differential equations. The first program essentially -serves to construct the determining equations for adjoint symmetries, -whose leading coefficients are allowed to be polynomial functions of the -velocities. The second program runs various tests concerning the possible -construction of a first integral or a lagrangian for the given system.}} - -@INPROCEEDINGS{Sasaki:79, - AUTHOR = "Tateaki Sasaki", - TITLE = "An Arbitrary Precision Real Arithmetic Package in {REDUCE}", - BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes -in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "358-368", - PUBLISHER = "Springer-Verlag", - ABSTRACT = {A {REDUCE} arbitrary precision real arithmetic package is -described which will become a part of the kernel of an algebraic-numeric -system being developed for {REDUCE}.}} - -@ARTICLE{Savage:90, - AUTHOR = "Stuart B. Savage", - TITLE = "Symbolic computation of the flow of granular avalanches", - JOURNAL = "J. Symbolic Computation", - YEAR = 1990, VOLUME = 9, NUMBER = 4, PAGES = "515-530", MONTH = "April"} - -@ARTICLE{Sayers:87, - AUTHOR = "C. M. Sayers", - TITLE = "The Elastic Anisotropy of Polycrystalline Aggregates -of Zirconium and Its Alloys", - JOURNAL = "J. Nuclear Materials", - YEAR = 1987, VOLUME = 144, PAGES = "211-213", - COMMENT = {Used {REDUCE} for calculations of tensor products.}} - -@ARTICLE{Sayers:87a, - AUTHOR = "C. M. Sayers", - TITLE = "Elastic Wave Anisotropy in the Upper Mantle", - JOURNAL = "Geophysical J. R. Ast. Soc.", - YEAR = 1987, VOLUME = 88, PAGES = "417-424", - COMMENT = {Used {REDUCE} in calculations. "Theoretical expressions for -angular dependence of the longitudinal and shear wave velocities in an -axially symmetric aggregate{\ldots}"}} - -@INPROCEEDINGS{Schlegel:91, - AUTHOR = "H. Schlegel", - TITLE = "Determination of the Root System of Semisimple {Lie} Algbras from -the {Dynkin} Diagram", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "239-240"} - -@INPROCEEDINGS{Schmuck:77, - AUTHOR = "P. Schmuck", - TITLE = "Verification of the Transient, Two Phase Fluid -Flow Program {Kachina} using Computerized Similarity Analysis", - YEAR = 1977, MONTH = "October", - BOOKTITLE = "Second {GAMM} Conference on Numerical Methods -in Fluid Mechanics, k{\"o}ln"} - -@TECHREPORT{Schoebel:92, - AUTHOR = "Franziska Schoebel", - TITLE = "The Symbolic Classification of Real Four-Dimensional - Lie Algebras", NUMBER = "Preprint 27/92", YEAR = 1992, - INSTITUTION = "Naturwissenschaftlich-Theoretisches Zentrum, Universitaet - Leipzig, Germany"} - -@TECHREPORT{Schoepf:91, - AUTHOR = "Rainer Sch{\"o}pf and Peter Deuflhard", - TITLE = "{OCCAL} A mixed symbolic-numeric {Optimal Control CALculator}", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1991, TYPE = "Preprint", NUMBER = "SC 91-13", MONTH = "December", - ABSTRACT = {The numerical solution of optimal control problems by indirect -methods (such as multiple shooting or collocation) requires a considerable -amount of analytic calculation to establish a numerically tractable system. -These analytic calculations, though being rather tedious in realistic -examples, are nowadays mostly still done by hand--and thus prone to -calculation errors. The paper aims at automating this analytic processing -to a reasonable extent by means of a modern symbolic manipulation language -(here: REDUCE). In its present stage of development the package OCCAL -(mnemotechnically for Optimal Control CALculator) permits an interactive -use, covering tasks like automatic determination of control and, in case of a -singular control, of its order. In simpler problems, the present version of -OCCAL automatically produces the full subroutine input for a MULtiple -shooting code (MULCON) with adaptive numerical CONtinuation. - -In more complicated problems where singular sub-arcs may occur or where the -sequence of sub-arcs of the optimal trajectory is unclear OCCAL is a -significant help in reducing analytic pre-processing. Examples illustrate -the performance of OCCAL/MULCON.}} - -@ARTICLE{Schruefer:81, - AUTHOR = "E. Schr{\"u}fer and H. Heintzmann", - TITLE = "Lorentz-Covariant Eikonal Method in Magnetohydrodynamics -{II} - The Determination of the Wave Amplitude", - JOURNAL = "Phys. Lett.", - YEAR = 1981, VOLUME = {81A}, NUMBER = 9, PAGES = "501-506", - MONTH = "February", - COMMENT = {Used {REDUCE} for "rather tedious algebra."}} - -@ARTICLE{Schruefer:82, - AUTHOR = "E. Schr{\"u}fer", - TITLE = "An Implementation of the Exterior Calculus in {REDUCE:} -A Status Report", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "27-31", MONTH = "November"} - -@ARTICLE{Schruefer:87, - AUTHOR = "E. Schr{\"u}fer and F. W. Hehl and J. D. McCrea", - TITLE = "Exterior Calculus on the Computer: The {REDUCE}-Package -{EXCALC} Applied to General Relativity and to the {Poincar{\'e}} -Gauge Theory", - JOURNAL = "General Relativity and Gravitation", - YEAR = 1987, VOLUME = 19, NUMBER = 2, PAGES = "197-218", - MONTH = "February", - COMMENT = {Application of {EXCALC/REDUCE}, including review of other -systems, and description of {EXCALC}.}} - -@ARTICLE{Schruefer:88, - AUTHOR = "E. Schr{\"u}fer", - TITLE = "A Note on {Einstein} Metrics", - JOURNAL = "SIGSAM Bulletin", - YEAR = 1988, VOLUME = 22, NUMBER = 3, PAGES = "22-26", MONTH = "July"} - -@ARTICLE{Schwarz:80, - AUTHOR = "F. Schwarz", - TITLE = "An Approximation Scheme for Constructing $\pi_{0}\pi$ -Amplitudes from {ACU} Requirements", - JOURNAL = "Fortschritte der Physik", - YEAR = 1980, VOLUME = 28, PAGES = "201-235", - COMMENT = {"To derive the equations expressing the threshold and the -asymptotic behaviour one relies heavily on the programming system -{REDUCE}."}} - -@ARTICLE{Schwarz:82, - AUTHOR = "F. Schwarz", - TITLE = "Symmetries of the Two Dimensional {Korteweg-De Vries} Equation", - JOURNAL = "J. Phys. S. Japan", - YEAR = 1982, VOLUME = 51, NUMBER = 8, PAGES = "2387-2388", - COMMENT = {{REDUCE} used in the {SPDE} package.}} - -@ARTICLE{Schwarz:82a, - AUTHOR = "F. Schwarz", - TITLE = "A {REDUCE} Package for Determining {Lie} Symmetries of -Ordinary and Partial Differential Equations", - JOURNAL = "Computer Physics Communications", - YEAR = 1982, VOLUME = 27, PAGES = "179-186", - COMMENT = {Preliminary description of {REDUCE} packages {SODE} and -{SPDE}.}} - -@ARTICLE{Schwarz:83, - AUTHOR = "Fritz Schwarz", - TITLE = "A {REDUCE} Package for Series Analysis by {Hadamard's} -Theorem and {QD} Schemes", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "38-44", MONTH = "February"} - -@INPROCEEDINGS{Schwarz:83a, - AUTHOR = "Fritz Schwarz", - TITLE = "Automatically Determining Symmetries of Ordinary Differential -Equations", - BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes -in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "45-54", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Schwarz:84, - AUTHOR = "F. Schwarz", - TITLE = "The {Riquier-Janet} Theory and Its Application to Nonlinear -Evolution Equations", - JOURNAL = "Physica", - YEAR = 1984, VOLUME = "11D", PAGES = "243-251", - COMMENT = {Prologation methods in {REDUCE}. Points to existence of -{REDUCE} system.}} - -@ARTICLE{Schwarz:84a, - AUTHOR = "F. Schwarz and W. H. Steeb", - TITLE = "Symmetries and First Integrals for Dissipative Systems", - JOURNAL = "J. Phys. {A:} Math. Gen.", - YEAR = 1984, VOLUME = 17, PAGES = "L819-L823"} - -@ARTICLE{Schwarz:85, - AUTHOR = "F. Schwarz", - TITLE = "Automatically Determining Symmetries of Partial Differential -Equations", - JOURNAL = "Computing", - YEAR = 1985, VOLUME = 34, PAGES = "91-106", - COMMENT = {Describes the {SPDE} package for {REDUCE}.}} - -@ARTICLE{Schwarz:85a, - AUTHOR = "Fritz Schwarz", - TITLE = "An Algorithm for Determining Polynomial First Integrals of -Autonomous Systems of Ordinary Differential Equations", - JOURNAL = "J. Symbolic Computation", - YEAR = 1985, VOLUME = 1, NUMBER = 2, PAGES = "229-233", MONTH = "June"} - -@ARTICLE{Schwarz:86, - AUTHOR = "F. Schwarz", - TITLE = "A {REDUCE} Package for Determining First Integrals of -Autonomous Systems of Ordinary Differential Equations", - JOURNAL = "Computer Physics Communications", - YEAR = 1986, VOLUME = 39, PAGES = "285-296", - COMMENT = {Description of package {DISSYS} in {REDUCE}.}} - -@INPROCEEDINGS{Schwarz:87, - AUTHOR = "F. Schwarz", - TITLE = "Symmetries and Involution Systems: Some Experiments in -Computer Algebra", - YEAR = 1987, MONTH = "August", - BOOKTITLE = "Topics in Soliton Theory and Exactly Solvable Nonlinear -Equations", PUBLISHER = "World Science Press", ADDRESS = "Singapore", - COMMENT = {Description of algorithm {INVSYS} and applications.}} - -@ARTICLE{Schwarz:88, - AUTHOR = "F. Schwarz", - TITLE = "Symmetries of Differential Equations: From {Sophus Lie} to -Computer Algebra", - JOURNAL = "Siam Review", - YEAR = 1988, VOLUME = 30, PAGES = "450-481", - COMMENT = {Review article on applying the {REDUCE} package {SPDE}.}} - -@ARTICLE{Schwarz:94, - AUTHOR = "F. Schwarz", - TITLE = "Efficient Factorization of Linear {ODE's}", - JOURNAL = "Sigsam Bulletin", - YEAR = 1994, VOLUME = 28, NUMBER = 1, PAGES = "9-17", - ABSTRACT = {Factorization and testing for irreducibility has turned out to -be one of the most important algorithms for handling linear ode's. The -main hindrance for applying it is its trmendous complexity originating to a -large extent from solving certain Riccati equations which occur during the -factorization. The solution procedure for these Riccati equations is much -more manageable if it is subdivided into two major parts. At first so -called solution candidates are determined each of which depends only on the -parameters of a single irreducible denominator or the behavior at infinity. -In a second step it is tried to complete each candidate into a genuine -solution of the Riccati equation, possibly including an unspecified number -of additional first order poles. Furthermore a scheme is proposed for -running the factorization procedure in parallel on a two-processor machine -in which possible factors are searched for both from the right and the left -at the same time.}} - -@ARTICLE{Seiler:91, - AUTHOR = "Werner M. Seiler", - TITLE = "{SUPERCALC-} a {REDUCE} package for commutator calculations", - JOURNAL = "Computer Physics Communications", - YEAR = 1991, VOLUME = 66, PAGES = "363-376", - COMMENT = {A {REDUCE} package for commutator calculations in sypersymmetric -theories (including ordered products) and for infinite sums is presented -and an application to the computation of anomalies in string theory is -given.}} - -@INPROCEEDINGS{Shablygin:87, - AUTHOR = "E. Shablygin", - TITLE = "Integral Equation with Hidden Eigenparameter Solver: -{REDUCE} and {FORTRAN} in Tandem", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "186-191", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Shmueli:83, - AUTHOR = "U. Shmueli and A. J. C. Wilson", - TITLE = "Generalized Intensity Studies: The Subcentric Distribution -and Effects of Dispersion", - JOURNAL = "Acta Cryst.", - YEAR = 1983, VOLUME = "A39", PAGES = "225-233", - COMMENT = {Uses {REDUCE} for series expansion to high order as convergence -is slow.}} - -@ARTICLE{Shmueli:83a, - AUTHOR = "U. Shmueli and U. Kaldor", - TITLE = "Moments of the Trigonometric Structure Factor", - JOURNAL = "Acta Cryst.", - YEAR = 1983, VOLUME = "A39", PAGES = "615-621", - COMMENT = {Eight moment of magnitude of trigonometric structure factor. -Used {REDUCE}. Description of {REDUCE} in appendix.}} - -@TECHREPORT{Shtokhamer:75, - AUTHOR = "R. Shtokhamer", - TITLE = "Canonical Form of Polynomials in the Presence of -Side Relations", - INSTITUTION = "Technion", - YEAR = 1975, NUMBER = "Technion-PH-76-25"} - -@TECHREPORT{Shtokhamer:77, - AUTHOR = "R. Shtokhamer", - TITLE = "The Use of {``LET''} Statements in Producing Short -Comprehended Outputs", - INSTITUTION = "Department of Physics, Technion-Israel -Institute of Technology, Haifa, Israel", - YEAR = 1977, NUMBER = "Technion-PH-77-36", - ABSTRACT = {It is shown that an algebraic implementation of {"LET"} -statements may be useful in producing comprehended outputs. -The suggested algorithm is based on solving large set of -linear equations over a field.}} - -@INPROCEEDINGS{Smit:79, - AUTHOR = "J. Smit", - TITLE = "New Recursive Minor Expansion Algorithms, A Presentation in -a Comparative Context", - BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes -in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "74-87", -PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Smit:81, - AUTHOR = "J. Smit and J. A. van Hulzen and B. J. A. Hulshof", - TITLE = "{NETFORM} and Code Optimizer Manual", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1981, VOLUME = 15, NUMBER = 4, PAGES = "23-32", - MONTH = "November"} - -@INPROCEEDINGS{Smit:82, - AUTHOR = "J. Smit and J. A. van Hulzen", - TITLE = "Symbolic Numeric Methods in Microwave Technology", - BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes -in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "281-288", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{Smit:87, - AUTHOR = "J. Smit and S. H Gerez and R. Mulder", - TITLE = "Application of a Structured {LISP} System to Computer Algebra", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "149-160", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Soderstrand:72, - AUTHOR = "M. A. Soderstrand and D. C. Huey", - TITLE = "Sensitivities of Fourth-Order Filters Obtained by a -Low-Pass to Band-Pass Transformation", - INSTITUTION = "University of California, Davis", - YEAR = 1972, TYPE = "Report"} - -@INPROCEEDINGS{Soderstrand:72a, - AUTHOR = "M. A. Soderstrand and S. K. Mitra", - TITLE = "Computer-aided Sensitivity Analysis of Higher Filters", - YEAR = 1972, MONTH = "July", - BOOKTITLE = "Proc. Second Symposium on Network Theory, -Herzegnovia, Yugoslavia"} - -@TECHREPORT{Soderstrand:74, - AUTHOR = "M. A. Soderstrand and J. F. Lathrop", - TITLE = "Two Computer Programs for the Sensitivity Analysis -of Higher Order Filters", - INSTITUTION = "Sandia Laboratories", YEAR = 1974, - TYPE = "Report", NUMBER = "SLL-73-0225", MONTH = "January"} - -@ARTICLE{Soma:77, - AUTHOR = "T. Soma", - TITLE = "Relativistic Aberration Formulas for Combined -Electric-Magnetic Focusing-Deflection System", - JOURNAL = "Optik", - YEAR = 1977, VOLUME = 49, PAGES = "255-262", - COMMENT = {Existence of a vertical landing electron beam deflecting -system free of all deflection induced aberrations is -presented analytically.}} - -@INPROCEEDINGS{Soma:85, - AUTHOR = "Takashi Soma", - TITLE = "Recent Applications of {REDUCE} in {RIKEN}", - YEAR = 1985, - BOOKTITLE = "Proc. of the Second {RIKEN} International -Symposium on Symbolic and Algebraic Computation by Computers", - PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "181-182"} - -@INPROCEEDINGS{Spiridonova:87, - AUTHOR = "M. Spiridonova", - TITLE = "Some extensions and Applications of {REDUCE} System", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "136-137", - PUBLISHER = "Springer-Verlag"} - -@TECHREPORT{Squire, - AUTHOR = "W. Squire", - TITLE = "Some Applications of Symbolic Matrix Inversion", - INSTITUTION = "Dept. of Mechanical and Aerospace Engineering, -West Virginia University"} - -@BOOK{Steeb:92b, - AUTHOR = "Willi-Hans Steeb and Dirk Lewien", - TITLE = "Algorithms and Computation with {REDUCE}", - PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", YEAR = 1992, - ABSTRACT ={This book gives a collection of 75 standard methods - in mathematics, physics and engineering together with their - programs in {REDUCE} 3.4. Each item consists of a one page mathematical - description and one page {REDUCE} algebraic source text (in most cases - a few lines only). The book is an introduction by example - to algebraic programming in {REDUCE} and a collection of - ready to use solutions for many mathematical subtasks}} - -@BOOK{Steeb:92c, - AUTHOR = "Willi-Hans Steeb", - TITLE = "Chaos and Fractals: Algorithms and Computations", - PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", - YEAR = 1992, - COMMENT = "This book includes 26 Turbo C and C++, 47 Turbo PASCAL -and 23 REDUCE programs"} - -@ARTICLE{Steeb:92d, - AUTHOR = "W-H Steeb", - TITLE = "Computer Algebra and Its Applications in Physics", - JOURNAL = "International Journal of Modern Physics C", - YEAR = 1992, VOLUME = 3, NUMBER = 6, PAGES = "1333-1350", - COMMENT = {Computer algebra is a powerful tool in the study of a wide -class of problems in mathematics, physics, and engineering. The primary -domain of computer algebra is the solution of large scale formal problems. -We give an introduction and survey on computer algebra. In particular we -show with examples how problems in physics can be solved. We also show -with an example how object-oriented programming can be used in such -problems.}} - -@ARTICLE{Steeb:93, - AUTHOR = "W-H Steeb", - TITLE = "Fermi Systems and Computer Algebra", - JOURNAL = "International Journal of Modern Physics C", - YEAR = 1993, VOLUME = 4, NUMBER = 4, PAGES = "841-846", - COMMENT = {Computer algebra is a helpful tool in studying Fermi systems. -We show how the anticommutation relations can be implemented with computer -algebra. Then we give an application to the Hubbard model.}} - -@BOOK{Steeb:93a, - AUTHOR = "W.-H Steeb", - TITLE = "Invertible Point Transformations and Nonlinear Differential -Equations", - PUBLISHER = "World Scientific Publishing", - YEAR = 1993} - -@BOOK{Steeb:94, - AUTHOR = "W.-H Steeb", - TITLE = "Chaos und Quantenchaos in dynamischen Systemen", - PUBLISHER = "Bi-Wissenschaftsverlag, Mannheim", - YEAR = 1994} - -@BOOK{Steeb:94a, - AUTHOR = "W.-H Steeb", - TITLE = "Quantum Mechanics using Computer Algebra", - PUBLISHER = "World Scientific Publishing, Singapore", - YEAR = 1994} - -@ARTICLE{Steeb:94b, - AUTHOR = "W-H Steeb", - TITLE = "Applications of Computer Algebra in Quantum Groups", - JOURNAL = "International Journal of Modern Physics C", - YEAR = 1994, VOLUME = 6, PAGES = "701-706"} - -@ARTICLE{Steeb:94c, - AUTHOR = "W-H Steeb", - TITLE = "Extended {Lorenz} Models and Time Dependent First Integrals", - JOURNAL = "Zeitschrift fuer Naturforschung", - YEAR = 1994, VOLUME = "49a", PAGES = "751-753"} - -@ARTICLE{Steeb:95, - AUTHOR = "W-H Steeb", - TITLE = "{Bose-Fermi} Systems and Computer Algebra", - JOURNAL = "Foundations of Physics Letters", YEAR = 1995} - -@ARTICLE{Steinberg:82, - AUTHOR = "Stanly Steinberg", - TITLE = "Mathematics and Symbol Manipulation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 3, PAGES = "11-15", MONTH = "August"} - -@InProceedings{Steinberg:93, - author = "S. Steinberg and R. Liska", - title = "Stability Analysis and Quantifier Elimination", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "62-67", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - comment = {Stability of time-stepping numerical schemes for partial - differential equations based on the {REDUCE} package FIDE - and the SACLIB package QEPCAD.} -} - -@ARTICLE{Steuerwald, - AUTHOR = "J. Steuerwald and W. Kerner", - TITLE = "A Contribution to the Efficient Solution of -Extensive Symbolic Computations", - JOURNAL = "Comp. Phys. Comm."} - -@ARTICLE{Stoutemyer:74, - AUTHOR = "D. Stoutemyer", - TITLE = "Automatic Error Analysis Using the Computer Symbolic -Manipulation Language", - JOURNAL = "TOMS 3", - YEAR = 1977, VOLUME = 3, NUMBER = 1, PAGES = "26-43", - MONTH = "March", - ABSTRACT = {This paper shows how the inherent error and the fixed-point -or floating-point roundoff of chopoff error of an expression can be -determined automatically using a computer algebra language such as -{REDUCE}.}} - -@TECHREPORT{Stoutemyer:75, - AUTHOR = "David R. Stoutemyer", - TITLE = "Symbolic Computer Solution of an Equation in Finite Terms", - INSTITUTION = "Dept. of Comp. Science, Univ. of Utah", - TYPE = "Report", YEAR = 1975, NUMBER = "UCP-33", - ABSTRACT = {This report contains a program listing together with -documentation, a demonstration, and discussion of a {REDUCE} program for the -exact solution of an equation in finite terms. Capable of treating certain -equations involving elementary transcendental functions, radicals, -and polynomials, the program incorporates several solution techniques -not implemented in existing analogous programs written in other -computer algebra languages. The program is also capable of solving -linear or linear fractional in the unknowns. In this case it simply -used the built-in matrix equation solver, but permitting input as -lists of expressions rather than matrices, which is convenient for -sparse or small linear systems.}} - -@ARTICLE{Stoutemyer:77, - AUTHOR = "David R. Stoutemyer", - TITLE = "Analytically Solving Integral Equations by Using Computer -Algebra", - JOURNAL = "TOMS", - YEAR = 1977, VOLUME = 3, NUMBER = 2, PAGES = "128-146", - MONTH = "June", - ABSTRACT = {This report describes how a computer algebra language, such as -{REDUCE}, may be used to automatically construct closed-form and series -analytical solutions of integral equations.}} - -@ARTICLE{Stroscio:74, - AUTHOR = "M. A. Stroscio and J. M. Holt", - TITLE = "Radiative Corrections to the Decay Rate of Orthopositronium", - JOURNAL = "Phys. Rev. A", - YEAR = 1974, MONTH = "September", VOLUME = 10, PAGES = "749-755"} - -@ARTICLE{Stuart:88, - AUTHOR = "Robin G. Stuart", - TITLE = "Algebraic Reduction of one-loop {Feynman} Diagrams to -Scalar Integrals", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1988, VOLUME = 48, NUMBER = 3, PAGES = "367-389", MONTH = "March"} - -@ARTICLE{Stuart:90, - AUTHOR = "Robin G. Stuart and A. G{\'o}ngora-T", - TITLE = "Algebraic Reduction of one-loop {Feynman} Diagrams to -Scalar Integrals II", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1990, VOLUME = 56, NUMBER = 3, PAGES = "337-350", MONTH = "January"} - -@ARTICLE{Suppes:89, - AUTHOR = "Patrick Suppes and Shuzo Takahashi", - TITLE = "An Interactive Calculus Theorem-prover for Continuity -Properties", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 7, NUMBER = 6, PAGES = "573-590", MONTH = "June"} - -@ARTICLE{Surguladze:89, - AUTHOR = "L.R. Surguladze and F.V. Tkachov", - TITLE = "{LOOPS:} Procedures for Multiloop Calculations in Quantum Field -Theory for the {REDUCE} System", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1989, VOLUME = 55, NUMBER = 2, PAGES = "205-215", - MONTH = "September", PUBLISHER = "North Holland Publishing Company"} - -@INPROCEEDINGS{Surguladze:91, - AUTHOR = "Levan R. Surguladze and Mark A. Samuel", - TITLE = "Algebraic Perturbative Calculations in High Energy Physics -Methods, algorithms, computer programs and physical applications", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "439-447", - ABSTRACT = {The methods and algorithms for high order algebraic -perturbative calculations in theoretical high energy physics are briefly -reviewed. The {SCHOONSCHIP} program {MINCER} and the {REDUCE} program -{LOOPS} for analytical computation of arbitrary massless, one-, two- -and three-loop Feynman diagrams of the propagator type are described. -The version of the program {LOOPS} for personal computers and the extended -version of the program {MINCER} for four-loop renormalization group -calculations are presented. The new program for algebraic perturbative -calculations is also discussed. This program is written on the new -algebraic programming system {FORM}. Some recent results of application -to the high energy physics are given.}} - -@ARTICLE{Tallents:84, - AUTHOR = "G. J. Tallents", - TITLE = "The Relative Intensities of Hydrogen-Like Fine Structure", - JOURNAL = "J. Phys. B", - YEAR = 1984, VOLUME = 17, PAGES = "3677-3691", - COMMENT = {{REDUCE} used to check a formula; also checked numerically.}} - -@InProceedings{Tao90, - author = "Qingsheng Tao", - title = "Symbolic and Algebraic manipulation for Formulae of - Interpolation and Quadrature", - booktitle = "Proceedings of the 1990 International Symposium on - Symbolic and Algebraic Computation", - year = "1990", - editor = "S. Watanabe and Morio Nagata", - pages = "306", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@TECHREPORT{Tasso:76, - AUTHOR = "H. Tasso and J. Steuerwald", - TITLE = "Subroutine for Series Solutions of Linear Differential Equations", - INSTITUTION = "Max Planck Institut for Plasmaphysik", - YEAR = 1976, NUMBER = "IPP 6/143"} - -@TECHREPORT{Thas:89, - AUTHOR = "C. Thas", - TITLE = "A collection of {REDUCE} and {MACSYMA} programs about college -geometry. Part 1", - INSTITUTION = "State University of Gent", - YEAR = 1989, NUMBER = 5, MONTH = "September"} - -@TECHREPORT{Thas:89a, - AUTHOR = "C. Thas", - TITLE = "A collection of {REDUCE} and {MACSYMA} programs about college -geometry. Part 2", - INSTITUTION = "State University of Gent", - YEAR = 1989, NUMBER = 5, MONTH = "September"} - -@INPROCEEDINGS{Todd:88, - AUTHOR = "P. H. Todd and G. W. Cherry", - TITLE = "Symbolic Analysis of Planar Drawings", - BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", - YEAR = 1988, VOLUME = 358, PAGES = "344-355"} - -@ARTICLE{Toth:86, - AUTHOR = "K. T{\'o}th and K. Szeg{\"o} and A. Margaritis", - TITLE = "Radiative Corrections for Semileptonic Decays of {Hyperons: -`Model-Independent' Part}", - JOURNAL = "Physical Review D", YEAR = 1986, VOLUME = 33, NUMBER = 11, - PAGES = "3306-3315", MONTH ="June"} - -@INPROCEEDINGS{Tournier:79, - AUTHOR = "Evelyne Tournier", - TITLE = "An Algebraic Form of a Solution of a System -of Linear Differential Equations with Constant Coefficients", - BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes -in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "153-163", - PUBLISHER = "Springer-Verlag", - ABSTRACT = {In this paper we describe an algorithm for finding an -algebraic form for the solution of a system of linear differential -equations with constant coefficients, using the properties of elementary -divisors of a polynomial matrix.}} - -@PHDTHESIS{Tournier:87, - AUTHOR = "Evelyne Tournier", - TITLE = "Solutions Formelles D'Equations Differentielles, -le Logiciel de Calcul Formel: {DESIR} Etude Theorique -et Realisation", - SCHOOL = "L'Universit{\'e} Scientifique, Technologique et -Medicale de Grenoble", - YEAR = 1987, MONTH = "April"} - -@INPROCEEDINGS{Trenkov:91, - AUTHOR = "I. Trenkov and M. Spiridonova and M. Daskalova", - TITLE = "An Application of the {REDUCE} System for Solving a Mathematical -Geodesy Problem", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "448-449"} - -@INPROCEEDINGS{Trotter:89, - AUTHOR = "H. F. Trotter", - TITLE = "Use of Symbolic Methods in Analyzing an Integral Operator", - BOOKTITLE = "Proc. of Computers and Mathematics '89", - EDITOR = "E. Kaltofen and S. M. Watt", - YEAR = 1989, PAGES = "82-90", PUBLISHER = "Springer-Verlag, New York"} - -@ARTICLE{Tsai:65, - AUTHOR = "Y. S. Tsai and A. C. Hearn", - TITLE = "Differential Cross-Section for e+ + e- $\rightarrow$ {W+} + -{W-} $\rightarrow$ e- + $\overline{\nu}_{e} + \mu + \nu_{\mu}$", - JOURNAL = "Phys. Rev.", - YEAR = 1965, VOLUME = 140, PAGES = "B721-B729"} - -@ARTICLE{Tsai:74, - AUTHOR = "Y. S. Tsai", - TITLE = "Pair Production and Bremsstrahlung of Charged Leptons", - JOURNAL = "Rev. Mod. Phys.", - YEAR = 1974, VOLUME = 46, PAGES = "815-851"} - -@ARTICLE{Ucoluk:82, - AUTHOR = "G. {\"U}\c{c}oluk and A. Hacinliyan", - TITLE = "A Proposal for Extensions to {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 2, PAGES = "4-14", MONTH = "May", - ABSTRACT = {Three classes of extensions are proposed for {REDUCE}: A -facility for evaluating arbitrary functions of matrices; a facility for -grouping, modifying or restoring the status of various flags -in {REDUCE}; further extensions and modifications for separating -terms, coefficients of expressions, concatenation, and non- -commuting algebra.}} - -@BOOK{Ueberberg:92, - AUTHOR = "Johannes Ueberberg", - TITLE = "Einf{\"u}hrung in die computeralgebra mit {REDUCE}", - PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", - YEAR = 1992} - -@ARTICLE{Umeno:89, - AUTHOR = "Takaji Umeno and Syuichi Yamashita and Osami Saito and -Kenichi Abe", - TITLE = "Symbolic Computation Application for the Design of Linear -Multivariable Control Systems", - JOURNAL = "J. Symbolic Computation", - YEAR = 1989, VOLUME = 8, NUMBER = 6, PAGES = "581-588", MONTH = "December"} - -@INPROCEEDINGS{Urintsev:91, - AUTHOR = "A.L. Urintsev and A.V. Samoilov", - TITLE = "Complex Reduce-programs for analytic solution of some problems of -beam transport systems", - YEAR = 1991, - BOOKTITLE = "In: 4th International Conference on Computer Algebra in -Physical Research", - EDITOR = "D.V. Shirkov and V.A. Rostovtsev and V.P. Gerdt", - PUBLISHER = "World Scientific", ADDRESS = "Singapore, New Jersey, London, -Hong Kong", PAGES = "438-442"} - -@ARTICLE{vandenHeuvel:86, - AUTHOR = "Pim van den Heuvel", - TITLE = "Adding Statements to {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "8-14", - MONTH = "February and May"} - -@TECHREPORT{vandenHeuvel:86a, - AUTHOR = "Pim van den Heuvel", - TITLE = "Some Experiments in {REDUCE} Related to the -Calculation of {Groebner} Bases", - INSTITUTION = "Department of Computer Science, Twente -University of Technology, The Netherlands", - YEAR = 1986, MONTH = "June"} - -@INPROCEEDINGS{vandenHeuvel:87, - AUTHOR = "P. van den Heuvel and J. A. van Hulzen and V. V. Goldman", - TITLE = "Automatic Generation of {FORTRAN}-Coded {Jacobians} and -{Hessians}", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "120-131", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{vandenHeuvel:87a, - AUTHOR = "P. van den Heuvel and B. J. A. Hulshof and J. A. van Hulzen", - TITLE = "Some Simple Pretty-Print Facilities for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1987, VOLUME = 21, NUMBER = 1, PAGES = "14-17", MONTH = "February"} - -@TECHREPORT{vanHeerwaarden, - AUTHOR = "M. C. van Heerwaarden and J. A. van Hulzen", - TITLE = "Pretty Print Facilities for {REDUCE}", - INSTITUTION = "Department of Computer Science, University -of Twente, The Netherlands", - YEAR = 1988, TYPE = "Memorandum", - NUMBER = "INF-88-36", MONTH = "August"} - -@ARTICLE{vanHulzen:80, - AUTHOR = "J. A. van Hulzen", - TITLE = "Computational Problems in Producing {Taylor} Coefficients -for the Rotating Disk Problem", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1980, VOLUME = 14, NUMBER = 2, PAGES = "36-49", MONTH = "May"} - -@TECHREPORT{vanHulzen:81, - AUTHOR = "J. A. van Hulzen", - TITLE = "Breuer's Grow Factor Algorithm in Computer Algebra", - INSTITUTION = "Department of Applied Mathematics, Twente University -of Technology, The Netherlands", - YEAR = 1981, TYPE = "Memorandum", NUMBER = 332, MONTH = "April", - COMMENT = {A shorter version appears in: Proceedings SYMSAC 81 - (Paul S. Wang, ed.) ACM, August 1981.}} - -@ARTICLE{vanHulzen:82, - AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof", - TITLE = "An Expression Analysis Package for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "32-44", MONTH = "November"} - -@INPROCEEDINGS{vanHulzen:82a, - AUTHOR = "J. A. van Hulzen", - TITLE = "Computer Algebra Systems Viewed by a Notorious User", - BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes -in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "166-180"} - -@INCOLLECTION{vanHulzen:83, - AUTHOR = "J. A. van Hulzen and J. Calmet", - TITLE = "Computer Algebra Systems", - EDITOR = "B. Buchberger and G. E. Collins and R. Loos and R. Albrecht", - BOOKTITLE = "Computer Algebra and Symbolic and Algebraic Computation", - EDITION = "2nd", PUBLISHER = "Springer-Verlag", YEAR = 1983} - -@INPROCEEDINGS{vanHulzen:83a, - AUTHOR = "J. A. van Hulzen", - TITLE = "Code Optimization of Multivariate Polynomial Schemes: A -Pragmatic Approach", - BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes -in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "286-300", - PUBLISHER = "Springer-Verlag"} - -@INPROCEEDINGS{vanHulzen:87, - AUTHOR = "J. A. van Hulzen", - TITLE = "Program Generation Aspects of the Symbolic-Numeric Interface", - BOOKTITLE = "Proc. Third Intern. Conf. on Computer Algebra and its -applications in Theor. Phys, 1985", YEAR = 1987, PAGES = "104-113", - PUBLISHER = "{J.I.N.R., Dubna, USSR}"} - -@TECHREPORT{vanHulzen:88, - AUTHOR = "J. A. van Hulzen", - TITLE = "Formule Manipulatie m.b.v. {REDUCE} (in {Dutch})", - INSTITUTION = "Department of Computer Science, Twente University -of Technology, The Netherlands", - YEAR = 1988, MONTH = "October"} - -@INPROCEEDINGS{vanHulzen:89, - AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof and B. L. Gates and -M. C. Van Heerwaarden", - TITLE = "A Code Optimization Package for {REDUCE}", - BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", - YEAR = 1989, PAGES = "163-170", - COMMENT = {Lecture Notes.}} - -@TECHREPORT{vanHulzen:89a, - AUTHOR = "J. A. van Hulzen", - TITLE = "Computer Algebra and Numerical Mathematics: The Odd Couple?", - INSTITUTION = "Department of Computer Science, Twente University -of Technology, The Netherlands", - NUMBER = "Informatica 89-40", - YEAR = 1989, MONTH = "June"} - -@TECHREPORT{VanProeyan:76, - AUTHOR = "A. Van Proeyen", - TITLE = "Quantum Gravity Corrections on the Anomalous -Magnetic and Quadrupole Moments of a Spin-1 Particle", - INSTITUTION = "Instituut voor Theor. Fys., Leuven", - YEAR = 1976, MONTH = "October"} - -@TECHREPORT{VanProeyan:79, - AUTHOR = "A. Van Proeyan", - TITLE = "Gravitational Divergences of the Electromagnetic -Interactions of Massive Vectorparticles", - INSTITUTION = "Universiteit Leuven", - YEAR = 1979, TYPE = "Preprint", NUMBER = "KUL-TF-79/032", - MONTH = "October", - ABSTRACT = {In a search for the explanation of the finite quantum -gravity corrections to anomalous moments we examined a -spontaneous broken 0(3) model with Yang-Mills particles -and Higgs scalars coupled to gravitons.}} - -@INPROCEEDINGS{Vega:91, - AUTHOR = "Laureano Gonz{\'a}lez Vega", - TITLE = "Working with Real Algebraic Plane Curves in {REDUCE:} the -{GCUR} package", - YEAR = 1991, MONTH = "July", - BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and -Algebraic Computation", - EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", - PAGES = "397-402"} - -@TECHREPORT{Vinitsky:87, - AUTHOR = "S. I. Vinitsky and V. A. Rostovtsev", - TITLE = "A Use of {REDUCE} System in Problems of -Hydrogen Atom in an Electric Field", - INSTITUTION = "J.I.N.R., Dubna", TYPE = "Preprint", - YEAR = 1987, NUMBER = "P11-87-303"} - -@ARTICLE{Viry:93, - AUTHOR = "Guy Viry", - TITLE = "Factorization of Multivariate Polynomials with Coefficients in -$F_{p}$", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, VOLUME = 15, NUMBER = 4, PAGES = "371-391", MONTH = "November", - COMMENT = {The ring of polynomials in $X,X_{1}, \1dots ,X_{m}$ are denoted -by $F_{p}[X,X_{1}, \1dots ,X_{m}]$ in $F_{p}$, that is the field of -integers defined modulo $p$. In the usual factorization algorithm defined -by Wang, the given polynolmial $P$ is first factorized modulo $\Delta^{n}$, -where $\Delta^{n}$ is an ideal. This algorithm uses a generalization of -Hensel's Lemma. If there are no extraneous factors, then the factors -defined modulo $\delta^[{n}$ correspond to the factors of $P$ in -$F_{p}[X,X_{1}, \1dots ,X_{m}]$ or else the defined factors must be -regrouped to find the factors of $P$ in $F_{p}[X,X_{1}, \1dots ,X_{m}]$. -In this paper, a mapping that transforms the product of the factors into a -sum is defined. A theorem that determines whether a subproduct of the -factors of $P$ corresponds to a factor of $P$ in $F_{p}[X,X_{1}, \1dots -,X_{m}]$ is given. Therefore the regrouping of the factors of $P$ reduces -to solving a system of linear equations, as in the univariate case, with -Berlekamp's algorithm.}} - -@ARTICLE{Voros:77, - AUTHOR = "A. Voros", - TITLE = "Asymptotic K-Expansions of Stationary Quantum States", - JOURNAL = "Ann. Inst. H. Poincare", - YEAR = 1977, VOLUME = "26A", PAGE = "343"} - -@TECHREPORT{Wanas, - AUTHOR = "M. I. Wanas", - TITLE = "The Third Face of Computer -- Computer Solution -of Symbolic Problems", - INSTITUTION = "Military Technical College, Cairo, Egypt", - NUMBER = "CAP-3 837"} - -@INPROCEEDINGS{Wanas:85, - AUTHOR = "M. I. Wanas", - TITLE = "Manipulation of Parameters Indicating the -Physical Significance of any Absolute Parallelism -Space Using {REDUCE} 2", - YEAR = 1985, - BOOKTITLE = "Tenth International Congress for Statistics, -Computer Science, Social and Demographic Research"} - -@INPROCEEDINGS{Wang:84, - AUTHOR = "Paul S. Wang and T. Y. P. Chang and J. A. van Hulzen", - TITLE = "Code Generation and Optimization for Finite Element Analysis", - BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes -in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "237-247", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Wang:93, - AUTHOR = "Jian-Xiong Wang", - TITLE = "Automatic calculation of {Feynman loop-diagrams}, I. Generation -of a simplified form of the amplitude", - YEAR = 1993, VOLUME = 77, NUMBER = 2, PAGES = "263-285", MONTH = "October"} - ABSTRACT = {In order to develop an automatic system to calculate loop -diagrams in renormalizable theories, we present the first part of a -complete system written in {REDUCE} and {RLISP}. It can generate the tensor -and gamma matrix basis which is able to cast the total amplitude into a -simpler form with the help of gauge invariance and symmetry among identical -particles.} - -@ARTICLE{Wassam:87, - AUTHOR = "W. A. {Wassam, Jr.} and Go. Torres-Vega", - TITLE = "Dual {Lanczos} Transformation Theory: Closed Set of Algebraic -Equations Connecting {Lanczos} Parameters with Moments in Moment -Expansions of Time-Dependent Quantities", - JOURNAL = "Chemical Phys. Lett.", - YEAR = 1987, VOLUME = 134, NUMBER = 4, PAGES = "355-360", - COMMENT = {"The utility of this set of equations is illustrated by using -them with the aid of symbolic manipulation on a computer to construct a -previously unknown exact continued fraction for the spectral density -of the incoherent scattering function{\ldots}" The system used is {REDUCE} -on a Burroughs. Appear enthusiastic about the possibilities for -computer algebra in related fields.}} - -@ARTICLE{Wassam:87a, - AUTHOR = "W. A. {Wassam, Jr.} and Go. Torres-Vega and J. Neito-Frausto", - TITLE = "Dual {Lanczos} Transformation Theory: Exact Continued -Fraction Expression for Resonant $\gamma$-ray Absorption Spectrum of a -Harmonically Bound Atom Executing Classical Motion Described by -{Smoluchowski} Dynamics", - JOURNAL = "Chemical Phys. Lett.", - YEAR = 1987, VOLUME = 136, NUMBER = 1, PAGES = "26-30", - COMMENT = {"{\ldots}with the aid of symbolic manipulation techniques, we -construct a previously unknown exact continued fraction for the resonance -$\gamma$-ray absorption spectrum{\dots}" The system used is {REDUCE} -on a Burroughs.}} - -@TECHREPORT{Watanabe:85, - AUTHOR = "Yoichi Watanabe", - TITLE = "Symbolic Manipulation of Structure Functions -in Availability Analysis", - INSTITUTION = "Fusion Technology Institute, University of -Wisconsin, Madison, Wisconsin", - YEAR = 1985, NUMBER = "UWFDM-658", MONTH = "November"} - -@ARTICLE{Watanabe:76, - AUTHOR = "Shunro Watanabe", - TITLE = "Formula Manipulations Solving Linear Ordinary -Differential Equations {II}", - JOURNAL = "Publications of the Research Institute for -Mathematical Sciences, Kyoto University", - YEAR = 1976, VOLUME = 11, NUMBER = 2, PAGES = "297-337"} - -@ARTICLE{Watanabe:79, - AUTHOR = "Shunro Watanabe", - TITLE = "A Verification for Non-existence of Movable Branch Points of Six -Painlev{\'e} Transcendents by Formula Manipulations", - JOURNAL = "Tokyo Journal of Mathematics", - YEAR = 1979, VOLUME = 2, NUMBER = 2, PAGES = "285-291"} - -@ARTICLE{Weber:79, - AUTHOR = "Lawrence A. Weber and Gerhard Rayna", - TITLE = "Problem \#11 Solved in {REDUCE:} A Case Study in Program -Translation", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1979, VOLUME = 13, NUMBER = 4, PAGES = "21-24", MONTH = "November"} - -@ARTICLE{Wehner:86, - AUTHOR = "M. F. Wehner and W. G. Wolfer", - TITLE = "The Pressure of a Hard Sphere Fluid on a Curved Surface", - JOURNAL = "J. Statistical Phys.", - YEAR = 1986, VOLUME = 42, PAGES = "509-521", - COMMENT = {Integral equation approach and perturbation expansions in -{REDUCE}. "Therefore, in order to avoid errors, the integrations have been -done in closed form with the algebraic manipulation routine {REDUCE}."}} - -@InProceedings{Weispfenning:94, - author = {Volker Weispfenning}, - title = {Quantifier elimination for real algebra -- the cubic case}, - booktitle = {Symbolic and Algebraic Computation}, - editor = {}, - series = {ISSAC}, - year = {1994}, - organization = {SIGSAM}, - publisher = {ACM}, - pages = {258--263} -} - -@INCOLLECTION{Winkelmann:89, - AUTHOR = "Volker Winkelmann and Friedrich W. Hehl", - TITLE = "{REDUCE} for Beginners. Six Lectures on the -Application of Computer Algebra", - EDITOR = "D. Stauffer and F. W. Hehl and V. Winkelmann and -J. G. Zabolitzky", - BOOKTITLE = "Computer Simulation and Computer Algebra. -Lectures for Beginners", - CHAPTER = 3, EDITION = "2nd", PUBLISHER = "Springer-Verlag", - YEAR= 1989} - -@TECHREPORT{Winkler:88, - AUTHOR = "F. Winkler and B. Kutzler and F. Lichtenberger", - TITLE = "Computeralgebrasysteme (in {German})", - INSTITUTION = "RISC - LINZ, Austria", TYPE = "Report", - YEAR = 1988, NUMBER = "88-10"} - -@ARTICLE {Witham:77, - AUTHOR = "C. R. Witham and S. Dubowsky", - TITLE = "An Improved Symbolic Manipulation Technique for -the Simulation of Nonlinear Dynamic Systems With Mixed -Time-Varying and Constant Terms", - JOURNAL = "Journal of Dynamic Systems, Measurement, and Control", - YEAR = 1977, MONTH = "September", PAGES = "157-165", - ABSTRACT = {The time domain behavior of nonlinear dynamic systems -often is obtained by numerical integration on the digital -computer. These solutions are usually expensive and limit -the scope of the dynamic study. The proposed improved -technique results in a substantial increase in the computational -efficiency by using automatic symbolic manipulation to generate -explicit equations of motion algebraically prior to numerical -integration.}} - -@TECHREPORT{Wolf:95, - AUTHOR = "Thomas Wolf", - TITLE = "Programs for Applying Symmetries of PDEs", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1995, TYPE = "Preprint", NUMBER = "SC 95-5", MONTH = "February", - ABSTRACT = {In this paper the programs APPLYSYM, QUASILINPDE and DETRAFO -are described which aim at the utilization of infinitesimal symmetries of -differential equations. The purpose of QUASILINPDE is the general solution -of quasilinear PDEs. This procedure is used by APPLYSYM for the -application of point symmetries for either - -calculating similarity variables to perform a point transformation which -lowers the order of an ODE or effectively reduces the number of explicitly -occuring independent variables in a PDE(-system) or for - -generalizing given special solutions of ODEs/PDEs with new constant -parameters. - -The program DETRAFO performs arbitrary point- and contact transformations -of ODEs/PDEs and is applied if similarity and symmetry variables have been -found. The program APPLYSYM is used in connection with the program LIEPDE -for formulating and solving the conditions for point- and contact -symmetries which is described in [4]. The actual problem solving is done -in all these programs through a call to the package CRACK for solving -overdetermined PDE-systems.}} - -@ARTICLE{Wood:89, - AUTHOR = "John C. Wood", - TITLE = "Harmonic Two Spheres in the Unitary Group", - YEAR = 1989, - JOURNAL = "Proc. London Math. Soc.", - VOLUME = 3, NUMBER = 58, PAGES = "608-624"} - -@TECHREPORT{Wright:84, - AUTHOR = "F. J. Wright and G. Dangelmayr", - TITLE = "Explicit Iterative Algorithms to Reduce a Univariate Catastrophe -to Normal Form", - INSTITUTION = "Universit{\"a}t T{\"u}bingen", - YEAR = 1984} - -@TECHREPORT{Wulkow:90, - AUTHOR = "Michael Wulkow and Peter Deuflhard", - TITLE = "Towards an efficient computational treatment of heterogeneous -polymer reactions", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", - YEAR = 1990, TYPE = "Preprint", NUMBER = "SC 90-1", MONTH = "January"} - -@INPROCEEDINGS{Yamamoto:87, - AUTHOR = "T. Yamamoto and Y. Aoki", - TITLE = "{REDUCE} 3.2 on {iAPX 86/286}-based Personal Computers", - BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes -in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "134-135", - PUBLISHER = "Springer-Verlag"} - -@ARTICLE{Yamartino:91, - AUTHOR = "Robert J. Yamartino and Richard Pavelle", - TITLE = "An Application of Computer Algebra to a Problem in Stratified -Fluid Flow", - JOURNAL = "J. Symb. Comp.", - YEAR = 1991, VOLUME = 12, NUMBER = 6, PAGES = "669-672", MONTH = "December", - ABSTRACT = {The computationally tedious problem of considering trial Green's -function solutions to the fourth-order partial differential equation for a -stratified atmosphere flowing over a hill is approached using MACSYMA. -Significance of the problem, solution methodologies and CPU time -intercomparisons using various computer platforms and other algebra systems -are discussed.}} - -@ARTICLE{Yannouleas:88, - AUTHOR = "C. Yannouleas and J. M. Pacheco", - TITLE = "An Algebraic Program for the States Associated with the -${U(5)} \supset {O(5)} \supset {O(3)}$ Chain of Groups", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1988, VOLUME = 52, NUMBER = 1, PAGES = "85-92", MONTH = "December"} - -@ARTICLE{Yannouleas:89, - AUTHOR = "C. Yannouleas and J. M. Pacheco", - TITLE = "Algebraic Manipulation of the States Associated with the -${U(5)} \supset {O(5)} \supset {O(3)}$ Chain of {groups:} -Orthonormalization and Matrix Elements", - JOURNAL = "Comp. Phys. Comm.", - YEAR = 1989, VOLUME = 54, NUMBER = "2 and 3", PAGES = "315-328", -MONTH = "June and July"} - -@ARTICLE{Zacrep:75, - AUTHOR = "Douglas Zacrep and Bing-Lin Young", - TITLE = "Trace and {Ward-Takahashi} Identity Anomalies -in an {SU}(3) Current Model with Energy-Momentum Tensor", - JOURNAL = "Phys. Rev. D", - YEAR = 1975, VOLUME = 12, PAGES = "513-522"} - -@ARTICLE{Zahalak:87, - AUTHOR = "G. I. Zahalak and P. R. Rao and S. P. Sutera", - TITLE = "Large Deformations of a Cylindrical Liquid-Filled Membrane -by a Viscous Shear Flow", - JOURNAL = "J. Fluid Mech.", - YEAR = 1987, VOLUME = 179, PAGES = "283-305", - COMMENT = {Draws attention to the use of classical perturbation -techniques combined with computer algebra as an alternative to -numerical calculation.}} - -@ARTICLE{Zeng:84, - AUTHOR = "{Wan-zhen} Zeng and {Bail-lin} Hao", - TITLE = "Scaling Property of Period-n-Tupling -Sequences in One-Dimensional Mappings", - JOURNAL = "Commun. in Theor. Phys., Beijing, China", - YEAR = 1984, VOLUME = 3, NUMBER = 3, PAGES = "283-295"} - -@ARTICLE{Zharkov:93, - AUTHOR = "A. Yu. Zharkov", - TITLE = "Computer Classification of the Integrable Coupled {Kdv}-like -Systems with Unit Main Matrix", - JOURNAL = "J. Symbolic Computation", - YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "85-90", MONTH = "January", - COMMENT = {The classification of 2-component systems of equations for -the form $u^{i}_{t}=u^{i}_{xxx}+c_{ij}u^{i}u^{j}_{x}(i,j=1,2)$ which -possess higher symmetries is given. A new class of such integrable -KdV-like systems is obtained. All the computations have been done using -the {REDUCE}computer algebra system.}} - -@InProceedings{Zharkov:93a, - author = "A. Yu. Zharkov and Yu. A. Blinkov", - title = "Involution Approach to Solving Systems of Algebraic -Equations", - booktitle = "Proceedings of the 1993 International IMACS Symposium on - Symbolic Computation", - year = "1993", - editor = "G. Jacob and N. E. Oussous and S. Steinberg", - pages = "11-16", - organization ="IMACS", - publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", - - comment = {An "involutive set" is a canonical basis of a 0-dim - polynomial ideal based on Janet division and well suited for - equation solving. It can be transformed into a - lexicographic Groebner basis by linear algebra tools. - The algorithms for computing involutive sets has been - developed using {REDUCE}.} -} - -@TECHREPORT{Zhidkova:78, - AUTHOR = "I. E. Zhidkova and I. P. Nedyalkov and V. A. Rostovtsev", - TITLE = "On Applicability Limits of the Experimental Method -for Investigating Strong Gravitational Fields", - INSTITUTION = "J.I.N.R., Dubna", - YEAR = 1978, NUMBER = "P2 - 11589", - COMMENT = {Mechanical effects of tidal forces on the physical apparatus -exploring strong gravitational fields are investigated.}} - +% REDUCE BIBLIOGRAPHY + +% Part 1: A-E + +% Copyright (c) 1995 RAND. All Rights Reserved. + +% Additions and corrections are solicited. Please send them, in the +% same format as these entries if possible, to reduce at rand.org. + + +@ARTICLE{Abbott:85, + AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", + TITLE = "A Remark on Factorisation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "31-33", MONTH = "May"} + +@INPROCEEDINGS{Abbott:86, + AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", + TITLE = "The {Bath} Algebraic Number Package", + BOOKTITLE = "Proc. of {SYMSAC} '86", + YEAR = 1986, PAGES = "250-253"} + +@INPROCEEDINGS{Abbott:87, + AUTHOR = "J. A. Abbott and J. H. Davenport", + TITLE = "Polynomial Factorization: An Exploration of {Lenstra's} +Algorithm", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes in Computer Science", + YEAR = 1987, VOLUME = 378, PAGES = "391-402", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Abbott:87a, + AUTHOR = "J. A. Abbott", + TITLE = "Integration: Solving the {Risch} Differential Equation", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "465-467", + PUBLISHER = "Springer-Verlag"} + +@PHDTHESIS{Abbott:88, + AUTHOR = "J. A. Abbott", + TITLE = "Factorisation of Polynomials over Algebraic Number Fields", + SCHOOL = "Univ. of Bath, England", + YEAR = 1988} + +@ARTICLE{Abbott:88a, + AUTHOR = "J. A. Abbott and J. H. Davenport", + TITLE = "A Remark on a Paper by {Wang}: Another Surprising Property of 42", + JOURNAL = "Math. Comp.", + YEAR = 1988, VOLUME = 51, PAGES = "837-839"} + +@INPROCEEDINGS{Abbott:89, + AUTHOR = "J. A. Abbott", + TITLE = "Recovery of Algebraic Numbers from their p-Adic Approximations", + BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", + YEAR = 1989, PAGES = "112-120"} + +@TECHREPORT{Abbott:89a, + AUTHOR = "J. A. Abbott and R. J. Bradford and J. H. Davenport", + TITLE = "A Remark on the Multiplication of Sparse Polynomials", + NUMBER = "TR 89-21", YEAR = 1989, + INSTITUTION = "School of Mathematical Sciences, University of Bath"} + +@INPROCEEDINGS{Abdali:88, + AUTHOR = "S. K. Abdali and D. S. Wise", + TITLE = "Experiments with Quadtree Representation of Matrices", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "96-108"} + +@ARTICLE{Abiezzi:83, + AUTHOR = "Salim S. {Abi-Ezzi}", + TITLE = "Clarification to the Symbolic Mode in {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = "3 and 4", PAGES = "43-47", + MONTH = "August and November"} + +@INPROCEEDINGS{Abramov:91, + AUTHOR = "S. A. Abramov and K. Yu. Kvansenko", + TITLE = "Fast Algorithms to Search for the Rational Solutions of Linear +Differential Equations with Polynomial Coefficients", + EDITOR = "Stephen M. Watt", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, + PAGES = "267-270"} + +@TECHREPORT{Abramov:91a, + AUTHOR = "S. A. Abramov and K. Yu. Kvashenko", + TITLE = "Fast search of a certain type solutions of linear ordinary +differential equations with polynomial coefficients", + INSTITUTION = "Computer Center of the USSR, Academy of Science, Moscow", + YEAR = 1991} + +@InProceedings{Adamchik90, + author = "V. S. Adamchik and O. I. Marichev", + title = "The Algorithm for calculating Integrals of + Hypergeometric type functions and its realization in + {REDUCE} System", + booktitle = "Proceedings of the 1990 International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "212-224", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Adams:83, + AUTHOR = "K. J. Adams", + TITLE = "Analytic Estimates for the Dynamic Aperture of Nonlinear Lattices", + JOURNAL = "IEEE Trans. Nucl. Sci.", + YEAR = 1983, VOLUME = "NS-30", PAGES = "2436-2438", + COMMENT = {"For an accelerator lattice{\ldots}" {REDUCE} was used to obtain low +order coefficients in the calculation of the amplitude.}} + +@ARTICLE{Adkins:83, + AUTHOR = "G. S. Adkins", + TITLE = "Analytic Evaluation of an {O}($\alpha$) Vertex Correction to the +Rate of Orthopositronium", + JOURNAL = "Phys. Rev. A", + YEAR = 1983, VOLUME = 27, PAGES = "530-532", + ABSTRACT = {The order-$\alpha$ correction to the lowest order +orthopositronium decay rate due to the two outer-vertex graphs obtained in +analytic form.}} + +@ARTICLE{Adkins:83a, + AUTHOR = "G. S. Adkins and F. R. Brown", + TITLE = "Rate for Positronium Decay to Five Photons", + JOURNAL = "Phys. Rev. A", + YEAR = 1983, VOLUME = 28, PAGES = "1164-1165", + COMMENT = {{REDUCE} used to calculate trace of $\gamma$ matrices. Large +calculation.}} + +@ARTICLE{Adkins:85, + AUTHOR = "G. S. Adkins", + TITLE = "Inner-Vertex Contributions to the Decay Rate of Orthopositronium", + JOURNAL = "Phys. Rev. A", + YEAR = 1985, VOLUME = 31, PAGES = "1250-1252", + COMMENT = {{REDUCE} trace calculations. "In this paper the order-$\alpha$ +contribution to the inner-vertex graphs to the decay rate of +orthopositronium is obtained in analytic form."}} + +@ARTICLE{Aguilera-Navarro:87, + AUTHOR = "V. C. Aguilera-Navarro and R. Guardiola and C. Keller and +M. de Llano and M. Popovic and M. Fortes", + TITLE = "Van der {Waals} Perturbation Theory for Fermion and Boson +Ground-State Matter", + JOURNAL = "Phys. Rev. A", + YEAR = 1987, VOLUME = 35, PAGES = "3901-3910", + COMMENT = {Uses computer algebra to rearrange ideal-gas-based low-density +expansions; to them {REDUCE} or {MACSYMA} provide just the expertise they +require to substitute forms into equations, and so makes their +formulation possible.}} + +@TECHREPORT{Akselrod:90, + AUTHOR = "I.R. Akselrod and V.P. Gerdt and V.E. Kovtun and V.N. Robuk", + TITLE = "Construction of a {Lie} algebra by a subset of generators and +commutation relations", + INSTITUTION = "J.I.N.R.", YEAR = 1990, TYPE = "Preprint", + NUMBER = "E5-90-508", + ABSTRACT = {The problem of constructing the quotient algebra for a free +{Lie} algebra over an ideal given by a subset of generators and commutation +relations is investigated. The method proposed to solve this problem can be +applied in particular for constructing a {L-A} pair for nonlinear evolution +equations. The algorithm is based on the concept of {Hall} basis for a +free {Lie} algebra and is implemented in the computer algebra system +{REDUCE}.}} + +@ARTICLE{Aldins:69, + AUTHOR = "J. Aldins and S. J. Brodsky and A. J. Dufner and +T. Kinoshita", + TITLE = "Photon-Photon Scattering Contribution to the Sixth +Order Magnetic Moments of the Muon and Electron", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1969, VOLUME = 23, PAGES = "441-443"} + +@TECHREPORT{Alekseev:86, + AUTHOR = "A. I. Alekseev and V. F. Edneral", + TITLE = "Tensor Structure of Axial Gauge Polarization Operator in the +Infrared Region", + INSTITUTION = "IHEP", YEAR = 1986, TYPE = "Preprint", + NUMBER = "86-46"} + +@ARTICLE{Alekseev:87, + AUTHOR = "A. I. Alekseev and V. F. Edneral", + TITLE = "Tensor Structure of Gluon Polarization Operator in the +Axial Gauge for Infra-Red Region", + JOURNAL = "Journal of Nuclear Physics", + YEAR = 1987, PAGES = "1105-1114"} + +@TECHREPORT{Alekseev:87a, + AUTHOR = "A. I. Alekseev and V. F. Edneral", + TITLE = "On Evaluation of {Feynman} Integrals in Axial Gauge", + INSTITUTION = "IHEP", YEAR = 1987, TYPE = "Preprint", + NUMBER = "87-118", + ABSTRACT = {The recurrent algorithm for axial gauge calculations of +one-loop massless {Feynman} integrals in the n-dimensional +momentum space is described. The algorithm we suggest is +realized on the basis of {REDUCE} system and presented as +a procedure. It is rather effective for cumbersome +combinations of those integrals.}} + +@ARTICLE{Alfeld:82, + AUTHOR = "P. Alfeld", + TITLE = "Fixed Point Iteration with Inexact Function Values", + JOURNAL = "Math. Comp.", + YEAR = 1982, VOLUME = 38, PAGES = "87-98", + COMMENT = {Numerical analysis generating an improved iterative scheme. +"The technical manipulations in this paper were carried out using the +symbol manipulation language {REDUCE}."}} + +@TECHREPORT{Amirkhanov:87, + AUTHOR = "I. V. Amirkhanov and E. P. Zhidkov and I. E. Zhidkova", + TITLE = "The Conditions of Bounding of the Oscillation Amplitudes of +Charge Particle within the Resonance Vicinity Investigations", + INSTITUTION = "J.I.N.R., Dubna", YEAR = 1987, NUMBER = "P11-87-452"} + +@INPROCEEDINGS{Amirkhanov:91, + AUTHOR = "I.V. Amirkhanov and E.P. Zhidkov and I.E. Zhidkova", + TITLE = "The Betatron Oscillations in the Vicinity of Nonlinear Resonance +in Cyclic Accelerator Investigation", + EDITOR = "Stephen M. Watt", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, + PAGES = "452-453"} + +@ARTICLE{Antweiler:89, + AUTHOR = "Werner Antweiler and Andreas Strotmann and Volker Winkelmann", + TITLE = "A {\TeX}-{REDUCE}-Interface", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1989, VOLUME = 23, + MONTH = "February", PAGES = "26-33"} + +@ARTICLE{Appelquist:70, + AUTHOR = "T. W. Appelquist and S. J. Brodsky", + TITLE = "The Order $\alpha^{2}$ Electrodynamic Corrections to +the {Lamb} Shift", + JOURNAL = "Phys. Rev. Letters", + YEAR = 1970, VOLUME = 24, PAGES = "562-565"} + +@TECHREPORT{Arbuzov:86, + AUTHOR = "B. A. Arbuzov and E. E. Boos and A. I. Davydychev", + TITLE = "Infrared Asymptotics of Gluonic {Green} Functions +in Covariant Gauge", + INSTITUTION = "IHEP", YEAR = 1986, TYPE = "Preprint", + NUMBER = "86-123"} + +@TECHREPORT{Kendall:93, + AUTHOR = "Gerard Ben Arous and Michael Cranston and Wilfrid S. Kendall", + TITLE = "Coupling constructions for hypoelliptic diffusions: Two +examples", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1993, + MONTH = "October", TYPE = "Research Report", NUMBER = 261, + ABSTRACT = {Coupling constructions are given for two examples of +hypoelliptic diffusions with smooth coefficients: the two-dimensional +diffusion formed by scalar Brownian motion and its time integral; and the +three-dimensional diffusion formed by planar Brownian motion and its +stochastic area. In both cases it is shown that one can construct +co-adapted copies of Brownian motion such that the corresponding copies of +the diffusion will couple in finite time. The first case uses stopping +time arguments; the second is computationally more involved and the +solution was found using a computer algebra implementation of stochastic +calculus (though the final proof has been checked completely by hand). +Questions are formulated about coupling problems for more general +hypoelliptic diffusions with smooth coefficients.}} + +@ARTICLE{Aso:81, + AUTHOR = "T. Aso and T. Nonoyama and S. Kato", + TITLE = "Numerical Simulation of Semidiurnal Atmospheric Tides", + JOURNAL = "J. Geophysical R.", + YEAR = 1981, VOLUME = 86, NUMBER = 11, PAGES = "388-400", + COMMENT = {"Numerical modeling of the solar and lunar semidiurnal +atmospheric tides has been performed by invoking a comprehensive approach that +includes both algebraic manipulation and numerical solution of the +primitive equation system." Used {REDUCE} to overcome difficulties of +complication and error.}} + +@ARTICLE{Atherton:73, + AUTHOR = "R. W. Atherton and G. M. Homsey", + TITLE = "Use of Symbolic Computation to Generate Evolution +Equations and Asymptotic Solutions to Elliptic Equations", + JOURNAL = "Journ. Comp. Phys.", + YEAR = 1973, VOLUME = 1, PAGES = "45-59"} + +@ARTICLE{Aurenche:84, + AUTHOR = "P. Aurenche and A. Douir and R. Baier and M. Fontannaz and +D. Schiff", + TITLE = "Photoproduction of Hadrons at Large Transverse Momentum in +Second Order {QCD}", + JOURNAL = "Phys. Lett.", + YEAR = 1984, VOLUME = "135B", PAGES = "164-168", + COMMENT = {Uses {REDUCE} and {SCHOONSCHIP} in the extension of calculations +to a higher order to keep pace with experimental results.}} + +@ARTICLE{Aurenche:84a, + AUTHOR = "P. Aurenche and A. Douir and R. Baier and M. Fontannaz and +D. Schiff", + TITLE = "Prompt Photon Production at Large $p_{\tau}$ in {GCD} Beyond the +Leading Order", + JOURNAL = "Phys. Lett.", + YEAR = 1984, VOLUME = "140B", PAGES = "87-92", + COMMENT = {Uses {REDUCE} and {SCHOONSCHIP}.}} + +@ARTICLE{Autin:89, + AUTHOR = "B. Autin and J. Bengtsson", + TITLE = "Symbolic Evaluation of Integrals Occurring in Accelerator +Orbit Theory", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 7, NUMBER = 2, PAGES = "183-187", MONTH = "February"} + +@ARTICLE{Baekler:84, + AUTHOR = "P. Baekler and F. W. Hehl", + TITLE = "A Charged {Taub-NUT} Metric with Torsion: A New Axially +Symmetric Solution of the {Poincar\'{e}} Gauge Field Theory", + JOURNAL = "Phys. Lett.", + YEAR = 1984, VOLUME = "100A", PAGES = "277-316"} + +@TECHREPORT{Baekler:84a, + AUTHOR = "Peter Baekler and Friedrich W. Hehl", + TITLE = "On the Dynamics of the Torsion of Spacetime: +Exact Solutions in a Gauge Theoretical Model of Gravity", + INSTITUTION = "Department of Physics, University of California, +Los Angeles", YEAR = 1984, + NUMBER = "UCLA/84/TEP/19", PAGE = "18", MONTH = "December"} + +@INPROCEEDINGS{Baekler:86, + AUTHOR = "P. Baekler and F. W. Hehl and E. W. Mielke", + TITLE = "Nonmetricity and Torsion: Facts and Fancies in Gauge +Approaches to Gravity", + EDITOR = "R. Ruffini", + BOOKTITLE = "Proc. 4th Marcel Grossmann Meeting on +General Relativity", PUBLISHER = "North-Holland, Amsterdam", + YEAR = 1986, PAGES = "277-316"} + +@ARTICLE{Baekler:87, + AUTHOR = "P. Baekler and R. Hecht and F. W. Hehl and T. Shirafuji", + TITLE = "Mass and Spin of Exact Solutions of the {Poincar{\'e}} Gauge +Theory", + JOURNAL = "Prog. Theor. Phys.", + YEAR = 1987, VOLUME = 78, PAGES = "16-21"} + +@ARTICLE{Baekler:87a, + AUTHOR = "P. Baekler and M. Guerses", + TITLE = "Exact Solutions of the {Poincar{\'e}} Gauge Theory from Its +Linearized Field Equations", + JOURNAL = "Lett. Math. Phys.", + YEAR = 1987, VOLUME = 14, PAGES = "185-191"} + +@ARTICLE{Baekler:87b, + AUTHOR = "P. Baekler and E. W. Mielke and F. W. Hehl", + TITLE = "Kinky Torsion in a {Poincar{\'e}} Gauge Model of Gravity Coupled +to a Massless Scalar Field", + JOURNAL = "Nuclear Phys.", + YEAR = 1987, VOLUME = "B288", PAGES = "800-812"} + +@ARTICLE{Baekler:88, + AUTHOR = "P. Baekler and M. Seitz and V. Winkelmann", + TITLE = "Cylindrically Symmetric Solutions of Self-Consistently +Coupled {Dirac} Fields in Gauge Theories of Gravity", + JOURNAL = "Class. Quantum Grav.", + YEAR = 1988, VOLUME = 5, PAGES = "479-490"} + +@ARTICLE{Baekler:88a, + AUTHOR = "P. Baekler and M. Guerses and F. W. Hehl and J. D. McCrea", + TITLE = "The Exterior Gravitational Field of a Charged Spinning +Source in the {Poincar{\'e}} Gauge Theory: A {Kerr-Newman} Metric with +Dynamic Torsion", + JOURNAL = "Phys. Lett.", + YEAR = 1988, VOLUME = "A128", PAGES = "245-250"} + +@ARTICLE{Baekler:88b, + AUTHOR = "P. Baekler and M. Guerses and F. W. Hehl", + TITLE = "A New Method to Solve the Field Equations of {Poincar{\'e}} +Gauge Theories", + JOURNAL = "Class. Quantum Grav.", + YEAR = 1988} + +@TECHREPORT{Bahrdt:90, + AUTHOR = "J. Bahrdt and G. W{\"u}stefeld", + TITLE = "A New Tracking Routine for Particles in Undulator and +Wiggler Fields", + INSTITUTION = "Technischer Bericht", + YEAR = 1990, TYPE = "Report", NUMBER = "BESSY TB Nr. 158", + MONTH = "October", + ABSTRACT = {In this report we present an approximated solution of the +particle motion in wiggler and undulator fields by an algebraic mapping +routine. The solution is based on a series expansion up to the third +order in the two transversal angle coordinates and, as a third variable, +the bending radius of the particle orbit. The wiggler and undulator fields +are represented by an expansion as suggested by K. Halbach. + +The report consists of two parts. In the first part we solve the +equations of motion by an iteration procedure, which originally was also +the first approach. In the second part the solution is based on a Taylor +series expansion. Both approaches are equivalent.}, +ABSTRACT2 = {Beside the presentation of the solution, the main topics +discussed in the two parts are the calculation speed and accuracy of the +algebraic method in comparison to integration methods along undulator +fields, as they are typically applied in lattice design codes. + +As a further result of the discussion we obtain a proper canonical mapping +routine at least as accurate but faster than typical integration routines.}} + +@ARTICLE{Baier:81, + AUTHOR = {V. N. Baier and A. G. Grozin}, + TITLE = {Inclusive quarkonium production in {$e^+ e^-$} annihilation}, + JOURNAL = {Yad. Fiz. (Sov. J. Nucl. Phys.)}, + YEAR = 1981, VOLUME = 33, NUMBER = 2, PAGES = {491-500}} + +@ARTICLE{Baier:85, + AUTHOR = {V. N. Baier and A. G. Grozin}, + TITLE = {Gluonic contributions to the exclusive amplitudes}, + JOURNAL = {Zeit. f\"ur Phys. C}, + YEAR = 1985, VOLUME = 29, PAGES = {161-165}} + +@ARTICLE{Baier:90, + AUTHOR = {V. N. Baier and A. G. Grozin}, + TITLE = {Decay {$B \to D l \bar\nu$} from {QCD} sum rules}, + JOURNAL = {Zeit. f\"ur Phys. C}, + YEAR = 1990, VOLUME = 47, PAGES = {669-675}} + +@TECHREPORT{Bajla:78, + AUTHOR = "I. Bajla and G. A. Ososkov and A. C. Hearn", + TITLE = "The Orthogonalization Program of Polynomials +in Two Variables in {REDUCE}-2 Language", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1978, TYPE = "Report", NUMBER = "P10-11944", + ABSTRACT = {The analytical algorithm for constructing orthogonal +polynomials in two variables, based on the {Gram-Schmidt} +orthogonalization method, is proposed.}} + +@INPROCEEDINGS{Balian:78, + AUTHOR = "R. Balian and G. Parisi and A. Voros", + TITLE = "Quartic Oscillator", + YEAR = 1978, MONTH = "May", + BOOKTITLE = "Proc. of the Colloq. on Mathematical Problems in {Feynman} +Path Integrals, Marseille", + ABSTRACT = {On the example of the semi-classical expansion for the levels +of the quartic oscillator -(d**2/dq**2)+q**4, we show how the complex WKB +method provides information about the singularities of the Borel transform +of the semi-classical series.}} + +@ARTICLE{Baker:81, + AUTHOR = "G. A. Baker and L. P. Benofy and M. Fortes and M. de Llano and +S. M. Peltier and A. Plastino", + TITLE = "Hard-Core Square-Well Fermion", + JOURNAL = "Phys. Rev. A", + YEAR = 1982, VOLUME = 26, PAGES = "3575-3588", + COMMENT = {The mixed use of {FORTRAN} and {REDUCE}, various derivative were +calculated algebraically, but the double series was evaluated numerically.}} + +@ARTICLE{Barbier:92, + AUTHOR = "Christine Barbier and Peter Bettess and Jacqueline A. Bettess", + TITLE = "Automatic Generation of Mapping Functions for Infinite Elements +using {REDUCE}", + JOURNAL = "J. Symbolic Computation", + YEAR = 1992, VOLUME = 14, NUMBER = 5, PAGES = "523-534", MONTH = "November", + ABSTRACT = {Co continuous basis functions for use in the finite element +method when the elements extend to infinity in one or more directions can be +derived simply following the method of Zienkiewicz. The numerical code +for these functions can be generated automatically using computer algebra +languages such as {REDUCE}. This paper describes the method and explains +how {REDUCE} is used to easily produce numerical code.}} + +@ARTICLE{Barfoot:86, + AUTHOR = "D. T. Barfoot and D. J. Broadhurst", + TITLE = "Investigation of a bound on the anomalous dimensions of four-quark +operators", + JOURNAL = "Phys. Lett. B", + YEAR = 1986, VOLUME = 166, PAGES = "347-350"} + +@ARTICLE{Barfoot:87, + AUTHOR = "D. T. Barfoot and D. J. Broadhurst", + TITLE = "Finite field theories in three dimensions with and without +supersymmetry", + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1987, VOLUME = 33, PAGES = "391-395"} + +@ARTICLE{Barfoot:88, + AUTHOR = "D. T. Barfoot and D. J. Broadhurst", + TITLE = {$\mbox{Z}_2\times\mbox{S}_6$ symmetry of the two-loop diagram}, + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1988, VOLUME = 41, PAGES = "81-85"} + +@ARTICLE{Bark:78, + AUTHOR = "Fritz H. Bark and Herman Tinoco", + TITLE = "Stability of Plane {Poiseuille} Flow of a Dilute +Suspension of Slender Fibres", + JOURNAL = "J. Fluid Mech.", + YEAR = 1978, VOLUME = 87, PAGES = "321-333", + ABSTRACT = {The linear hydrodynamic stability problem for plane {Poiseuille} +flow of a dilute suspension of rigid fibers is solved +numerically. The constitutive equation given by {Batchelor} +is used to model the rheological properties of the suspension. +The resulting eigenvalue problem is shown to be singular.}} + +@ARTICLE{Barthes-Biesel:73, + AUTHOR = "D. Barthes-Biesel and A. Acrivos", + TITLE = "On Computer Generated Analytic Solutions to the +Equations of Fluid Mechanics, The Case of Creeping Flows", + JOURNAL = "Journ. Comp. Phys.", + YEAR = 1973, VOLUME = 3, PAGES = "403-411"} + +@ARTICLE{Barton:72, + AUTHOR = "David Barton and Anthony C. Hearn", + TITLE = "Comment on Problem \#2 - The {Y(2n)} Functions", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1972, VOLUME = 15, + ABSTRACT = {A compact program for the solution of {SIGSAM} Problem \#2 +is presented.}} + +@ARTICLE{Bateman:86, + AUTHOR = "G. Bateman and R. G. Storer", + TITLE = "Direct Determination of Axisymmetric Magnetohydrodynamic +Equilibrium in {Hamada} Coordinates", + JOURNAL = "Journ. Comp. Phys.", + YEAR = 1986, VOLUME = 64, PAGES = "161-176", + COMMENT = {Plasma. {"REDUCE} was used to analyse the general set of +equations for large numbers of {Fourier} harmonics {\ldots}"}} + +@INPROCEEDINGS{Belkov:91, + AUTHOR = "Alexander A. Bel'Kov and Alexander V. Lanyov", + TITLE = "{REDUCE} Usage for Calculation of Low-Energy Process Amplitudes in +Chiral {QCD} Model", + EDITOR = "Stephen M. Watt", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, + PAGES = "454-455", + ABSTRACT = {We describe the extension of {REDUCE} capabilities for the +calculations of strong and weak meson processes within the chiral +Lagrangians with higher derivatives. The main non-trivial difficulty is to +obtain the process amplitude from the Lagrangian, describing these +interactions. Another one is to overcome some {REDUCE} deficiencies such +as the lack of arguments in the matrix data type as well as of some +physical operations with the particle operators. This package of procedures +allows one to claculate the amplitudes of the strong and weak processes by +simple specifying the particles involved and their momenta.}} + +@TECHREPORT{Bennett:88, + AUTHOR = "J. P. Bennett and J. H. Davenport and H. M. Sauro", + TITLE = "Solution of Some Equations in Biochemistry", + INSTITUTION = "School of Mathematical Sciences, University of +Bath, England", NUMBER = "88-12", YEAR = 1988} + +@ARTICLE{Bennett:93, + AUTHOR = "J. P. Bennett and M. Grinfeld and J. Hubble", + TITLE = "Computer Algebra Techniques in Affinity Binding Equations: +the Dimer Case", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "79-83", MONTH = "January", + COMMENT = {In this note we apply computer algebra techniques to affinity +binding equations. We treat the situation in which the protein is +dimeric and shows cooperative binding. Special attention is paid to the +case where more than one molecule of the immobilized ligand can be +bound by the macromolecule.}} + +@ARTICLE{Berends:81, + AUTHOR = "A. Berends and R. Kleiss and P. de Causmaecher and T. T. Wu", + TITLE = "Single Bremsstrahlung Process in Gauge Theories", + JOURNAL = "Phys. Lett.", + YEAR = 1981, VOLUME = "103B", PAGES = "124-128", + COMMENT = {Used {REDUCE} to calculate 25 {Feynman} diagrams to produce +theoretical results which could be checked against experiment.}} + +@TECHREPORT{Berkovich:89, + AUTHOR = "L.M. Berkovich and V.P. Gerdt and Z.T. Kostova and +M.L. Nechaevsky", + TITLE = "Second Order Reducible Linear Differential Equations", + INSTITUTION = "J.I.N.R., Dubna", YEAR = 1989, TYPE = "Preprint", + NUMBER = "E5-89-141"} + +@TECHREPORT{Berkovich:90, + AUTHOR = "L.M. Berkovich and V.P. Gerdt and Z.T. Kostova and +M.L. Nechaevsky", + TITLE = "Computer algebra generating related {2nd} order linear differential +equation", + INSTITUTION = "J.I.N.R., Dubna", YEAR = 1990, TYPE = "Preprint", + NUMBER = "E5-90-509", + ABSTRACT = {An algorithm with its mathematical foundation concerning {2nd} +order ordinary linear differential equations {(OLDE)} is described. It +allows one to generate related {four-parametric} families of {OLDE} with +coefficients of preassigned (in the scope of the procedure) structures +integrable in terms of a given (generating) equation. The number of those +families in each next generation grows according to geometric progression +with ratio eight. Several examples of both mathematical and physical +significance illustrate the efficiency of the algorithm implemented in the +{REDUCE} compute algebra system.}} + +@ARTICLE{Berman:63, + AUTHOR = "S. M. Berman and Y. S. Tsai", + TITLE = "Intermediate Boson Pair Production as a Means for +Determining its Magnetic Moment", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1963, VOLUME = 11, PAGES = "483-487"} + +@INPROCEEDINGS{Berndt:91, + AUTHOR = "R. Berndt and A. Lock and G. Witte and Ch. W{\"o}ll", + TITLE = "Application of Computer Algebra to Surface Lattice Dynamics", + EDITOR = "Stephen M. Watt", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", YEAR = 1991, + PAGES = "433-438", + ABSTRACT = {Lattice dynamical calculations for surfaces and in particular +for stepped and adsorbed covered surfaces are commonly hampered by the +complexity of the dynamical matrix for these systems. We propose the use +of computer algebra programs to set up the dynamical matrix. In the +present implementation the dynamical matrix is calculated fully analytically +within the framework of a force constant-model and partially analytically +for other interaction models such as the shell model or the bond charge +model.}} + +@ARTICLE{Bessis:85, + AUTHOR = "N. Bessis and G. Bessis and D. Roux", + TITLE = "Closed-Form Expressions for the {Dirac-Coulomb} Radial $r^{t}$ +Integrals", + JOURNAL = "Phys. Rev. A", + YEAR = 1985, VOLUME = 32, PAGES = "2044-2050", + COMMENT = {No direct algebraic manipluation, but the formula is stated to be +well suited to evaluation by {REDUCE} or {MACSYMA}, and this is an +advantage of their formula.}} + +@ARTICLE{Bilge:92, + AUTHOR = "Ay{\c{s}}e H{\"{u}}meyra Bilge", + TITLE = "A {REDUCE} program for the integration of differential +polynomials", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1992, VOLUME = 71, NUMBER = 3, PAGES = "263-268", + MONTH = "September", + COMMENT = {A differential polynomial F[u] is a polynomial expression of the +derivatives of the function u(x). A {REDUCE} program for the integration +of differential polynomials is given. The program is tested on the +computation of the conserved densities of polynomial evolution equations. +Input and output from the test runs are included in the library files.}} + +@TECHREPORT{Billoire:78, + AUTHOR = "A. Billoire and R. Lacaze and A. Morel and H. Navelet", + TITLE = "The {OZI} Rule Violating Radiative Decays of the Heavy +Pseudoscalars", + INSTITUTION = "{CEN}-Saclay", YEAR = 1978, TYPE = "Report", + NUMBER = "DpH-T 43/78", + COMMENT = {Submitted to Phys. Letters B. +In lowest order {QCD} the rates for radiative transitions violating the {OZI} +rule of heavy pseudoscalars are found to be extremely small.}} + +@ARTICLE{Biro:86, + AUTHOR = "T. S. Biro and J. Zimanyi and M. Zimanyi", + TITLE = "Hadrochemistry in Relativistic Mean Fields", + JOURNAL = "Physics Letters", + YEAR = 1986, VOLUME = "167B", NUMBER = 3, PAGES = "271-276", + MONTH = "February"} + +@ARTICLE{Biro:87, + AUTHOR = "T. S. Biro and K. Niita and A. L. de Paoli and W. Bauer +and W. Cassing and U. Mosel", + TITLE = "Microscopic Theory of Photon Production in Proton-Nucleus +and Nucleus-Nucleus Collisions", + JOURNAL = "Nuclear Physics", + YEAR = 1987, VOLUME = "475A", PAGES = "579-597", MONTH = "December"} + +@TECHREPORT{Birrell:77, + AUTHOR = "N. D. Birrell", + TITLE = "The Application of Adiabatic Regularization +to Calculations of Cosmological Interest", + INSTITUTION = "Dept. Math, King's College, London", + YEAR = 1977} + +@ARTICLE{Biswas:75, + AUTHOR = "S. N. Biswas and S. R. Chaudhuri and K. S. Taank +and J. A. Campbell", + TITLE = "Neutrino Production in Stellar Matter by Photons +in a Renormalizable Scalar-Boson-Exchange Model of Weak +Interactions", + JOURNAL = "Phys. Rev. D", + YEAR = 1975, VOLUME = 8, PAGES = "2523-2525"} + +@TECHREPORT{Bittencourt:90, + AUTHOR = "Guilherme Bittencourt and Jacques Calmet", + TITLE = "Integrating Computer Algebra and Knowledge Representation", + INSTITUTION = "Universit{\"a}t Karlsruhe Institut f{\"u}r +Algorithmen und Kognitive Systeme", YEAR = 1990, TYPE = "Preprint"} + +@InProceedings{Blum:93, + author = "W. Blum and V. Ganzha and W. Strampp", + title = "An Introduction to ODE's by CAS", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "110-119", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + comment = {Use of {REDUCE} and MATHEMATICA for math education.} +} + +@ARTICLE{Bocko:92, + AUTHOR = "J. Bocko", + TITLE = "{EQSHELL} - a {REDUCE-based} program for generation of equations +of equilibrium for shell", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1992, VOLUME = 69, NUMBER = 1, PAGES = "215-222", MONTH = "February", + COMMENT = {EQSHELL is a REDUCE-based program which generates the equations +of equilibrium for various shapes of shells. This program also produces +other important characteristics of the shell.}} + +@ARTICLE{Boege:86, + AUTHOR = "W. Boege and R. Gebauer and H. Kredel", + TITLE = "Some Examples for Solving Systems of Algebraic Equations +by Calculating {Groebner} Bases", + JOURNAL = "J. Symbolic Computation", + YEAR = 1986, VOLUME = 2, NUMBER = 1, PAGES = "83-98", MONTH = "March"} + +@ARTICLE{Bogdanova:88, + AUTHOR = "N. Bogdanova and H. Hogreve", + TITLE = "A {REDUCE} Package for Exact {Coulomb} Interaction Matrix +Elements", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1988, VOLUME = 48, NUMBER = 2, PAGES = "319-326", MONTH = "February"} + +@ARTICLE{Bordoni:81, + AUTHOR = "Luciana Bordoni and Attilio Colagrossi", + TITLE = "An Application of {REDUCE} to Industrial Mechanics", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1981, VOLUME = 15, NUMBER = 2, PAGES = "8-12", MONTH = "May"} + +@InProceedings{Borst:94, + author = "W. N. Borst and V. V. Goldman and J. A. van Hulzen", + title = {{GENTRAN} 90: a {REDUCE} package for the generation of + {Fortran} 90 code}, + booktitle = {Symbolic and Algebraic Computation}, + editor = {}, + series = {ISSAC}, + year = {1994}, + organization = {SIGSAM}, + publisher = {ACM}, + pages = {45--51}, + ABSTRACT = {GENTRAN is a code GENerator and TRANslator running under REDUCE +and MACSYMA. It is a tool for generating Fortran 77, RATFOR or C programs +from program specifications and symbolic expressions. Its facilities +include template processing, automatic segmentation of large expressions +and a file handling mechanism. GENTRAN can be used in combination with +SCOPE 1.5, a Source Code Optimization PackagE for REDUCE. We present an +extension of the REDUCE version of GENTRAN, called GENTRAN 90. It makes +generation of Fortran 90 code possible.}} + +@INPROCEEDINGS{Bowyer:87, + AUTHOR = "A. Bowyer and J. H. Davenport and P. S. Milne and J. A. Padget +and A. F. Wallis", + TITLE = "Applications of Computer Algebra in Solid Modelling", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "244-245", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Boyd:78, + AUTHOR = "John P. Boyd", + TITLE = "The Effects of Latitudinal Shear on Equatorial +Waves, Part {I}: Theory and Methods", + INSTITUTION = "Dept. of Atmos. and Oceanic Science, Univ. +of Michigan", + YEAR = 1978, TYPE = "Preprint", MONTH = "January", + COMMENT = {To be published in Journal of The Atmospheric Sciences. +By using the method of multiple scales in height and a +variety of methods in latitude, analytic solutions for +equatorial waves in combined vertical and horizontal shear +are derived.}} + +@ARTICLE{Boyd:93, + AUTHOR = "John P. Boyd", + TITLE = "Chebyshev and {Legendre} Spectral Methods in Algebraic Manipulation +Languages", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, MONTH = "October", VOLUME = 16, NUMBER = 4, PAGES = "377-399", + COMMENT = {In this tutorial, we show how to combine Galerkin and collocation +methods with algebraic manipulation languages. Because polynomial and +trigonometric manipulations are a special strength of {REDUCE}, Maple, and +other symbolic languages, it is easy to use Chebyshev and Legendre +polynomials and Fourier series as the basis sets. However, because the +truncation is small and calculations are performed symbolically in rational +arithmetic, many of the standard precepets for numerical use of spectral +methods must be modified or reversed. We offer many guidelines and +suggestions. Six examples programmed in {REDUCE}, and +Maple---eigenproblems, bifurcations, and nonlinear diffusion--illustrate +the possibilities.}} + +@INPROCEEDINGS{Brackx:87, + AUTHOR = "F. Brackx and H. Serras", + TITLE = "Boundary Value Problems for the {Laplacian} in {Euclidean} Space +Solved by Symbolic Computation", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "208-215", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Brackx:87a, + AUTHOR = "F. Brackx and D. Constales and R. Delanghe and H. Serras", + TITLE = "{Clifford} Algebra with {REDUCE}", + JOURNAL = "Rend. Circ. Mat. Palermo, Ser. II", + YEAR = 1987, VOLUME = 16, PAGES = "11-19"} + +@ARTICLE{Brackx:89, + AUTHOR = "F. Brackx and D. Constales and A. Ronveaux and H. Serras", + TITLE = "On the Harmonic and Monogenic Decomposition of Polynomials", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 8, NUMBER = 3, PAGES = "297-304", MONTH = "September"} + +@BOOK{Brackx:92, + AUTHOR = "F. Brackx and D. Constales", + TITLE = "Computer Algebra with LISP and REDUCE", + PUBLISHER = "Kluwer Academic Publishers", + YEAR = 1992, + PREFACE = {This text is based upon a series of lectures on LISP and REDUCE + held at the Universities of Averio and Coimbra (Portugal), as part of the + European Community's ERASMUS Project, and at the University of Gent + (Belgium). It has been adapted to the newest release of REDUCE, version + 3.4}} + +@INPROCEEDINGS{Bradford:86, + AUTHOR = "R. J. Bradford and A. C. Hearn and J. A. Padget +and E. Schr{\"u}fer", + TITLE = "Enlarging the {REDUCE} Domain of Computation", + BOOKTITLE = "Proc. of {SYMSAC} '86", + YEAR = 1986, PAGES = "100-106"} + +@INPROCEEDINGS{Bradford:88, + AUTHOR = "R. J. Bradford and J. H. Davenport", + TITLE = "Effective Tests for Cyclotomic Polynomials", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "244-251"} + +@InProceedings{Bradford90, + author = "Russell Bradford", + title = "A parallelization of the {Buchberger} Algorithm", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "296", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Broadhurst:83, + AUTHOR = "D. J. Broadhurst", + TITLE = "{Non-relativistic sum rules for $\mbox{QCD}_2$, {QED} and +$\mbox{QCD}_4$}", + JOURNAL = "Phys. Lett. B", + YEAR = 1983, VOLUME = 123, PAGES = "251-254"} + +@ARTICLE{Broadhurst:84, + AUTHOR = "D. J. Broadhurst and S. C. Generalis", + TITLE = "Can mass singularities be minimally subtracted?", + JOURNAL = "Phys. Lett. B", + YEAR = 1984, VOLUME = 142, PAGES = "75-79"} + +@ARTICLE{Broadhurst:85, + AUTHOR = "D. J. Broadhurst and S. C. Generalis", + TITLE = "Dimension-8 contributions to light-quark {QCD} sum rules", + JOURNAL = "Phys. Lett. B", + YEAR = 1985, VOLUME = 165, PAGES = "175-180"} + +@ARTICLE{Broadhurst:85a, + AUTHOR = "D. J. Broadhurst", + TITLE = "Evaluation of a Class of {Feynman} Diagrams for all Numbers of +Loops and Dimensions", + JOURNAL = "Phys. Lett. B", + YEAR = 1985, VOLUME = 164, PAGES = "356-360", + COMMENT = {Uses {REDUCE} to calculate explicitly the l-loop member of a +class of massless, dimensionally regularized {Feynman} diagrams, in order to +verify an explicit formula.}} + +@ARTICLE{Broadhurst:86, + AUTHOR = "D. J. Broadhurst and A. G. Grozin", + TITLE = "Exploiting the 1,440-fold symmetry of the master two-loop diagram", + JOURNAL = "Zeitschrift {f\"{u}r} Physik c", + YEAR = 1986, VOLUME = 32, PAGES = "249-253"} + +@ARTICLE{Broadhurst:87, + AUTHOR = "D. J. Broadhurst", + TITLE = "Two-loop negative-dimensional integration", + JOURNAL = "Phys. Lett. B", + YEAR = 1987, VOLUME = 197, PAGES = "179-182"} + +@ARTICLE{Broadhurst:90, + AUTHOR = "D. J. Broadhurst", + TITLE = "The master two-loop diagram with masses", + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1990, VOLUME = 47, PAGES = "115-124"} + +@ARTICLE{Broadhurst:91, + AUTHOR = {D. J. Broadhurst and A. G. Grozin}, + TITLE = {Two-loop renormalization of the effective field theory +of a static quark}, + JOURNAL = {Phys. Lett. B}, + YEAR = 1991, VOLUME = 267, PAGES = {105-110}} + +@TECHREPORT{Broadhurst:91a, + AUTHOR = {D. J. Broadhurst and A. G. Grozin}, + TITLE = {Operator product expansion in static-quark effective theory: +large perturbative corrections}, + INSTITUTION = {Open University, Milton Keynes MK7 6AA, England}, + YEAR = 1991, NUMBER = {OUT-4102-31}} + +@ARTICLE{Broadhurst:91b, + AUTHOR = "D. J. Broadhurst and N. Gray and K. Schilcher", + TITLE = {Gauge-invariant on-shell ${Z}_2$ in {QED}, {QCD} and the effective +field theory of a static quark}, + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1991, VOLUME = 52, PAGES = "111-122"} + +@ARTICLE{Broadhurst:92, + AUTHOR = {D. J. Broadhurst and A. G. Grozin}, + TITLE = "Operator product expansion in static-quark effective field theory: +Large perturbative correction", + JOURNAL = {Phys. Lett. B}, + YEAR = 1992, VOLUME = 274, PAGES = {421- }} + +@ARTICLE{Broadhurst:92a, + AUTHOR = {D. J. Broadhurst}, + TITLE = {Three-loop on-shell charge renormalization without integration: +$\Lambda^{\overline{\rm MS}}_{\rm QED}$ to four loops}, + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1992, VOLUME = 54, PAGES = {599- }} + +@ARTICLE{Broadhurst:93, + AUTHOR = "D. J. Broadhurst", + TITLE = "Large {N} expansion of {QED}: asymptotic photon propagator and +contributions to the muon anomaly, for any number of loops", + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1993, VOLUME = 58, PAGES = {339-345}} + +@ARTICLE{Broadhurst:93a, + AUTHOR = "D. J. Broadhurst and J. Fleischer and O. V. Tarasov", + TITLE = "Two-loop two-point functions with masses: asymptotic expansions +and {Taylor} series, in any dimension", + JOURNAL = "Physics Letters", VOLUME = "B329", PAGES = {103-110}, YEAR = 1994, + ABSTRACT = {In all mass cases needed for quark and gluon self-energies, +the two-loop master diagram is expanded at large and small $q^{2}$, in +$d$ dimensions, using identities derived from integration by parts. +Expansions are given, in terms of hypergeometric series, for all gluon +diagrams and for all but one of the quark diagrams; expansions of the +latter are obtained from differential equations. Pad\'{e} approximants +to truncations of the expansions are shown to be of great utility. As an +application, we obtain the two-loop photon self-energy, for all $d$, and +achieve highly accelerated convergence of its expansions in powers of +$q^{2}/m^{2}/q^{2}$, for $d=4$.}} + +@TECHREPORT{Broadhurst:94, + AUTHOR = {D. J. Broadhurst and P. A. Baikov and J. Fleischer and V. A. +Smirnov}, + TITLE = {Two-loop gluon-condensate contributions to heavy-quark +current correlators: exact results and approximations}, + INSTITUTION = {Open University, Milton Keynes MK7 6AA, England}, + YEAR = 1994, NUMBER = {OUT-4102-49}, + ABSTRACT = {The coefficient functions of the gluon condensate $\langle +G^2\rangle$, in the correlators of heavy-quark vector, axial, scalar and +pseudoscalar currents, are obtained analytically, to two loops, for all values +of $z=q^2/4m^2$. In the limiting cases $z\to0$, $z\to1$, and $z\to-\infty$, +comparisons are made with previous partial results. Approximation methods, +based on these limiting cases, are critically assessed, with a view to +three-loop work. High accuracy is achieved using a few moments as input. +A {\em single\/} moment, combined with only the {\em leading\/} threshold and +asymptotic behaviours, gives the two-loop corrections to better than 1\% in +the next 10 moments. A two-loop fit to vector data yields +$\langle\frac{\alpha_{\rm s}}{\pi}G^2\rangle\approx0.021$~GeV$^4$}} + +@ARTICLE{Brodsky:62, + AUTHOR = "S. J. Brodsky and A. C. Hearn and R. G. Parsons", + TITLE = "Determination of the Real Part of the {Compton} Amplitude +at a Nucleon Resonance", + JOURNAL = "Phys. Rev.", + YEAR = 1962, VOLUME = 187, PAGES = "1899-1904"} + +@ARTICLE{Brodsky:67, + AUTHOR = "S. J. Brodsky and J. D. Sullivan", + TITLE = "W-Boson Contribution to the Anomalous Magnetic Moment of the +Muon", + JOURNAL = "Phys. Rev.", + YEAR = 1967, VOLUME = 156, PAGES = "1644-1647"} + +@INPROCEEDINGS{Brodsky:69, + AUTHOR = "S. J. Brodsky", + TITLE = "Status of Quantum Electrodynamics", + YEAR = 1969, + BOOKTITLE = "Proc. International Symposium on +Electron and Photon Interactions at High Energies, Liverpool, +England"} + +@TECHREPORT{Brodsky:70, + AUTHOR = "S. J. Brodsky", + TITLE = "Quantum Electrodynamic Theory: Its Relation to Precision Low +Energy Experiments", + INSTITUTION = "SLAC", + YEAR = 1970, TYPE = "Report", NUMBER = "SLAC-PUB-795", + MONTH = "August"} + +@INPROCEEDINGS{Brodsky:71, + AUTHOR = "S. J. Brodsky", + TITLE = "Algebraic Computation Techniques in Quantum Electrodynamics", + YEAR = 1971, VOLUME = "II", PAGES = "IV-1 to IV-27", + BOOKTITLE = "Proc. {2nd} Computing Methods in Theoretical Physics, +Marseilles"} + +@TECHREPORT{Brodsky:72, + AUTHOR = "S. J. Brodsky", + TITLE = "Atomic Physics and Quantum Electrodynamics in the Infinite +Momentum Frame", + INSTITUTION = "SLAC", YEAR = 1972, + TYPE = "Report", + NUMBER = "SLAC-PUB-1118", MONTH = "August", + COMMENT = {Presented at the Third International Conference on Atomic +Physics.}} + +@ARTICLE{Brodsky:72a, + AUTHOR = "S. J. Brodsky and J. F. Gunion and R. L. Jaffe", + TITLE = "Test for Fractionally Charged Partons from +Deep-Inelastic Bremsstrahlung in the Scaling Region", + JOURNAL = "Phys. Rev. D", + YEAR = 1972, VOLUME = 6, PAGES = "2487-2494"} + +@ARTICLE{Brodsky:72b, + AUTHOR = "S. J. Brodsky and R. Roskies", + TITLE = "Quantum Electrodynamics and Renormalization Theory +in The Infinite Momentum Frame", + JOURNAL = "Phys. Lett.", + YEAR = 1972, VOLUME = "41B", PAGES = "517-520"} + +@ARTICLE{Brodsky:73, + AUTHOR = "S. J. Brodsky and R. Roskies and R. Suaya", + TITLE = "Quantum Electrodynamics and Renormalization Theory in the +Infinite-Momentum Frame", + JOURNAL = "Phys. Rev. D", + YEAR = 1973, VOLUME = 8, PAGES = "4574-4594"} + +@ARTICLE{Broughan:82, + AUTHOR = "K. A. Broughan", + TITLE = "{Grad-Fokker-Planck} Plasma Equations. Part 1. {Collision} +Moments", + JOURNAL = "J. Plasma Phys.", + YEAR = 1982, VOLUME = 27, PAGES = "437-452", + COMMENT = {{REDUCE} used in collaboration with hand calculation. {REDUCE} +did the substitutions, with hand integrations. "Thirteen moments are taken +of the collision term in Boltzmann-Fokker-Planck +equation{\ldots}plasma{\ldots}"}} + +@ARTICLE{Broughan:91, + AUTHOR = "K. A. Broughan and G. Keady and T. D. Robb and M. G. Richardson +and M. C. Dewar", + TITLE = "Some Symbolic Computing Links to the {NAG} Numeric Library", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1991, VOLUME = 25, NUMBER = 3, PAGES = "28-37", MONTH = "July"} + +@ARTICLE{Brown:79, + AUTHOR = "W. S. Brown and A. C. Hearn", + TITLE = "Applications of Symbolic Algebraic Computation", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1979, VOLUME = 17, PAGES = "207-215", + COMMENT = {This paper is a survey of applications of systems for symbolic +algebraic computation.}} + +@ARTICLE{Bryan-Jones:87, + AUTHOR = "Jane Bryan-Jones", + TITLE = "A Tutorial in Computer Algebra for Statisticians", + JOURNAL = "The Professional Statistician", + YEAR = 1987, VOLUME = 6, NUMBER = 6, MONTH = "December",PAGES = "TBD"} + +@TECHREPORT{Burnel, + AUTHOR = "A. Burnel and H. Caprasse", + TITLE = "Locality in Class III Noncovariant Gauges", + INSTITUTION = "Physique Th{\'e}orique et Math{\'e}matique, +Universit{\'e} de Li{\`e}ge", + ABSTRACT = {It is shown within a perturbative calculation of the gluon +self-energy that, in the framework of a general formulation of linear gauges, +axial gauges do not exhibit nonlocal counterterms.}} + +@TECHREPORT{Burnel:94, + AUTHOR = "A. Burnel and H. Caprasse and A. Dresse", + TITLE = "Computing the {BRST} operator", + INSTITUTION = "D{\'e}partement d'Astronomie et d'Astrophysique, +Universit{\'e} de Li{\`e}ge", YEAR = 1994, + ABSTRACT = {It is shown that for a large class of non-holonomic quantum +mechanical systems one can make the computation of {BRST} charge fully +algorithmic. Two computer algebra programs written in the language of +{REDUCE} are described. They are able to realize the complex calculations +needed to determine the charge for general nonlinear algebras. Some +interesting specific solutions are discussed.}} + +@ARTICLE{Burnel:94a, + AUTHOR = "A. Burnel and H. Caprasse", + TITLE = "Computing the {BRST} Operator Used in Quantization of Gauge +Theories", + JOURNAL = "International Journal of Modern Physics C", + YEAR = 1994, VOLUME = 5, NUMBER = 6, PAGES = "1035-1047", + COMMENTS = {It is shown that for a large class of non-holonomic quantum +mechanical systems one can make the computation of BRST charge fully +algorithmic. Two computer algebra programs written in the language of REDUCE +are described. They are able to realize the complex calculations needed +to determine the charge for general nonlinear algebras. Some interesting +specific solutions are discussed.}} + +@TECHREPORT{Calmet:72, + AUTHOR = "Jacques Calmet", + TITLE = "Further Evaluation of the Sixth Order Corrections to the +Anomalous Magnetic Moment of the Electron", + INSTITUTION = "Department of Physics, University of Utah", + YEAR = 1972, + ABSTRACT = {We report on the contributions to the $\alpha^{3}$ +part of the anomalous magnetic moment of the electron from the +seven so-called cross and ladder diagrams.}} + +@ARTICLE{Calmet:72a, + AUTHOR = "Jacques Calmet", + TITLE = "A {REDUCE} Approach to the Calculation of {Feynman} Diagrams", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1972, VOLUME = 4, PAGES = "199-204", + ABSTRACT = {A brief survey of two existing {REDUCE} programs (by +Campbell-Hearn and by Calmet) dealing with algebraic computation of +{Feynman} diagrams is given. Work in progress on a more general approach +to this problem is discussed.}} + +@ARTICLE{Calmet:74, + AUTHOR = "Jacques Calmet", + TITLE = "Computer Recognition of Divergences in {Feynman} Graphs", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1974, VOLUME = 8, NUMBER = 3, PAGES = "74-75", MONTH = "August", + ABSTRACT = {A description of a program for the recognition of divergences +in {Feynman} graphs is given.}} + +@INCOLLECTION{Calmet:83, + AUTHOR = "J. Calmet and J. A. van Hulzen", + TITLE = "Computer Algebra Applications", + EDITOR = "B. Buchberger and G. E. Collins and R. Loos and R. Albrecht", + BOOKTITLE = "Computer Algebra Symbolic and Algebraic Computation", + EDITION = "2nd", PUBLISHER = "Springer-Verlag", YEAR = 1983} + +@ARTICLE{Campbell:67, + AUTHOR = "J. A. Campbell", + TITLE = "Algebraic Computation of Radiative Corrections for +Electron-Positron Scattering", + JOURNAL = "Nucl. Phys.", + YEAR = 1967, VOLUME = "B1", PAGES = "283-300"} + +@ARTICLE{Campbell:68, + AUTHOR = "J. A. Campbell", + TITLE = "Astrophysical Consequences of the Existence of Charged +Intermediate Vector Bosons", + JOURNAL = "Aust. Journ. of Phys.", + YEAR = 1968, VOLUME = 21, PAGES = "139-148"} + +@ARTICLE{Campbell:70, + AUTHOR = "J. A. Campbell and A. C. Hearn", + TITLE = "Symbolic Analysis of {Feynman} Diagrams by Computer", + JOURNAL = "Journ. of Comp. Phys.", + YEAR = 1970, VOLUME = 5, PAGES = "280-327"} + +@ARTICLE{Campbell:70a, + AUTHOR = "J. A. Campbell and R. B. Clark and D. Horn", + TITLE = "Low-T Theorems for Charged-Pion Photoproduction", + JOURNAL = "Phys. Rev. D", + YEAR = 1970, VOLUME = 2, PAGES = "217-224"} + +@ARTICLE{Campbell:74, + AUTHOR = "J. A. Campbell", + TITLE = "Symbolic Computing and Its Relationship to Particle Physics", + JOURNAL = "Acta Physica Austriaca", + YEAR = 1974, VOLUME = "Suppl. XIII", PAGES = "595-647"} + +@ARTICLE{Campbell:87, + AUTHOR = "J. A. Campbell and P. O. Fr{\"o}man and E. Walles", + TITLE = "Explicit series formulae for the evaluation of integrals by the +method of steepest descents", + JOURNAL = "Studies in Applied Mathematics", + YEAR = 1987, VOLUME = 77, PAGES = "151-172"} + +@TECHREPORT{Caprasse:84, + AUTHOR = "H. Caprasse", + TITLE = "Description et Utilisation d'Une Extension du Programme {REDUCE}", + INSTITUTION = "Physique Th{\'e}orique et Math{\'e}matique, +Universit{\'e} de Li{\`e}ge", YEAR = 1984, MONTH = "October"} + +@ARTICLE{Caprasse:85, + AUTHOR = "H. Caprasse and M. Hans", + TITLE = "A New Use of Operators in the Algebraic Mode of {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "46-52", MONTH = "August"} + +@ARTICLE{Caprasse:86, + AUTHOR = "H. Caprasse", + TITLE = "Description of an Extension of the Matrix Package of {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1986, VOLUME = 20, NUMBER = 4, PAGES = "7-10", MONTH = "December"} + +@ARTICLE{Caprasse:86a, + AUTHOR = "H. Caprasse", + TITLE = "A Complete Simplification Package for the Absolute Value +Function in {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "18-21", + MONTH = "February and May", + COMMENT = {Implementation for {REDUCE} 3.2 of the function {"ABS"}.}} + +@INPROCEEDINGS{Caprasse:88, + AUTHOR = "H. Caprasse and J. Demaret and E. Schruefer", + TITLE = "Can {EXCALC} be Used to Investigate {High-dimensional} +Cosmological Models with {Non-Linear Lagrangians}?", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, PAGES = "116-124"} + +@ARTICLE{Caprasse:89a, + AUTHOR = "H. Caprasse", + TITLE = "Les Th{\'e}ories des {Champs} dans le monde de {REDUCE} +(in {French})", + JOURNAL = "{CALSYF} (to appear)", + YEAR = 1989} + +@ARTICLE{Caprasse:90, + AUTHOR = "H. Caprasse", + TITLE = "Renormalization Group, Function Iterations and Computer +Algebra", + JOURNAL = "J. Symbolic Computation", + YEAR = 1990, VOLUME = 9, NUMBER = 1, PAGES = "61-72", MONTH = "January", + COMMENT = {Based on a renormalization group equation met in Quantum Field +Theory, Continuous Iterations of a large class of functions are computed +using {REDUCE}.}} + +@ARTICLE{Caprasse:91, + AUTHOR = "H. Caprasse and J. Demaret and K. Gatermann and H. Melenk", + TITLE = "Power-law type solutions of fourth-order gravity for +multidimensional {Bianchi I} Universes", + JOURNAL = "International Journal of Modern Physics C", + YEAR = 1991, VOLUME = 2, NUMBER = 2, PAGES = "601-611", + COMMENT = {This paper is devoted to the application of computer algebra to +the study of solutions of the field equations derived from a non-linear +Lagrangian, as suggested by recently proposed unified theories. More +precisely, we restrict ourselves to the most general quadratic Lagrangian, +i.e. containing quadratic contributions in the different curvature tensors +exclusively. The corresponding field equations are then fourth-order in the +metric tensor components. The cosmological models studied are the simplest +ones in the class of spatially homogeneous but anisotropic models, +i.e. Bianchi I models. For these models, we consider only power-law +type solutions of the field equations. All the solutions of the associated +system of algebraic equations are found, using computer algebra, from a +search of its Groebner bases. While, in space dimension d=3, the +Einsteinian-Kasner metric is still the most general power-law type solution, +for d>3, no solution, other than the Minkowski space-time, is common to the +three systems of equations corresponding to the three contributions to the +Lagrangian density. In the case of a pure Riemann-squared contribution to the +Lagrangian (suggested by a recent calculation of the effective action for +the heterotic string), the possibility exists to realize a splitting of the +d-dimensional space into a (d-3)-dimensional internal space and a physical +3-dimensional space, the latter expanding in time as a power bigger than +2 (about 4.5 when d=9).}} + +@ARTICLE{Carlson:80, + AUTHOR = "P. Carlson", + TITLE = "Coordinate Free Relativity", + JOURNAL = "J. Math. Phys.", + YEAR = 1980, VOLUME = 21, PAGES = "1149-1154", + COMMENT = {{REDUCE} programs for tetrad formulation of GR.}} + +@PHDTHESIS{Carroll:73, + AUTHOR = "R. Carroll", + TITLE = "The Anomalous Magnetic Moment of the Electron in the +Mass Operator Formalism", + SCHOOL = "University of Michigan", + YEAR = 1973} + +@ARTICLE{Carroll:75, + AUTHOR = "R. Carroll", + TITLE = "Mass-Operator Calculation of the Electron g-Factor", + JOURNAL = "Phys. Rev. D", + YEAR = 1975, VOLUME = 8, PAGES = "2344-2354"} + +@TECHREPORT{Cejchan, + AUTHOR = "A. Cejchan and J. Nadrchal", + TITLE = "Application of {REDUCE}-2 and Analytic Integration +Program in the Theoretical Solid State Physics", + INSTITUTION = "Institute of Physics, CSAV, Prague"} + +@INPROCEEDINGS{Chaffy:88, + AUTHOR = "C. Chaffy-Camus", + TITLE = "An Application of {REDUCE} to the Approximation of $f(x,y)$", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "73-84"} + +@ARTICLE{Chinnick:86, + AUTHOR = "K. Chinnick and C. Gibson and J. F. Griffiths and W. Kordylewski", + TITLE = "Isothermal Interpretations of Oscillatory Ignition During +Hydrogen Oxidation in an Open System. {I}. {Analytical} Predictions and +Experimental Measurements of Periodicity", + JOURNAL = "Proc. Royal Soc. Lond.", + YEAR = 1986, VOLUME = "A405", PAGES = "117-128", + COMMENT = {Used {REDUCE} to solve Jacobian, but answer too complicated to +be of any use.}} + +@ARTICLE{Cline:90, + AUTHOR = "Terry Cline and Harold Abelson and Warren Harris", + TITLE = "Symbolic Computing in Engineering Design", + JOURNAL = "AI EDAM", YEAR = 1990, MONTH = "February"} + +@TECHREPORT{Cohen:76, + AUTHOR = "H. I. Cohen and O. Leringe and Y. Sundblad", + TITLE = "The Use of Algebraic Computing in General Relativity", + INSTITUTION = "The Royal Institute of Technology Department of Mechanics", + YEAR = 1976, NUMBER = "TRITA-MEK-76-02"} + +@TECHREPORT{Cohen:76a, + AUTHOR = "I. Cohen and F. Bark", + TITLE = "Perturbation Calculations for the Spin Up Problem Using {REDUCE}", + INSTITUTION = "The Royal Institute of Technology, Department +of Mechanics", + YEAR = 1976, NUMBER = "TRITA-MEK-76-03"} + +@TECHREPORT{Cohen:77, + AUTHOR = "I. Cohen and S. Yu. Slavyanov", + TITLE = "Smooth Perturbations of the {Schr{\"o}dinger} Equation with a +Linear Potential Related to the Charmonium Models", + INSTITUTION = "University of Stockholm Institute of Physics", + YEAR = 1977, TYPE = "USIP Report", NUMBER = "77-17"} + +@ARTICLE{Cohen:79, + AUTHOR = "J. P. Fitch and H. I. Cohen", + TITLE = "Using {CAMAL} for Algebraic Calculations in General Relativity", + JOURNAL = "General Relativity and Gravitation", VOLUME = 11, YEAR = 1979, + PAGES = "411-418"} + +@ARTICLE{Cohen:84, + AUTHOR = "H. I. Cohen and I. B. Frick and J. E. {\AA}man", + TITLE = "Algebraic Computing in General Relativity", + JOURNAL = "General Relativity and Gravitation, ed.", + YEAR = 1984, PAGES = "139-162", + COMMENT = {General relativity review.}} + +@INPROCEEDINGS{Cohen:89, + AUTHOR = "Joel S. Cohen", + TITLE = "The Effective Use of Computer Algebra Systems", + YEAR = 1989, PAGES = "677-698", + BOOKTITLE = "Transactions of the Sixth Army Conference on Applied +Mathematics and Computing", + COMMENT = {Review of author's experience with four computer algebra +systems.}} + +@ARTICLE{Connor:84, + AUTHOR = "J. N. L. Connor and P. R. Curtis and D. Farrelly", + TITLE = "The Uniform Asymptotic Swallowtail Approximation: Practical +Methods for Oscillating Integrals with Four Coalescing Saddle Points", + JOURNAL = "J. Phys. A", + YEAR = 1984, VOLUME = 17, PAGES = "283-310", + COMMENT = {Used {REDUCE} and {SCHOONSCHIP} for some algebraic +manipulations, and then checked the results with {MACSYMA}; this is the most +distrustful reference we have found.}} + +@ARTICLE{Connor:84a, + AUTHOR = "J. N. L. Connor and P. R. Curtis and C. J. Edge and A. Lagan{`a}", + TITLE = "The Uniform Asymptotic Swallowtail Approximation: Application +to the Collinear $H+F_{2}$", + JOURNAL = "J. Chem. Phys.", YEAR = 1984, VOLUME = 80, NUMBER = 3, + PAGES = "1362-1363", MONTH = "February"} + +@ARTICLE{Conwell:84, + AUTHOR = "P. R. Conwell and P. W. Barber and C. K. Rushworth", + TITLE = "Resonant Spectra of Dielectric Sphere", + JOURNAL = "J. Opt. Soc. Am. A", + YEAR = 1984, VOLUME = 1, PAGES = "62-67", + COMMENT = {{REDUCE} used to confirm independently convergence and accuracy +of {Numerical Bessel} function routine, expanding series by {REDUCE} and +using bigfloats. Described as slow but worthwhile.}} + +@INPROCEEDINGS{Cowan:79, + AUTHOR = "Richard M. Cowan and Martin L. Griss", + TITLE = "Hashing -- The Key to Rapid Pattern Matching", + BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes +in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "266-278", + PUBLISHER = "Springer-Verlag"} + +@BOOK{Cox:92, + AUTHOR = "D. Cox and J. Little and D. O'Shea", + TITLE = "deals, Varieties and Algorithms: + An Introduction of Computational Algebraic Geometry + and Commutative Algebra", + PUBLISHER = "Springer-Verlag", + YEAR = 1992, + COMMENTS = {The appendix contains a discussion of the Groebner basis + package for REDUCE}, + ABSTRACT = {This book is an introduction to algebraic geometry and +commutative algebra aimed primarily at undergraduates. It emphasizes +applications and the computational and algorithmic aspects of the +subject. Less abstract than other texts, and with prerequisites +(a course in linear algebra and any course discussing how to do +simple proofs), the text is also ideal for computer scientists as +well as mathematicians interested in the subject. The exposition +assumes that students have access to a computer algebra system such +as Maple, REDUCE or Mathematica, but assumes no prior experience +with a computer. + +Table of Contents: Geometry, Algebra and Algorithms; Groebner Bases; +Elimination Theory; The Algebra-Geometry Dictionary; Polynomial and +Rational Functions on a Variety; Robotics and Automatic Geometric +Theorem Proving; Invariant Theory of Finite Groups; Projective +Algebraic Geometry; The Dimension of a Variety; Appendices on Some +Concepts From Algebra, Pseudocode, Computer Algebra Systems, and +Independent Projects.}} + +@ARTICLE{Cung:75, + AUTHOR = "V. K. Cung", + TITLE = "Differential Cross Section of e+ + e- to e+ + $\mu-$ + +$\bar{\nu}_\mu$ + $\bar{\nu}_e$", + JOURNAL = "Phys. Lett.", + YEAR = 1975, VOLUME = "55B", PAGES = "67-70"} + +@TECHREPORT{Darbaidze:86, + AUTHOR = "Ya. Z. Darbaidze", + TITLE = "A Gluon Bremsstrahlung in Supersymmetry {QCD}", + INSTITUTION = "JINR", YEAR = 1986, TYPE = "Preprint", + NUMBER = "P2-86-825"} + +@ARTICLE{Darbaidze:86a, + AUTHOR = "J. Z. Darbaidze and V. A. Matveev and +Z. V. Merebashvili and L. A. Slepchenko", + TITLE = "Gluon Bremsstrahlung in Supersymmetric {QCD}", + JOURNAL = "Phys. Lett.", + YEAR = 1986, VOLUME = "B177", PAGE = "188"} + +@TECHREPORT{Darbaidze:88, + AUTHOR = "Ya. Z. Darbaidze and Z.V. Merebashvili and V.A. Rostovtsev", + TITLE = "Some Computer Realizations of the {REDUCE-3} Calculations for +Exclusive Processes", + INSTITUTION = "JINR", YEAR = 1988, TYPE = "Preprint", + NUMBER = "P2-88-769"} + +@TECHREPORT{Darbaidze:89, + AUTHOR = "Ya. Z. Darbaidze and V.A. Rostovtsev", + TITLE = "Analysis of the Differential Equations for the Exclusive Processes +and Explanation for the {``Mystery''} of the {Gamma-Distribution}", + INSTITUTION = "JINR", YEAR = 1989, TYPE = "Preprint", + NUMBER = "E2-89-286"} + +@INPROCEEDINGS{Dautcourt:79, + AUTHOR = "G. Dautcourt", + TITLE = "Application of {REDUCE} to Algebraic Computations in General +Relativity and Astrophysics", + YEAR = 1979, MONTH = "September", + BOOKTITLE = "Proc. of the Workshop in Symbolic Computation, Dubna, +{U.S.S.R.}", + COMMENT = {Reports the use of the system {REDUCE} 2 for general relativistic +calculations.}} + +@TECHREPORT{Dautcourt:80, + AUTHOR = "G. Dautcourt and K. P. Jann", + TITLE = "A Program Package in {REDUCE} 2 for Algebraic Computations in +General Relativity", + YEAR = 1980, + INSTITUTION = "Zentralinstitut fuer Astrophysik der +Akademie der Wissenschaften"} + +@ARTICLE{Dautcourt:81, + AUTHOR = "G. Dautcourt and K. P. Jann and E. Riemer and M. Riemer", + TITLE = "User's Guide to {REDUCE} Subroutines For Algebraic +Computations in General Relativity", + JOURNAL = "Astron. Nachr.", + YEAR = 1981, VOLUME = 302, PAGES = "1-13"} + +@ARTICLE{Dautcourt:83, + AUTHOR = "G. Dautcourt", + TITLE = "The Cosmological Problem as an Initial Value Problem on the +Observer's Past Light Cone: Geometry", + JOURNAL = "J. Phys. A", + YEAR = 1983, VOLUME = 16, PAGES = "3507-3528", + COMMENT = {Checked calculations with {REDUCE}, mainly {Riemann} tensor in +null coordinates.}} + +@ARTICLE{Davenport:81, + AUTHOR = "James Harold Davenport", + TITLE = "On the Integration of Algebraic Functions", + JOURNAL = "Lecture Notes in Computer Science", + PUBLISHER = "Springer-Verlag", + YEAR = 1981, VOLUME = 102, PAGES = "1-197"} + +@ARTICLE{Davenport:82, + AUTHOR = "James H. Davenport", + TITLE = "Fast {REDUCE:} The {trade-off} between efficiency and +generality", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 1, PAGES = "8-11", MONTH = "February"} + +@ARTICLE{Davenport:82a, + AUTHOR = "James H. Davenport", + TITLE = "What do we want from a {high-level} language?", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "6-9", MONTH = "November"} + +@INPROCEEDINGS{Davenport:85, + AUTHOR = "James Davenport and Julian Padget", + TITLE = "{HEUGCD:} How Elementary Upperbounds Generate Cheaper Data", + BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes +in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "18-28", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Davenport:88, + AUTHOR = "J. H. Davenport", + TITLE = "The World of Computer Algebra", + JOURNAL = "New Scientist", + YEAR = 1988, MONTH = "September", VOLUME = 1629, PAGES = "71-72"} + +@BOOK{Davenport:88a, + AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", + TITLE = "Computer Algebra, Systems and Algorithms for Algebraic Computation", + PUBLISHER = "Academic Press", EDITION = "2nd", YEAR = 1993} + +@BOOK{Davenport:88b, + AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", + TITLE = "Calcul Formel (in French)", + PUBLISHER = "Masson", EDITION = "2nd", YEAR = 1993} + +@BOOK{Davenport:88c, + AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", + TITLE = "Kompyuter Algebra (in Russian)", + PUBLISHER = "MIR", EDITION = "1st", YEAR = 1991} + +@TECHREPORT{Della-Dora:81, + AUTHOR = "J. Della Dora and E. Tournier", + TITLE = "Solutions Formelles D'Equations Differentielles au Voisinage de +Points Singuliers Reguliers", + INSTITUTION = "Centre National de la Recherche Scientifique", + YEAR = 1981, TYPE = "Report", NUMBER = 239} + +@INPROCEEDINGS{Della-Dora:84, + AUTHOR = "J. Della Dora and E. Tournier", + TITLE = "Homogeneous Linear Difference Equation {(Frobenius-Boole Method)}", + BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes +in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "2-12", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Della-Dora:85, + AUTHOR = "Jean Della-Dora and Claire Dicrescenzo and Dominique Duval", + TITLE = "About a New Method for Computing in Algebraic Number Fields", + INSTITUTION = "Universit{\'e} de Grenoble, Institut Fourier, +France", YEAR = 1985, MONTH = "November"} + +@ARTICLE{Demaret:89, + AUTHOR = "J. Demaret and H. Caprasse and A. Moussiaux and Ph. Tombal and +D. Papadopoulos", + TITLE = "{Ten-dimensional Lovelock-type Space-Times}", + JOURNAL = "{To appear} Phys. Rev. D", + YEAR = 1989, MONTH = "July"} + +@ARTICLE{DeMenna:87, + AUTHOR = "L. De Menna and G. Miano and G. Rubinacci", + TITLE = "Volterra's Series Solutions of Free Boundary Plasma Equilibria", + JOURNAL = "Phys. Fluids", + YEAR = 1987, VOLUME = 30, PAGES = "409-416", + COMMENT = {Magnetohydrodynamics. "We have carried out the computations up +to the fourth order, (the fourth order has been obtained by means of the +symbolic program {REDUCE}").}} + +@ARTICLE{Demichev:85, + AUTHOR = "A. P. Demichev and A. Ya. Rodionov", + TITLE = "A {REDUCE} Program for the Calculation of Geometrical +Characteristics of Compactified Multidimensional {Riemannian} Space", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1985, VOLUME = 38, PAGES = "441-448", + COMMENT = {Covariant theories in N dimensional ($N \geq 4$) space-time. +{REDUCE} programs to calculate {Ricci, Einstein and Yang-Mills} curvature +and energy-momentum tensor.}} + +@TECHREPORT{Demichev:86, + AUTHOR = "A. P. Demichev and A. Ya. Rodionov", + TITLE = "Freund-{Rubin} Type Solutions for Different Compactifications of +the Eleven-Dimensional Space", + INSTITUTION = "Institute for High Energy Physics", YEAR = 1986, + TYPE = "Preprint", NUMBER = "86-85", + ABSTRACT = {The results of calculating geometrical characteristics of +seven-dimensional quotient spaces are represented. These +quantities are necessary for the construction of compactifying +solutions of the eleven-dimensional supergravity.}} + +@ARTICLE{deRop:88, + AUTHOR = "Y. de Rop and J. Demaret", + TITLE = "Using {EXCALC} to Study Nondiagonal Multidimensional +Spatially Homogeneous Cosmologies", + JOURNAL = "Gen. Rel. Grav.", + YEAR = 1988, VOLUME = 20, PAGES = "1127-1139"} + +@TECHREPORT{DeVos:89, + AUTHOR = "Alexis De Vos", + TITLE = "The use of {Reduce} in solar energy conversion theory", + INSTITUTION = "State University of Gent, {CAGe} Computer Algebra +Group", YEAR = 1989, TYPE = "Reports of the {CAGe} Project", +NUMBER = 4, MONTH = "August"} + +@TECHREPORT{DeVos:93, + AUTHOR = "Alexis De Vos", + TITLE = "Carnot engines, {Gr{\"o}bner} bases and all the winds on the Earth", + INSTITUTION = "University of Gent, {CAGe} Computer Algebra Group", + YEAR = 1993, TYPE = "The {CAGe} Reports", NUMBER = 9, MONTH = "March", + ABSTRACT = {In the present paper, we determine which part of the solar +energy incident on a planet can be converted into mechanical work. The +planet is assumed to be spherical and not rotating around an axis. From +numerical calculations, we find that at the most 9.64% of the absorbed +solar energy can be converted into work. But can we find an analytical +expression for this fundamental number? We try this challenge with the +REDUCE procedures for manipulation of polynomials.}} + +@INPROCEEDINGS{Dewar:89, + AUTHOR = "M. C. Dewar", + TITLE = "{IRENA --} An Integrated Symbolic and Numerical Computation +Environment", + BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", + YEAR = 1989, PAGES = "171-179"} + +@ARTICLE{Dhar:85, + AUTHOR = "D. Dhar and J-M. Maillard", + TITLE = "Susceptibility of the Checkerboard {Ising} Model", + JOURNAL = "J. Phys. A", + YEAR = 1985, VOLUME = 18, PAGES = "L383-L388", + COMMENT = {Used {REDUCE} for tedious algebra, and got a simple answer. +statistical mechanics(?). "At the disorder variety, the n-point correlation +functions of the checkerboard Potts model has a simple causal +structure. An exact expression for the susceptibility in the Ising +case is obtained."}} + +@TECHREPORT{Dicrescenzo:85, + AUTHOR = "Claire Dicrescenzo", + TITLE = "Algebraic Computation on Algebraic Numbers", + INSTITUTION = "Institut Fourier, Laboratoire de +Math{\'e}matiques, France", YEAR = 1985, MONTH = "December", + COMMENT = {Examples are given of a new method, implemented on {REDUCE}, +for computing algebraically on algebraic numbers.}} + +@TECHREPORT{Diver, + AUTHOR = "D. A. Diver and E. Q. Laing and C. C. Sellar", + TITLE = "Waves in a Cold Plasma with a Spatially Rotating Magnetic Field", + YEAR = 1988, + INSTITUTION = "Department of Physics and Astronomy, University of +Glasgow, Plasma Physics Group", TYPE = "Report", NUMBER = "GU TPA 88/12-1", + COMMENT = {"{\ldots}The algebraic manipulation system {REDUCE} was used in +constructing the following tensor definitions which allows us to make fewer +approximations than other authors."}} + +@INPROCEEDINGS{Diver:86, + AUTHOR = "D. A. Diver and E. W. Laing", + TITLE = "Proc. 8th {Europhysics} Conference on +Computational Physics", + YEAR = 1986, + BOOKTITLE = "Computing in Plasma Physics"} + +@INPROCEEDINGS{Diver:88, + AUTHOR = "D. A. Diver and E. W. Laing", + BOOKTITLE = "Proc. {XV} {European} Conference on Controlled +Fusion and Plasma Heating", + YEAR = 1988} + +@TECHREPORT{Diver:88a, + AUTHOR = "D. A. Diver and E. W. Laing", + TITLE = "Alfven Resonance Absorption in a Magnetofluid", + YEAR = 1988, TYPE = "Report", + INSTITUTION = "Department of Physics and Astronomy, University of +Glasgow, Plasma Physics Group", + NUMBER = "GUTPA 88/04-01", MONTH = "July", + COMMENT = {Presented at 15th {UK} Plasma Physics Conference, {UMIST}.}} + +@ARTICLE{Diver:91, + AUTHOR = "D. A. Diver", + TITLE = "Modelling Waves with Computer Algebra", + JOURNAL = "J. Symbolic Computation", + YEAR = 1991, VOLUME = 11, NUMBER = 3, PAGES = "275-289", MONTH = "March", + ABSTRACT = {A sophisticated model for linear waves in an inhomogeneous +plasma is tackled completely using the computer algebra system {REDUCE}. +The algebra code mirrors the mathematics, and is structured in a simple +and straightforward manner. In so doing, the solution technique is made +obvious, and the overall philosophy of the approach is intuitive to the +{non-specialist} computer algebra user.}} + +@TECHREPORT{Dorfi:85, + AUTHOR = "E. A. Dorfi and L. O'C. Drury", + TITLE = "Simple Adaptive Grids for {1D} Initial Value Problems", + INSTITUTION = "Max-Plack-Institut fuer Kernphysik, Heidelberg, +West Germany", YEAR = 1985, + NUMBER = "MPI H-1985-V21"} + +@ARTICLE{Dorizzi:86, + AUTHOR = "B. Dorizzi and B. Grammaticos and J. Hietarinta and A. Ramani +and F. Schwarz", + TITLE = "New integrable three dimensional quartic potentials", + JOURNAL = "Phys. Lett.", + YEAR = 1986, VOLUME = "116A", PAGES = "432-436", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@TECHREPORT{dosSantos:85, + AUTHOR = "R. P. dos Santos and P. P. Srivastava", + TITLE = "Two-loop Effective Potential for {Wess-Zumino} Model using +Superfields", + INSTITUTION = "International Centre for Theoretical Physics", + YEAR = 1985, NUMBER = "IC/85/205", MONTH = "October", + ABSTRACT = {For the case of several interacting chiral superfields the +propagators for the unconstrained superfield potentials in the 'shifted' +theory, where the supersymmetry is explicitly broken, are derived in a +compact form. They are used to compute one-loop effective potential in +the general case, while a superfield calculation of renormalized effective +potential to two loops for the Wess-Zumino model is performed.}} + +@ARTICLE{dosSantos:87, + AUTHOR = "Renato P. dos Santos", + TITLE = "Using {REDUCE} in Supersymmetry", + JOURNAL = "J. Symb. Comp.", + YEAR = 1989, VOLUME = 7, PAGES = "523-525"} + +@PHDTHESIS{dosSantos:87a, + AUTHOR = "R. P. dos Santos", + TITLE = "O M{\'e}todo de Supercampos para o C{\'a}lculo de Potencial +Efetivo em Modelos com Supercampos Quirais: Os Modelos de Wess e +Zumino e de O'Raifeartaigh", + SCHOOL = "Centro Brasileiro de Pesquisas F{\'i}sicas", + YEAR = 1987, + COMMENT = {{(In Portuguese)} Using the method of {Superfields}, the +effective potential for supersymmetric models of {Wess-Zumino} and of +{O'Raifeartaigh} is evaluated up to two-loop order. The spontaneous +supersymmetry breaking is discussed. {REDUCE} plays very important +role in evaluation of the {Feynman} superdiagrams and in +renormalization.}} + +@TECHREPORT{dosSantos:88a, + AUTHOR = "Renato P. dos Santos", + TITLE = "Introdu\c{c}\~{a}o ao Sistema {REDUCE} de C\'{a}lculo +Alg\'{e}brico", + INSTITUTION = "CBPF, Rio de Janeiro, Brazil", + YEAR = 1988, NUMBER = "CBPF-NT-001/88", + COMMENT = {{(In Portuguese)} Lecture notes of a course on {REDUCE}.}} + +@ARTICLE{dosSantos:90, + AUTHOR = "R. P. dos Santos and W. L. Roque", + TITLE = "On the Design of an Expert Help System for Computer Algebra +Systems", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1990, VOLUME = 24, NUMBER = 4, PAGES = "22-25", MONTH = "October"} + +@InProceedings{Dresse:93, + author = "A. Dresse", + title = "Treatment of Dummy Variables and {BRST} Theory in Computer + Algebra", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "110-119", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + comment = {A canonical form algorithm for quantities with locally scoped + variables (e.g. Summation convention, tensor products) is + developed in a {REDUCE} package.} +} + +@ARTICLE{Drska:90, + AUTHOR = "Ladislav Drska and Richard Liska and Milan Sinor", + TITLE = "Two practical packages for computational physics{-GCPM, RLFI}", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1990, VOLUME = 61, NUMBER = "1-2", MONTH = "November", + PAGES = "225-230", + ABSTRACT = {Two handy computer-program packages for technical support of +the work in two different branches of the computational physics are reported: +(1) A general package for the symbolic and numerical transformation of +expressions from one system of units to another. (2) A package allowing +high-quality two-dimensional output of mathematical formulas from the +computer-algebra system {REDUCE}.}} + +@ARTICLE{Dubowsky:75, + AUTHOR = "S. Dubowsky and J. L. Grant", + TITLE = "Application of Symbolic Manipulation to Time +Domain Analysis of Nonlinear Dynamic Systems", + JOURNAL = "Journ. of Dynamic Systems, Measurement, and Control", + YEAR = 1975, VOLUME = "75-Aut-J"} + +@ARTICLE{Dudley:89, + AUTHOR = "M. L. Dudley and R. W. James", + TITLE = "{Computer-aided} Derivation of Spherical Harmonic Spectral Equations +in Astrogeophyics", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 8, NUMBER = 4, PAGES = "423-427", MONTH = "October"} + +@ARTICLE{Dufner:69, + AUTHOR = "A. M. Dufner and Y. S. Tsai", + TITLE = "Phenomenological Analysis of the $\gamma$NN* Form Factors", + JOURNAL = "Phys. Rev.", + YEAR = 1969, VOLUME = 168, PAGES = "1801-1809"} + +@INPROCEEDINGS{Dulyan:87, + AUTHOR = "L. S. Dulyan", + TITLE = "The Calculation of {QCD} Triangular {Feynman} Graphs in the +External Gluonic Field Using {REDUCE}-2 System", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "172-173", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Duncan:86, + AUTHOR = "Anthony Duncan and Ralph Roskies", + TITLE = "Representations of Unusual Mathematical Structures in Scientific +Applications of Symbolic Computation", + JOURNAL = "J. Symbolic Computation", + YEAR = 1986, VOLUME = 2, NUMBER = 2, PAGES = "201-206", MONTH = "June", + ABSTRACT = {We present examples of techniques we have used to apply {REDUCE} +to problems in particle physics which have mathematical structures unknown to +{REDUCE}.}} + +@PHDTHESIS{Duval:87, + AUTHOR = "Dominique Duval", + TITLE = "Diverses questions relatives au Calcul Formel +Avec des Nombres Alg{\'e}briques", + SCHOOL = "L'Universit{\'e} Scientifique, Technologique +et M{\'e}dicale de Grenoble", YEAR = 1987} + +@InProceedings{Dyer:94, + author = {Charles C. Dyer}, + title = {An Application of Symbolic Computation in the + Physical Sciences}, + booktitle = {Symbolic and Algebraic Computation}, + editor = {}, + series = {ISSAC}, + year = {1994}, + organization = {SIGSAM}, + publisher = {ACM}, + pages = {181--186} +} + +@ARTICLE{Earles:70, + AUTHOR = "D. Earles", + TITLE = "A Measurement of the Electron-Production of Muon Pairs", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1970, VOLUME = 25, PAGES = "129-133"} + +@ARTICLE{Eastwood:87, + AUTHOR = "James W. Eastwood", + TITLE = "Orthovec: A {REDUCE} Program for {3-D} Vector Analysis +in Orthogonal Curvilinear Coordinates", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1987, VOLUME = 47, NUMBER = 1, PAGES = "139-147", MONTH = "October"} + +@TECHREPORT{Eastwood:87a, + AUTHOR = "James W. Eastwood and Christopher J. H. Watson", + TITLE = "An Analytic Theory of {Wave-Current} Interactions", + INSTITUTION = "Culham Laboratory, Theory and Optics Division", + YEAR = 1987, NUMBER = "Plasma Physics Note 87/7", MONTH = "February", + ABSTRACT = {This report presents results of the Department of Energy +contract to obtain high order analytic solutions to nonlinear hydrodynamic +equation describing steady periodic waves propagating in sheared currents. +The purpose of this work is to provide working formulae for computing +combined wave and current loadings in the design of offshore structures. +Using the {REDUCE} algebra package, we have identified minor typographical +errors in the published fifth coefficients for uniform currents given by +{Fenton [2]} and by Skjelbreia and {Hendrickson [5]}. We have demonstrated +the equivalence of corrected forms of these expressions to fifth order, and +extended Fenton's expansion to seventh order. We present a new fifth order +theory for bilinear current profiles. {FORTRAN} software for the seven order +uniform current and fifth order bilinear current theories are given.}} + +@ARTICLE{Eastwood:91, + AUTHOR = "James W. Eastwood", + TITLE = "{ORTHOVEC:} version 2 of the {REDUCE} program for {3-D} vector +analysis in orthogonal curvilinear coordinates", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1991, VOLUME = 64, NUMBER = 1, PAGES = "121-122", MONTH = "April"} + +@TECHREPORT{Edelen:81, + AUTHOR = "Dominic G. B. Edelen", + TITLE = "Programs for Calculation of Isovector Fields in the +{REDUCE}-2 Environment", + INSTITUTION = "Center for the Application of Mathematics, +Lehigh University", YEAR = 1981, NUMBER = "TBD", MONTH = "August"} + +@ARTICLE{Edelen:82, + AUTHOR = "D. G. B. Edelen", + TITLE = "Isovector Fields for Problems in the Mechanics of Solids and +Fluids", + JOURNAL = "Int. Journ. Eng. Sci.", + YEAR = 1982, VOLUME = 20, PAGES = "803-815", + COMMENT = {Prolongation methods as a {REDUCE} package for this, available +from Center for Applications of Mathematics, Lehigh Univ., Bethlehem, PA +18015. Applications to mechanics of solids and fluids.}} + +@BOOK{Edneral:89, + AUTHOR = "Viktor F. Edneral and Aleksandr P. Kryukov and +Anatolii Ia. Rodionov", + TITLE = "The language of the analytic computer program {REDUCE}", + PUBLISHER = "Moscow, {Izd-vo}, Moskovskogo {un-ta}", YEAR = 1989, + COMMENT = {This monograph -- first in The Soviet Union with a systematic +treatment of the analytical computer (program) {REDUCE}.}} + +@ARTICLE{Eisenberger:90, + AUTHOR = "Moshe Eisenberger", + TITLE = "Application of Symbolic Algebra to the Analysis of Plates +on Variable Elastic Foundation", + JOURNAL = "J. Symbolic Computation", + YEAR = 1990, VOLUME = 9, NUMBER = 2, PAGES = "207-213", MONTH = "February"} + +@TECHREPORT{Eissfeller:86, + AUTHOR = "Bernd Ei{\ss}feller and G{\"u}nter W. Hein", + TITLE = "A Contribution to {3D-Operational} Geodesy", + INSTITUTION = "Universit{\"a}rer Studiengang Vermessungswesen +and Universit{\"a}t der Bundeswehr M{\"u}nchen", + YEAR = 1986, NUMBER = "Heft 17", MONTH = "December"} + +@PHDTHESIS{Eitelbach:73, + AUTHOR = "D. L. Eitelbach", + TITLE = "Automatic Analysis of Problems in Elementary Mechanics", + SCHOOL = "University of Illinois", + YEAR = 1973} + +@ARTICLE{Eleuterio:82, + AUTHOR = "S. M. Eleut{\'e}rio and R. V. Mendes", + TITLE = "Note on Equivalence and Singularities: An Application of +Computer Algebra", + JOURNAL = "Journ. Comp. Phys.", + YEAR = 1982, VOLUME = 48, PAGES = "150-156", + COMMENT = {{GR} equivalence, commenting on \AAman & Karlhede.}} + +@ARTICLE{Eliseev:85, + AUTHOR = "V. P. Eliseev and R. N. Fedorova and V. V. Kornyak", + TITLE = "A {REDUCE} Program for Determining Point and Contact {Lie} +Symmetries of Differential Equations", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1985, VOLUME = 36, PAGES = "383-389", + ABSTRACT = {A universal {REDUCE} program for obtaining the systems of +determining equations of the Lie algebra of point and contact +symmetries is proposed.}} + +@ARTICLE{Elishakoff:87, + AUTHOR = "Isaac Elishakoff and Joseph Hollkamp", + TITLE = "Computerized Symbolic Solution for a Nonconservative +System in Which Instability Occurs by Flutter in One Range +of a Parameter and by Divergence in Another", + JOURNAL = "Comp. Methods in Applied Mechanics and Engineering", + YEAR = 1987, VOLUME = 62, PAGES = "27-46", + COMMENT = {"{\ldots}the problem is solved by the {Galerkin} method in +conjunction with computerized symbolic algebra". The system used is {REDUCE}. +"It carries out algebraic operations irrespective of their complexity". +Includes snatches of code and algebraic answers. Mainly +differentiation and substitution, plus a little integration. The +coefficients get rather large (18 digits or so).}} + +@ARTICLE{Elishakoff:87a, + AUTHOR = "Isaac Elishakoff and Brian Couch", + TITLE = "Application of Symbolic Algebra to the Instability of a +Nonconservative System", + JOURNAL = "J. Symbolic Computation", + YEAR = 1987, VOLUME = 4, NUMBER = 3, PAGES = "391-396", MONTH = "December"} + +@ARTICLE{Esteban:90, + AUTHOR = "E.P. Esteban and E. Ramos", + TITLE = "Algebraic computing and the {Newman-Penrose} formalism", + JOURNAL = "Computers in Physics", + YEAR = 1990, PAGES = "285-290", MONTH = "May/June"} + +% REDUCE BIBLIOGRAPHY + +% Part 2: F-H + +% Copyright (c) 1995 RAND. All Rights Reserved. + +% Additions and corrections are solicited. Please send them, in the +% same format as these entries if possible, to reduce at rand.org. + + +@ARTICLE{Falck:89, + AUTHOR = "N. K. Falck and D. Graudenz and G. Kramer", + TITLE = "Cross section for {five-parton} production in $e^{+} e^{-}$ +annihilation", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1989, VOLUME = 56, PAGES = "181-198", NUMBER = 2, MONTH = "December"} + +@ARTICLE{Fazio:84, + AUTHOR = "P. M. Fazio and G. E. Copeland", + TITLE = "Cooper-Type Minima in Multipole Cross Sections of Atomic Hydrogen", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1984, VOLUME = 53, NUMBER = "2", MONTH = "July"} + +@INPROCEEDINGS{Fedorova:87, + AUTHOR = "R. N. Fedorova and V. P. Gerdt and N. N. Govorun +and V. P. Shirikov", + TITLE = "Computer Algebra in Physical Research of {Joint Institute} +for {Nuclear Research}", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "1-10", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Fedorova:87a, + AUTHOR = "R. N. Fedorova and V. V. Kornyak", + TITLE = "Computer Algebra Application for Determining Local Symmetries +of Differential Equations", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "174-175", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Feldmar:86, + AUTHOR = "E. Feldmar and K. S. K{\"o}lbig", + TITLE = "{REDUCE} Procedures for the Manipulation of Generalized +Power Series", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1986, VOLUME = 39, PAGES = "267-284"} + +@ARTICLE{Feuillebois:84, + AUTHOR = "F. Feuillebois", + TITLE = "Sedimentation in a Dispersion with Vertical Inhomogenieties", + JOURNAL = "Journ. Fluid Mech.", + YEAR = 1984, VOLUME = 139, PAGES = "145-171", + COMMENT = {Uses {REDUCE} and {INT} to evaluate some integrals in the +expansion of 1/s, a small quantity.}} + +@ARTICLE{Fitch:73, + AUTHOR = "John Fitch", + TITLE = "Problems \#3 and \#4 in {REDUCE} and {MACSYMA}", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1973, PAGES = "10-11", + ABSTRACT = {The algebra systems {REDUCE} and {MACSYMA} are used to solve +{SIGSAM} Problem \#3, the Reversion of a Double Series, and {SIGSAM} +Problem \#4, the Lie Transform Solution of the Harmonic Oscillator.}} + +@INPROCEEDINGS{Fitch:81, + AUTHOR = "J. P. Fitch", + TITLE = "User-based Integration Software", + BOOKTITLE = "Proc. 1981 {ACM} Symposium on Symbolic +and Algebraic Computation", + YEAR = 1981, PAGES = "245-248"} + +@INPROCEEDINGS{Fitch:83, + AUTHOR = "J. P. Fitch", + TITLE = "Implementing {REDUCE} on a Microprocessor", + BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes +in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "128-136", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Fitch:85, + AUTHOR = "J. P. Fitch", + TITLE = "Solving Algebraic Problems with {REDUCE}", + JOURNAL = "J. of Symbolic Computation", + YEAR = 1985, VOLUME = 1, NUMBER = 2, PAGES = "211-227", MONTH = "June"} + +@INPROCEEDINGS{Fitch:85a, + AUTHOR = "J. P. Fitch", + TITLE = "Applying Computer Algebra", + BOOKTITLE = "International Conference on Computer Algebra and its +Application in Theory", + YEAR = 1985, PAGES = "262-275"} + +@INPROCEEDINGS{Fitch:87, + AUTHOR = "J. P. Fitch", + TITLE = "Utilisation du Calcul Formel", + BOOKTITLE = "Calcul Formel et Automatique", + EDITOR = "P. Chenin", PUBLISHER = "Editions du {CNRS}", + YEAR = 1987, PAGES = "119-136"} + +@INPROCEEDINGS{Fitch:87a, + AUTHOR = "J. P. Fitch and R. G. Hall", + TITLE = "Symbolic Computation and the Finite Element Method", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "95-96", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Fitch:89, + AUTHOR = "J. P. Fitch", + TITLE = "Can {REDUCE} be run in parallel?", + BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", + YEAR = 1989, PAGES = "155-162"} + +@ARTICLE{Fitch:89a, + AUTHOR = "J. Fitch", + TITLE = "Compiling for Parallelism", + JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora +and J. Fitch", + YEAR = 1989, PAGES = "19-31", PUBLISHER = "Academic Press, London"} + +@InProceedings{Fitch90, + author = "J. P. Fitch", + title = "A delivery system for {REDUCE}", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "76-81", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Fitch:90a, + AUTHOR = "John Fitch", + TITLE = "The symbolic-numeric interface", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1990, VOLUME = 61, NUMBER = "1-2", MONTH = "November", + PAGES = "22-33", + ABSTRACT = {Algebraic computation can be of great assistance in the +preparation of numerical programs. The paper considers some of these, +from simple to complex, and describes work currently in progress to produce +a true integrated symbolic-numeric computing system.}} + +@ARTICLE{Fitch:93, + AUTHOR = "John Fitch", + TITLE = "Mathematics goes automatic", + JOURNAL = "Physics world", + YEAR = 1993, VOLUME = 6, NUMBER = 6, MONTH = "June", PAGES = "48-52", + COMMENT = {Computer algebra enhances the productivity of any scientist or +engineer by increasing efficiency and doing away with tedious operations}} + +@TECHREPORT{Flatau:86, + AUTHOR = "Piotr J. Flatau and John P. Boyd and William R. Cotton", + TITLE = "Symbolic Algebra in Applied Mathematics and Geophysical +Fluid Dynamics - {REDUCE} Examples", + INSTITUTION = "Dept. of Atmospheric and Oceanic Science, University +of Michigan, and Dept. of Atmospheric Science, Colorado State +University", YEAR = 1986} + +@TECHREPORT{Flath:86, + AUTHOR = "Dan Flath", + TITLE = "Remarks on Tensor Operators", + INSTITUTION = "National University of Singapore, Department +of Mathematics", TYPE = "Research Report", + YEAR = 1986, NUMBER = 266, MONTH = "July"} + +@ARTICLE{Fleischer:71, + AUTHOR = "J. Fleischer", + TITLE = "Partial Wave Analysis of Nucleon-Nucleon {Bethe}-{Salpeter} +Equation on the Computer", + JOURNAL = "Journ. of Comp. Phys.", + YEAR = 1971, VOLUME = 12, PAGES = "112-123"} + +@ARTICLE{Fleischer:73, + AUTHOR = "J. Fleischer and J. L. Gammel and M. T. Menzel", + TITLE = "Matrix {Pad\'e} Approximants for the {1SO}- and +{3PO}- Partial Waves in Nucleon-Nucleon Scattering", + JOURNAL = "Phys. Rev. D", + YEAR = 1973, VOLUME = 8, PAGES = "1545-1552"} + +@ARTICLE{Fleischer:75, + AUTHOR = "J. Fleischer and J. A. Tjon", + TITLE = "Bethe-{Salpeter} Equation for {J}=0 Nucleon-Nucleon +Scattering with One-Boson Exchange", + JOURNAL = "Nuclear Physics", + YEAR = 1975, VOLUME = "B84", PAGES = "375-396"} + +@ARTICLE{Fogelholm:82, + AUTHOR = "Rabbe Fogelholm and Inge B. Frick", + TITLE = "Standard {LISP} for the {VAX:} A Provisional Implementation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "10-12", MONTH = "November"} + +@ARTICLE{Foster:89, + AUTHOR = "Kenneth R. Foster and Haim H. Bau", + TITLE = "Symbolic Manipulation Programs for the Personal Computer", + JOURNAL = "Science", + YEAR = 1989, VOLUME = 243, PAGES = "679-243", MONTH = "February", + COMMENT = {Reviews several algebra programs that run on small machines. +doesn't rate the {PC} version of {REDUCE} very highly because of the small +workspace.}} + +@ARTICLE{Fox:71, + AUTHOR = "J. A. Fox", + TITLE = "Recalculation of the Crossed Graph Contribution +to the 4th Order {Lamb} Shift", + JOURNAL = "Phys. Rev. D", + YEAR = 1971, VOLUME = 3, PAGES = "3228-3230"} + +@ARTICLE{Fox:74, + AUTHOR = "John A. Fox and Anthony C. Hearn", + TITLE = "Analytic Computation of Some Integrals in Fourth Order +Quantum Electrodynamics", + JOURNAL = "Journ. Comp. Phys.", + YEAR = 1974, VOLUME = 14, PAGES = "301-317", + ABSTRACT = {A program for the analytic evaluation of some parametric +integrals which occur in fourth order {QED} calculations is described.}} + +@ARTICLE{Franceschetti:85, + AUTHOR = "G. Franceschetti and I. Pinto", + TITLE = "Nonlinear Propagation and Scattering: Analytical Solution and +Symbolic Code Implementation", + JOURNAL = "J. Opt. Soc. Am. A", + YEAR = 1985, VOLUME = 2, PAGES = "997-1006", + COMMENT = {Volterra series using {REDUCE}. Perturbation expansions.}} + +@INPROCEEDINGS{Freire:88, + AUTHOR = "E. Freire and E. Gamero and E. Ponce and L. G. Franquelo", + TITLE = "An Algorithm for Symbolic Computation of Center Manifolds", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "218-230"} + +@INPROCEEDINGS{Freire:89, + AUTHOR = "E. Freire and E. Gamero and E. Ponce", + TITLE = "An Algorithm for Symbolic Computation of {Hopf} Bifurcation", + BOOKTITLE = "Proc. Computers and Mathematics '89", + EDITOR = "E. Kaltofen and S. M. Watt", + YEAR = 1989, PAGES = "109-118", PUBLISHER = "Springer-Verlag, New York"} + +@TECHREPORT{Frick:82, + AUTHOR = "I. G. Frick and R. Fogelholm", + TITLE = "An Implementation of {Standard} {Lisp} Built on Top of {Franz Lisp}", + INSTITUTION = "University of Stockholm, Institute of +Physics", YEAR = 1982, TYPE = "Report", MONTH = "April", + COMMENT = {A Standard {LISP} system has been built for the {VAX-11} +large-address-space computer by embedding the required function +definitions in the available Franz Lisp system for {VAX/UNIX}.}} + +@ARTICLE{Fujimoto:84, + AUTHOR = "Y. Fujimoto and T. Garavaglia", + TITLE = "Phase Diagrams in {Scalar QED}", + JOURNAL = "Physics Letters", + YEAR = 1984, VOLUME = "148B", NUMBER = "1,2,3", PAGES = "220-224", + MONTH = "November"} + +@ARTICLE{Fuzio:85, + AUTHOR = "P. M. Fuzio and G. E. Copeland", + TITLE = "Partial Radiative-Recombination Cross Sections for Excited +States of Hydrogen", + JOURNAL = "Phys. Rev. A", + YEAR = 1985, VOLUME = 31, NUMBER = 1, PAGES = "187-195", + ABSTRACT = {The squares of the dipole and quadrupole matrix elements for the +free-to-bond transitions of hydrogen uptp high bound states are +derived in closed analytic form using a method suitable for computer +algebra.}} + +@TECHREPORT{Gaemers, + AUTHOR = "K. J. F. Gaemers and R. Gastmans and F. M. Renard", + TITLE = "Neutrino Counting in e+ e- Collisions", + INSTITUTION = "NIKHEF-H, Amsterdam", TYPE = "Preprint", + ABSTRACT = {The possibility of counting the number of neutrino types +in e+ e- $\rightarrow$ gamma nu nubar is re-examined by taking into +account effects of the Z-pole.}} + +@TECHREPORT{Gaemers:78, + AUTHOR = "K. J. F. Gaemers and G. J. Gounaris", + TITLE = "Polarization Amplitudes For e+e- $\rightarrow$ W+W- +$\rightarrow$ ZZ", + INSTITUTION = "CERN", YEAR = 1978, TYPE = "Preprint", + NUMBER = "TH.2548-CERN", MONTH = "August", + ABSTRACT = {The main purpose of this work is to study the three weak boson +vertex. We give explicit formulae for all polarization amplitudes of +the processes e+e- $\rightarrow$ W+W- and e+e- $\rightarrow$ ZZ, with +arbitrary couplings between the various intermediate vector bosons.}} + +@INPROCEEDINGS{Ganzha:89, + AUTHOR = "V. Ganzha and R. Liska", + TITLE = "Application of the {REDUCE} Computer Algebra System to Stability +Analysis of Difference Schemes", + BOOKTITLE = "Proc. Computers and Mathematics '89", + EDITOR = "E. Kaltofen and S. M. Watt", + YEAR = 1989, PAGES = "119-129", PUBLISHER = "Springer-Verlag, New York"} + +@InProceedings{Ganzha90, + author = "Victor G. Ganzha and Michail Yu. Shaskov", + title = "Local Approximation Study of Difference Operators by + means of {REDUCE} System", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "185-192", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@InProceedings{Ganzha90a, + author = "V. G. Ganzha and S. V. Meleshko and V. P. Shelest", + title = "Application of {REDUCE} System for Analyzing + Consistency of Systems of {P.D.E.'s}", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "301", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@INPROCEEDINGS{Ganzha:91, + AUTHOR = "V.G. Ganzha and B. Yu. Scobelev and E.V. Vorozhtsov", + TITLE = "Stability Analysis of Difference Schemes by the Catastrophe +Theory Methods and by Means of Computer Algebra", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "427-428", + YEAR = 1991} + +@InProceedings{Ganzha:94, + author = "V. G. Ganzha and E. V. Vorozhtsov and J. Boers and + J. A. van Hulzen", + title = {Symbolic-Numeric Stability Investigations of {Jameson's} + Schemes for Thin-layer {Navier-Stokes} Equations}, + booktitle = {Symbolic and Algebraic Computation}, + editor = {}, + series = {ISSAC}, + year = {1994}, + organization = {SIGSAM}, + publisher = {ACM}, + pages = {234--241} +} + +@TECHREPORT{Garavaglia, + AUTHOR = "Theodore Garavaglia", + TITLE = "Polarized Electron Scattering on Spin Zero and Polarized Spin +$\frac{1}{2}$ Targets: Deep Inelastic Scattering, Elastic Electron-muon +Scattering, and Elastic Electron-Nucleon Scattering", + INSTITUTION = "Inst. Teich. Bhaile Atha Cliath, Eire", TYPE = "Preprint", + ABSTRACT = {A covariant formulation is developed and used to derive +cross-sections for the analysis of experiments in which +polarized electrons(muons) are scattered from spin zero and +from polarized spin 1/2 targets.}} + +@ARTICLE{Garavaglia:80, + AUTHOR = "T. Garavaglia", + TITLE = "A Covariant Formulation for Polarized Electron (Muon) +Scattering on Spin-Zero and Polarized Spin-$\frac{1}{2}$ Targets", + JOURNAL = "Il Nuovo Cimento", + YEAR = 1980, VOLUME = "56A", PAGES = "121-128", + COMMENT = {{REDUCE} used in quantum mechanics.}} + +@ARTICLE{Garavaglia:84, + AUTHOR = "Theodore Garavaglia", + TITLE = "{Dirac-} and {Majorana-neutrino-mass} effects in +{neutrino-electron} elastic scattering", + JOURNAL = "Physical Review {D}", + YEAR = 1984, VOLUME = 29, NUMBER = 3, PAGES = "387-392", MONTH = "February"} + +@ARTICLE{Garcia:86, + AUTHOR = "Arnaldo Garcia and Paulo Viana", + TITLE = "Weierstrass Points on Certain Non-Classical Curves", + JOURNAL = "Arch. Math.", + YEAR = 1986, VOLUME = 46, PAGES = "315-322"} + +@ARTICLE{Garrad:86, + AUTHOR = "A. D. Garrad and D. C. Quarton", + TITLE = "Symbolic Computing as a Tool in Wind Turbine Dynamics", + JOURNAL = "Journ. of Sound and Vibration", + YEAR = 1986, VOLUME = 109, NUMBER = 1, PAGES = "65-78", + COMMENT = {{REDUCE} as a tool in turbine design, in particular present a +program for part of a stability analysis for a turbine tower.}} + +@ARTICLE{Gastmans:79, + AUTHOR = "R. Gastmans and A. van Proeyen and P. Verbaeten", + TITLE = "Symbolic Evaluations of Dimensionally Regularized {Feynman} +Diagrams", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1979, VOLUME = 18, PAGES = "201-203", + ABSTRACT = {A modification of the symbolic and algebraic manipulation +program {REDUCE} is reported which allows the treatment of vector and gamma +algebra in an arbitrary number of dimensions.}} + +@TECHREPORT{Gatermann:90, + AUTHOR = "Karin Gatermann", + TITLE = "Gruppentheoretische {Konstruktion} von symmetrischen +{Kubaturformeln}", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1990, TYPE = "Preprint", NUMBER = "TR 90-1", MONTH = "January"} + +@InProceedings{Gatermann90a, + author = "Karin Gatermann", + title = "Symbolic solution of polynomial equation systems with + symmetry", + booktitle = "Proceedings of the 1990 International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "112-119", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Gatermann:91, + AUTHOR = "Karin Gatermann and Andreas Hohmann", + TITLE = "Symbolic Exploitation of Symmetry in Numerical Pathfollowing", + JOURNAL = "IMPACT of Computing in Science and Engineering", + YEAR = 1991, MONTH = "December", VOLUME = 3, NUMBER = 4, + PAGES = "330-365", + ABSTRACT = {{Parameter-dependent} systems of nonlinear equations with +symmetry are treated by a combination of symbolic and numerical computations. +In the symbolic part of the algorithm the complete analysis of the symmetry +occurs, and it is here where symmetrical normal forms, symmetry reduced +systems, and block diagonal Jacobians are computed. Given a particular +problem, the symbolic algorithm can create and compute through the list of +possible bifurcations thereby forming a {so-called} tree of decisions +correlated to the different types of symmetry breaking bifurcation points. +The remaining part of the algorithm deals with the numerical pathfollowing +based on the implicit reparametrisation as suggested and worked out by +{Deuflhard/Fiedler/Kunkel}. The symmetry preserving bifurcation points are +computed using recently developed augmented systems incorporating the use +of symmetry.}} + +@INPROCEEDINGS{Gatermann:91a, + AUTHOR = "Karin Gatermann", + TITLE = "Mixed symbolic-numeric solution of symmetrical nonlinear systems", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + ORGANIZATION = "ACM", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "431-432", + YEAR = 1991, + ABSTRACT = {The mixed symbolic-numeric algorithm {SYMCON} for the fully +automatical treatment of equivariant systems is presented. The global +aspects of the theory of Vanderbauwhede for these systems are viewed with +regard to the full bifurcation scenario containing solution paths with +different isotropy groups and symmetry preserving and symmetry breaking +bifurcation points. The advanced exploitation of symmetry in the numerical +computations causes an comprehensive symmetry analysis and complicated +organization of numerical work which is done by the symbolic part of the +algorithm.}} + +@TECHREPORT{Gatermann:91b, + AUTHOR = "Karin Gatermann and Andreas Hohmann", + TITLE = "Hexagonal Lattice Dome--Illustration of a Nontrivial Bifurcation +Problem", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1991, MONTH = "July", TYPE = "Preprint", NUMBER = "SC-91-8"} + ABSTRACT = {The deformation of a hexagonal lattice dome under an external +load is an example of a parameter dependent system which is equivariant +under the symmetry group of a regular hexagon. In this paper the mixed +symbolic-numerical algorithm SYMCON is applied to analyze its steady state +solutions automatically showing their different symmetry and stability +properties.}} + +@TECHREPORT{Gatermann:92, + AUTHOR = "Karin Gatermann", + TITLE = "Computation of Bifurcation Graphs", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1992, MONTH = "June", TYPE = "Preprint", NUMBER = "SC-92-13"} + ABSTRACT = {The numerical treatment of equivariant parameter-dependent +nonlinear equation systems, and even more its automation requires the +intensive use of group theory. This paper illustrates the group theoretic +computations which are done in the preparation of the numerical computations. +The bifurcation graph which gives the bifurcation subgroups is determined +from the interrelationship of the irreducible representations of a group +and its subgroups. The Jacobian is transformed to block diagonal +structure using a modification of the transformation which transforms to +block diagonal structure with respect to a supergroup. The principle of +conjugacy is used everywhere to make symbolic and numerical computations +even more efficient. Finally, when the symmetry reduced problems and +blocks of Jacobian matrices are evaluated numerically, the fact that the +given representation is a quasi-permutation representation is exploited +automatically.}} + +@TECHREPORT{Gatermann:93, + AUTHOR = "Karin Gatermann and Bodo Werner", + TITLE = "Group Theoretical Mode Interactions with Different Symmetries", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1993, MONTH = "January", TYPE = "Preprint", NUMBER = "SC-93-3"} + ABSTRACT = {In two-parameter systems two symmetry breaking bifurcation +points of different types coalesce generically within one point. This causes +secondary bifurcation points to exit. The aim of this paper is to +understand this phenomenon with group theory and the innerconnectivity of +irreducible representations of supergroup and subgroups. Colored pictures +of examples are included.}} + +@TECHREPORT{Gatermann:93a, + AUTHOR = "Karin Gatermann and Bodo Werner", + TITLE = "Secondary {Hopf} bifurcation caused by steady-state steady-state +mode interaction", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1993, MONTH = "July", TYPE = "Preprint", NUMBER = "SC-93-16", + ABSTRACT = {In two-parameter systems with symmetry two steady state +bifurcation points of different symmetry types coalesce generically within +one point. Under certain group theoretic conditions involving the action +of the symmetry group on the kernels, we show that secondary Hopf +bifurcation is borne by the mode interaction. We explain this phenomenon +by using linear representation theory. For motivation an example with +$D_{3}$-symmetry is investigated where the main properties causing the Hopf +bifurcation are summarized.}} + +@TECHREPORT{Gatermann:94, + AUTHOR = "Karin Gatermann", + TITLE = "Semi-invariants, equivariants and algorithms", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1994, MONTH = "May", TYPE = "Preprint", NUMBER = "SC-94-11", + ABSTRACT = {The results from invariant theory and the results for semi- +invariants and equivariants are summarized in a way suitable for the +combination with G{r\"o}bner basis computation. An algorithm for the +determination of fundamental equivariants using projections and a +Poinca\'{r}e series is described. Secondly, an algorithm is given for the +representation of an equivariant in terms of the fundamental equivariants. +Several ways for the exact determination of zeros of equivariant systems +are discussed.}} + +@TECHREPORT{Gatermann:95, + AUTHOR = "Karin Gatermann and Reiner Lauterbach", + TITLE = "Automatic classification of normal forms", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1995, MONTH = "February", TYPE = "Preprint", NUMBER = "SC-95-3", + ABSTRACT = {The aim of this paper is to demonstrate a specific application +of Computer Algebra to bifurcation theory with symmetry. The +classification of different bifurcation phenomena in case of several +parameters is automated, based on a classification of G{r\"o}bner bases of +possible tangent spaces. The computations are performed in new coordinates +of fundamental invariants and fundamental equivariants, with the induced +weighted ordering. In order to justify the approach the theory of +intrinsic modules is applied. Results for the groups $D_{3},Z_{2}$, and +$Z_{2} x Z_{2}$ demonstrate that the algorithm works independent of the +group and that new results are obtained.}} + +@INPROCEEDINGS{Gates:85, + AUTHOR = "Barbara L. Gates and J. A. van Hulzen", + TITLE = "Automatic Generation of Optimized Programs", + BOOKTITLE = "Proc. {EUROCAL} '85", YEAR = 1985, + MONTH = "April"} + +@ARTICLE{Gates:85a, + AUTHOR = "Barbara L. Gates", + TITLE = "Gentran: An Automatic Code Generation Facility +for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "24-42", MONTH = "August"} + +@TECHREPORT{Gates:85b, + AUTHOR = "Barbara L. Gates", + TITLE = "Gentran User's Manual - {REDUCE} Version", + INSTITUTION = "Twente University of Technology, Department of +Computer Science, The Netherlands", TYPE = "Memorandum", + YEAR = 1985, NUMBER = "INF-85-11", MONTH = "June"} + +@TECHREPORT{Gates:85c, + AUTHOR = "Barbara L. Gates", + TITLE = "Gentran Design and Implementation, {REDUCE} Version", + INSTITUTION = "Twente University of Technology, Department of Computer +Science, The Netherlands", YEAR = 1985, TYPE = "Memorandum", + NUMBER = "INF-85-12", MONTH = "August"} + +@INPROCEEDINGS{Gates:86, + AUTHOR = "Barbara L. Gates", + TITLE = "A Numerical Code Generation Facility for {REDUCE}", + BOOKTITLE = "Proc. {SYMSAC} '86", + YEAR = 1986, PAGES = "94-99", MONTH = "July"} + +@TECHREPORT{Gebauer:85, + AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", + TITLE = "A Fast Variant of {Buchberger's} Algorithm", + INSTITUTION = "Universit{\"a}t Heidelberg and +Fernuniversit{\"a}t {Hagen}", YEAR = 1985, MONTH = "October"} + +@ARTICLE{Gebauer:88, + AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", + TITLE = "On an Installation of {Buchberger's} Algorithm", + JOURNAL = "J. Symbolic Computation", + YEAR = 1988, VOLUME = 6, NUMBER = "2 and 3", PAGES = "275-286"} + +@ARTICLE{Generalis:84, + AUTHOR = "S. C. Generalis and D. J. Broadhurst", + TITLE = "The heavy-quark expansion and {QCD} sum rules for light quarks", + JOURNAL = "Physics Lett. B", + YEAR = 1984, VOLUME = 139, PAGES = "85-89"} + +@ARTICLE{George:68, + AUTHOR = "D. J. George", + TITLE = "A Covariant Theory of the Disintegration of the +Deuteron by Pions and Photons at High Energy", + JOURNAL = "Phys. Rev.", + YEAR = 1968, VOLUME = 167, PAGES = "1357-1364"} + +@ARTICLE{Gerdt:80, + AUTHOR = "V. P. Gerdt", + TITLE = "Analytical Calculations in High Energy Physics by Computer", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1980, VOLUME = 20, PAGES = "85-90", + COMMENT = {A review, comparing {SCHOONSCHIP, ASHMEDAI and REDUCE-2}.}} + +@ARTICLE{Gerdt:80a, + AUTHOR = "V. P. Gerdt and O. V. Tarasov and D. V. Shirkov", + TITLE = "Analytical Calculations on Digital Computers for Applications +in Physics and Mathematics", + JOURNAL = "Sov. Phys. USP", + YEAR = 1980, VOLUME = 23, PAGES = "59-77", + COMMENT = {General review of applications in many languages.}} + +@TECHREPORT{Gerdt:80b, + AUTHOR = "V. P. Gerdt", + TITLE = "On Global Structure of the General Solution of the +{Chew-Low} Equations", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1980, TYPE = "Preprint", NUMBER = "P2-80-436"} + +@ARTICLE{Gerdt:85, + AUTHOR = "V. P. Gerdt and A. B. Shvachka and A. Yu. Zharkov", + TITLE = "Computer Algebra Application for Classification of +Integrable Non-Linear Evolution Equations", + JOURNAL = "J. Symb. Comp.", + YEAR = 1985, VOLUME = 1, PAGES = "101-107"} + +@TECHREPORT{Gerdt:85a, + AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev +and R. P. Roussev", + TITLE = "Calculation of the Matrix Elements of the +{Hamiltonian} of the Interacting Vector Boson Model Using +Computer Algebra - Basic Concepts of the Interacting Vector +Boson Model and Matrix Elements of the {SU(3)-Quadrupole} +Operator", + INSTITUTION = "Institute for Nuclear Research and Nuclear +Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", + YEAR = 1985, NUMBER = "E4-85-262"} + +@TECHREPORT{Gerdt:85b, + AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev", + TITLE = "Calculation of the Matrix Elements of the +{Hamiltonian} of the Interacting Vector Boson Model Using +Computer Algebra - Matrix Elements of the {Hamiltonian} and +Some {U(6)-Clebsch-Gordon} Coefficients", + INSTITUTION = "Institute for Nuclear Research and Nuclear +Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", + YEAR = 1985, NUMBER = "E4-85-263"} + +@TECHREPORT{Gerdt:85c, + AUTHOR = "V. P. Gerdt and N. A. Kostov and P. P. Raychev +and R. P. Roussev", + TITLE = "Calculation of the Matrix Elements of the +{Hamiltonian} of the Interacting Vector Boson Model +Using Computer Algebra - Matrix Elements of the {Hamiltonian} - +Analytical Results", + INSTITUTION = "Institute for Nuclear Research and Nuclear +Energy, Bulgarian Academy of Sciences, Sofia, Bulgaria", + YEAR = 1985, NUMBER = "E4-85-264"} + +@TECHREPORT{Gerdt:86, + AUTHOR = "V. P. Gerdt and M. G. Meshcheryakov and D. V. Shirkov", + TITLE = "Computers in Theoretical Physics", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1986, NUMBER = "P2-86-848", + ABSTRACT = {The paper is written on the basis of the report presented by +two authors ({M.G. Meshcheryakov} and {D.V. Shirkov}) at the 60th session +of the JINR Scientific Council, June 5, 1986. It reviews the usage of +computer mathematics in theoretical and mathematical investigations +carried out in the Joint Institute. Recommendations are given on further +development of the JINR Computer Center in accordance with the program of +theoretical researches in nearest Five-Year Plan.}} + +@INPROCEEDINGS{Gerdt:87, + AUTHOR = "V. P. Gerdt and A. B. Shabat and S. I. Svinolupov +and A. Yu. Zharkov", + TITLE = "Computer Algebra Application for Investigating +Integrability of Nonlinear Evolution Systems", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "81-92", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Gerdt:87a, + AUTHOR = "V. P. Gerdt and N. A. Kostov and Z. T. Kostova", + TITLE = "Computer Algebra and Computation of {Puiseux} Expansions of +Algebraic Functions", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "206-207", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Gerdt:89, + AUTHOR = "V. P. Gerdt and N. A. Kostov", + TITLE = "Computer Algebra in the theory of Ordinary Differential Equations +of Halphen type", + BOOKTITLE = "Proc. Computers and Mathematics '89", + EDITOR = "E. Kaltofen and S. M. Watt", + YEAR = 1989, PAGES = "279-288", PUBLISHER = "Springer-Verlag, New York"} + +@TECHREPORT{Gerdt:89a, + AUTHOR = "V. P. Gerdt and Z. T. Kostova and N. A. Kostov and I. P. Yudin", + TITLE = "Algebraic-Numeric Calculations of Proton Trajectories in Bending +Magnets of Synchrotron Accelerator", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1989, TYPE = "Preprint", NUMBER = "E11-89-755", + ABSTRACT = {We study a solution of nonlinear differential equation of the +second degree which describes the trajectories of the charged particles in +the fully inhomogeneous field of cyclic accelerator. We give the clear +mathematical statement of the problem and algorithm of solving it. We +realize this algorithm on the Computer Algebra System {REDUCE 3.2}. Our +algorithm is based both on the existence of exact solution in terms of +hyperelliptic integral and on the existence of power series solution of +specific inversion problem. We use the known {REDUCE} procedures of +operation on generalized power series. Using the {FORTRAN} code we give the +numerical analysis of these series in the close relation to the concrete +physical situation. We apply our results to the beam dynamics modeling +of the protons in the bending magnets in synchrotron accelerator.}} + +@TECHREPORT{Gerdt:89b, + AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", + TITLE = "Solving the Polynomial System Arising in Classification of +Integrable Coupled {KdV-like} Systems", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1989, TYPE = "Preprint", NUMBER = "P5-89-231", + ABSTRACT = {A system of algebraic equations which follows from the +necessary integrability conditions for the {ten-parametric} family of +coupled {KdV-like} nonlinear evolution systems is considered. The method +for solving this system based on the structure of the canonical local +conservation laws densities is described. Computer algebra system +{REDUCE} was used to find all the solutions. As a result we obtain the +complete list of integrable coupled {KdV-like} systems.}} + +@InProceedings{Gerdt90, + author = "V. P. Gerdt and A. Yu. Zharkov", + title = "Computer Generation of Necessary Integrability + Conditions for Polynomial-Nonlinear Evolution Systems", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "250-254", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@InProceedings{Gerdt90a, + author = "Vladimar P. Gerdt and Nikolai V. Khutornoy and Alexey + Yu. Zharkov", + title = "Solving Algebraic Systems which arise as Necessary + Integrability Conditions for Polynomial-Nonlinear + evolution Equations", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "299", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Gerdt:90b, + AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", + TITLE = "Computer Classification of Integrable Coupled {KdV-Like} Systems", + JOURNAL = "J. Symb. Comp.", + YEAR = 1990, VOLUME = 10, PAGES = "203-207", + ABSTRACT = {The foundations of the symmetry approach to the classification +problem of integrable {non-linear} evolution systems are briefly described. +Within the framework of the symmetry approach the {ten-parametric} family +of the third order {non-linear} evolution coupled {KdV-like} systems is +investigated. The necessary integrability conditions lead to an +{over-determined} {non-linear} algebraic system. To solve that system an +effective method based on its structure has been used. This allows us +to obtain the complete list of integrable systems of a given type. All +computation has been completed on the basis of computer algebra systems +{FORMAC} and {REDUCE}.}} + +@INPROCEEDINGS{Gerdt:90c, + AUTHOR = "V. P. Gerdt and N. A. Kostov and A. Yu. Zharkov", + TITLE = "Nonlinear Evolution Equations and Solving Algebraic Systems: +The Importance of Computer Algebra", + YEAR = 1990, + BOOKTITLE = "International Conference on Solitons and Its Applications", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "120-128"} + ABSTRACT = {In the present paper we study the application of computer +algebra to solve the nonlinear polynomial systems which arise in +investigation of nonlinear evolution equations. We consider several +systems which are obtained in classification of integrable nonlinear +evolution equations with uniform rank. Other polynomial systems are related +with the finding of algebraic curves for finite-gap elliptic potentials of +{Lame} type and generalizations. All systems under consideration are +solved using the method based on construction of the {Groebner} basis for +corresponding polynomial ideals. The computations have been carried out +using computer algebra systems.}} + +@INPROCEEDINGS{Gerdt:91, + AUTHOR = "V. P. Gerdt and A. Yu. Zharkov", + TITLE = "Lie-{B{\"a}cklund} Symmetries of Coupled Nonlinear +{Schr{\"o}dinger} Equations", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "313-314", + YEAR = 1991} + +@TECHREPORT{Gerdt:91a, + AUTHOR = "V. P. Gerdt and P. Tiller", + TITLE = "A {Reduce} Program for Symbolic Computation of {Puiseux} +Expansions", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1991, TYPE = "Preprint", NUMBER = "E5-91-401"} + ABSTRACT = {The program is described for computation of Puiseux expansions +of alebraic functions. The Newton polygon method is used for construction +of initial coefficients of all the Puiseux series at the given point. The +program is written in computer algebra language Reduce. Some illustrative +examples are given.}} + +@TECHREPORT{Gerdt:91b, + AUTHOR = "V. P. Gerdt", + TITLE = "Computer Algebra Tools for Higher Symmetry Analysis of Nonlinear +Evolution Equations", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1991, TYPE = "Preprint", NUMBER = "E5-91-402"} + ABSTRACT = {This paper presents a computer-aided approach and a software +package for symbolic algebraic computation to solve the problem of +verifying the existence of the canonical Lie-B{\"a}cklund symmetries +for multicomponent quasilinear evolution equations with polynomial- +nonlinearity and computing a given order symmetry if any. In the presence +of arbitrary numerical parameters the problem is reduced to investigation +and solving of nonlinear algebraic equations in those parameters. It is +remarkable that in all the known cases these algebraic equations are +completely solvable by the Gr{\"o}bner basis technique implemented as a part +of the software package.}} + +@InProceedings{Gerdt:93, + author = "V. Gerdt", + title = "Homogeneity of Integrability Conditions for Multiparametric + Families of Polynomial-Nonlinear Evolution Equations", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "181-186", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + comment = {A canonical form algorithm for quantities with locally scoped + variables (e.g. Summation convention, tensor products) is + developed in a {REDUCE} package.} +} + +@ARTICLE{Gervois:74, + AUTHOR = "A Gervois and Y. Pomeau", + TITLE = "Logarithmic Divergence in the Virial Expansion +of Transport Coefficients of Hard Spheres", + JOURNAL = "Phys. Rev. A", + YEAR = 1974, VOLUME = 9, PAGES = "2196-2213"} + +@TECHREPORT{Gladd:82, + AUTHOR = "N. T. Gladd", + TITLE = "Computational Aspects of Research on the +Relativistic {Whistler} Instability", + INSTITUTION = "Jaycor", YEAR = 1982, + NUMBER = "J530-82-020", MONTH = "June"} + +@INPROCEEDINGS{Gladkih:83, + AUTHOR = "I. Gladkih and E. Lovas", + TITLE = "On the Application of Computer Algebra Languages in the {Central +Research Institute for Physics}", + BOOKTITLE = "Proceedings of the International Conference on Systems and +Techniques of Analytical Computing and Their Applications in Theoretical +Physics, {D11-83-511, Dubna}", YEAR = 1983} + +@INPROCEEDINGS{Gladkih:84, + AUTHOR = "I. Gladkih and M. Zimanyi", + TITLE = "Comparison of systems for Symbolic Computing in use in the +{Central Research Institute for Physics} (in {Russian})", + BOOKTITLE = "Proceedings of the International Conference on {Computer-Based} +Scientific Research, Plovdiv", YEAR = 1984} + +@ARTICLE{Goldman:89, + AUTHOR = "V. V. Goldman and J. A. van Hulzen", + TITLE = "Automatic Code Vectorization of Arithmetic Expressions by +Bottom-Up Structure Recognition", + JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora +and J. Fitch", + YEAR = 1989, PAGES = "119-132", PUBLISHER = "Academic Press, London"} + +@INPROCEEDINGS{Golley, + AUTHOR = "Bruce W. Golley and Joseph Petrolito", + TITLE = "An Alternative Finite Strip Technique for the Static Analysis of +Single-Span, Multi-Span and Continuous Plates", + YEAR = 1982, + BOOKTITLE = "Proc. International Conference on +Finite Element Methods"} + +@ARTICLE{Good:75, + AUTHOR = "D. Good and R. L. London and W. W. Bledsoe", + TITLE = "An Interactive Program Verification System", + JOURNAL = "Sigplan Notices", + YEAR = 1975, VOLUME = 10, NUMBER = 6, PAGES = "482-492"} + +@ARTICLE{Goto:77, + AUTHOR = "E. Goto and T. Soma", + TITLE = "{MOL} (Moving Objective Lens) Formulation of +Deflective Aberration Free System", + JOURNAL = "Optik", + YEAR = 1977, VOLUME = 48, PAGES = "255-270"} + +@INPROCEEDINGS{Goto:78, + AUTHOR = "E. Goto and T. Soma", + TITLE = "Electron Beam Lithography for Advanced {LSI} Fabrication", + YEAR = 1978, PAGES = "1223-1228", + BOOKTITLE = "Proc. 1978 National Computer Conference, +{AFIPS} Press, New Jersey"} + +@ARTICLE{Gould:84, + AUTHOR = "H. W. Gould and M. E. Mays", + TITLE = "Series Expansions of Means", + JOURNAL = "Journ. of Mathematical Analysis and Applications", + YEAR = 1984, VOLUME = 101, NUMBER = 2, PAGES = "611-621", + MONTH = "July"} + +@ARTICLE{Graebe:93, + AUTHOR = "Hans-Gert Gr{\"a}be", + TITLE = "On Lucky Primes", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, VOLUME = 15, NUMBER = 2, PAGES = "199-209", MONTH = "February", + COMMENT = {Winkler (1988) and Pauer (1992) present algorithms for a Hensel +lifting of a modular Gr{\"o}bner basis over lucky primes to a rational +one. They have to solve a linear system with modular polynomial entries +that requires another (modular) Gr{\"o}ner basis computation. +After an extension of luckiness to arbitrary (commutative noetherian) base +rings we show in this paper that for a homogeneous polynomial ideal I one +lift not only only its Gr{\"o}bner basis but also a homogeneous basis of +its syzygy module. The same result holds for arbitrary ideals and +liftings from Z/p to Q. Moreover the same lifting can be obtained from a +true Gro{\"o}bner trace by linear algebra over Q only. Parallel modular +techniques allow to find such a true Gro{\"o}bner and a lucky prime with +high probability. +All these results generalize in an obvious way to homogeneous modules +generated by the rows of matrices with polynomial entries. Since +luckiness can be weakened to a condition that transfers from I to higher +syzygy modules the lifting theorem generalizes to a lifting theorem for +the resolution of I.}} + +@PHDTHESIS{Gragert:81, + AUTHOR = "Peter Gragert", + TITLE = "Symbolic Computations in Prolongation Theory", + SCHOOL = "Twente University of Technology, The Netherlands", + YEAR = 1981} + +@BOOK{Grammaticos, + AUTHOR = "B. Grammaticos and A. Voros", + TITLE = "Semi-Classical Approximations for Nuclear +{Hamiltonians}: {II}. {Spin-dependent} Potentials", + ABSTRACT = {A systematic semi-classical expansion procedure for physical +quantities in nuclei, based on the Thomas-Fermi approximation +to the Hartree-Fock equations and constructed in a previous +work, is extended here to the realistic case where the +effective one-body {Hamiltonian} for nucleons contains +spin-dependent terms.}} + +@TECHREPORT{Grammaticos:78, + AUTHOR = "B. Grammaticos and A. Voros", + TITLE = "Semi-classical Approximations for Nuclear +{Hamiltonians} {I}. {Spin-independent} Potentials", + INSTITUTION = "CEN, Saclay", YEAR = 1978, TYPE = "Preprint", + NUMBER = "DPh-T/78-75", MONTH = "August", + COMMENT = {Submitted to Annals of Physics}, + ABSTRACT = {A systematic procedure for calculating semi-classical +expansions of physically interesting quantities is presented.}} + +@ARTICLE{Grammaticos:85, + AUTHOR = "B. Grammaticos and B. Dorizzi and A. Ramani and J. Hietarinta", + TITLE = "Extending integrable {Hamiltonian} systems from 2 to {N} +dimensions", + JOURNAL = "Phys. Lett.", + YEAR = 1985, VOLUME = "109A", PAGES = "81-84", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Gray:90, + AUTHOR = "N. Gray and D. J. Broadhurst and W. Grafe and K. Schilcher", + TITLE = {Three-loop relation of quark $\overline{\rm MS}$ and pole masses}, + JOURNAL = "Zeitschrift {f\"{u}r} Physik C", + YEAR = 1990, VOLUME = 48, PAGES = "673-679"}} + +@ARTICLE{Greenland:84, + AUTHOR = "P. T. Greenland", + TITLE = "Comparison Between Phase Diffusion and Random Telegraph Signal +Models of Laser Bandwidth", + JOURNAL = "Journ. Phys. B", + YEAR = 1984, VOLUME = 17, PAGES = "1919-1925", + COMMENT = {{REDUCE} calculation of correlation matrix for molecular physics. +Tedious, but simple result.}} + +@ARTICLE{Grimm, + AUTHOR = "R. Grimm and H. K{\"u}hnelt", + TITLE = "Using {REDUCE} in Problems of Supersymmetry and Supergravity", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1980, VOLUME = 20, PAGES = "77", + COMMENT = {Describes how {REDUCE} may be used with advantage in tedious +calculations of supersymmetry and supergravity.}} + +@INPROCEEDINGS{Griss:74, + AUTHOR = "M. L. Griss", + TITLE = "The Algebraic Solution of Large Sparse Systems of Linear +Equations Using {REDUCE} 2", + YEAR = 1974, PAGES = "105-111", + BOOKTITLE = "Proc. ACM 74", + ABSTRACT = {This paper discusses some of the problems encountered during the +solution of a large system of sparse linear equations with algebraic +coefficients, using {REDUCE} 2.}} + +@ARTICLE{Griss:74a, + AUTHOR = "M. L. Griss", + TITLE = "The Algebraic Solution of Sparse Linear Systems Via Minor +Expansion", + JOURNAL = "ACM TOMS 2", + YEAR = 1976, PAGES = "31-49", + ABSTRACT = {An improved algorithm for computing the determinants of a (large) +sparse matrix of polynomials is described.}} + +@INPROCEEDINGS{Griss:75, + AUTHOR = "Martin L. Griss", + TITLE = "The {REDUCE} System for Computer Algebra", + BOOKTITLE = "Proc. ACM 75", + YEAR = 1975, PAGES = "4-5", + ABSTRACT = {A brief description of {REDUCE} is presented.}} + +@INPROCEEDINGS{Griss:76, + AUTHOR = "Martin L. Griss", + TITLE = "The Definition and Use of Data-Structures in {REDUCE}", + BOOKTITLE = "Proc. SYMSAC 76", + YEAR = 1976, PAGES = "53-59", + ABSTRACT = {This paper gives a brief description and motivation of the mode +analyzing and data-structuring extensions to the algebraic language +{REDUCE}.}} + +@INPROCEEDINGS{Griss:76a, + AUTHOR = "Martin L. Griss", + TITLE = "An Efficient Sparse Minor Expansion Algorithm", + BOOKTITLE = "Proc. ACM 76", + YEAR = 1976, PAGES = "429-434", + ABSTRACT = {An improved algorithm for computing the minors of a (large) +sparse matrix of polynomials is described, with emphasis on efficiency and +optimal ordering. A possible application to polynomial resultant +computation is discussed.}} + +@INPROCEEDINGS{Griss:77, + AUTHOR = "Martin L. Griss", + TITLE = "Efficient Expression Evaluation in Sparse Minor +Expansion, Using Hashing and Deferred Evaluation", + YEAR = 1977, PAGES = "169-172", + BOOKTITLE = "Proc. 10th Hawaii International Conference on +Systems Sciences, Western Periodicals, Calif.", + ABSTRACT = {Efficient computation of the determinant of a matrix with +symbolic entries using minor expansion requires careful control of expression +evaluation. The use of hashing and deferred evaluation to avoid +excess computation is explored.}} + +@ARTICLE{Griss:77a, + AUTHOR = "M. L. Griss", + TITLE = "Efficient Recursive Minor Expansion", + JOURNAL = "ACM TOMS", + YEAR = 1977, + ABSTRACT = {The use of a "memo" facility to develop an efficient recursive +minor expansion algorithm (RMEM) is discussed. The method is simple and +efficient, and can be implemented as an interesting non-trivial +recursive procedure. The method is particularly attractive for +sparse symbolic matrices, and can also be used to enhance other +minor expansion methods developed for sparse symbolic matrices.}} + +@ARTICLE{Griss:78, + AUTHOR = "Martin L. Griss", + TITLE = "Using an Efficient Sparse Minor Expansion Algorithm to Compute +Polynomial Subresultants and the Greatest Common Denominator", + JOURNAL = "IEEE Trans on Computers", + YEAR = 1978, VOLUME = "C-27", NUMBER = 10, PAGES = "945-950", + ABSTRACT = {In this paper, the use of an efficient sparse minor expansion +method to directly compute the subresultants needed for the {GCD} of two +polynomials is described. The sparse minor expansion method (applied +either to Sylvester's or Bezout's matrix) naturally computes the +coefficients of the subresultants in the order corresponding to +a {PRS}, avoiding wasteful recomputation as much as possible. It is +suggested that this is an efficient method to compute the Resultant +and {GCD} of Sparse Polynomials.}} + +@INPROCEEDINGS{Griss:78a, + AUTHOR = "Martin L. Griss and Robert R. Kessler", + TITLE = "{REDUCE}/1700: A Micro-coded Algebra System", + YEAR = 1978, VOLUME = 11, PAGES = "130-138", + BOOKTITLE = "Proc. Micro, {IEEE}", + ABSTRACT = {In this paper, we report on the status of an ongoing project +aimed at producing a micro-coded Algebra machine.}} + +@ARTICLE{Griss:79, + AUTHOR = "Martin L. Griss and Anthony C. Hearn", + TITLE = "Portable {LISP} Compiler", + JOURNAL = "Software - Practice and Experience", VOLUME = 11, + PAGES = "541-605", YEAR = 1979, + ABSTRACT = {This paper describes the development of a portable {LISP} +compiler in the sense that only Standard {LISP} functions are used in its +definition and the output is a sequence of standard macro calls +easily implementable on current computers.}} + +@TECHREPORT{Griss:79a, + AUTHOR = "Martin L. Griss and Robert R. Kessler", + TITLE = "A Micro-programmed Implementation of {Standard} {LISP} and +{REDUCE} on the {Burroughs B1700/B1800} Computer", + INSTITUTION = "University of Utah", YEAR = 1979, TYPE = "Report", + MONTH = "February", + ABSTRACT = {This paper describes the implementation of a microcoded {LISP} +"machine" (the MTLISP) for the Burroughs B1700/B1800 computers. +This interpreter supports a complete Standard {LISP} and {REDUCE} +Algebra system, as well as a variety of experimental {LISP-like} +systems.}} + +@INPROCEEDINGS{Grozin:83, + AUTHOR={A. G. Grozin}, + TITLE={Calculation of one-loop diagrams of {$1 \to 2$} decays with {REDUCE}}, + BOOKTITLE={Proc. Int. Conf. on Computer Algebra in Theoretical Physics, +Dubna}, + YEAR = 1983, PAGES = {226-231}, + COMMENT = {To appear in Phys. Lett. B}} + +@TECHREPORT{Grozin:88, + AUTHOR = "A. G. Grozin", + TITLE = "Solving Physical Problems with {REDUCE.} {1. REDUCE} +Language {2. Classical} Nonlinear Oscillator", + INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, +{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-115", + ABSTRACT = {This preprint is the first part of the problem book on using +{REDUCE} in physics. It contains many examples useful for the +construction of programs for solving physical problems of very +different nature. This part contains examples illustrating {REDUCE} +language (sect. 1) and the problem of classical nonlinear +oscillator (sect. 2). To be published (with additions) as a book with +"Nauka" publishers, Moscow.}} + +@TECHREPORT{Grozin:88a, + AUTHOR = "A. G. Grozin", + TITLE = "Solving Physical Problems with {REDUCE.} {3. Nonlinear} +Water Waves {4. Calculation} of the Curvature Tensor {5. Angular} +Momentum Addition", + INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, +{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-136", + ABSTRACT = {This preprint is the second part of the problem book on using +{REDUCE} in physics. It contains many examples useful for the construction of +programs for solving physical problems of very different nature. This +part contains the problem of nonlinear water waves (sect. 3), the +calculation of the curvature tensor (sect. 4) and angular momentum +addition (sect. 5).}} + +@TECHREPORT{Grozin:88b, + AUTHOR = "A. G. Grozin", + TITLE = "Solving Physical Problems with {REDUCE.} {6. Quantum} +Nonlinear Oscillator {7. Rotator} in a Weak Field {8. Radiative} +Transitions in Charmonium", + INSTITUTION = "Institute of Nuclear Physics 630090, Novosibirsk, +{USSR}", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-140", + ABSTRACT = {This preprint is the last part of the problem book on using +{REDUCE} in physics. It contains many examples useful for the construction of +programs for solving physical problems of very different nature. This +part contains the problem of quantum nonlinear oscillator (sect. 6), +rotator in a weak field (sect. 7) and radiative transitions in +charmonium (sect. 8).}} + +@TECHREPORT{Grozin:90, + AUTHOR = {A. G. Grozin}, + TITLE = {{REDUCE} in elementary particle physics. {Introduction}}, + INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, + YEAR = 1990, NUMBER = {INP 90-42}, + COMMENT = {These 5 preprints together with the previous 3 will be published +as a book "Solving physical problems with REDUCE"}} + +@TECHREPORT{Grozin:90a, + AUTHOR = {A. G. Grozin}, + TITLE = {{REDUCE} in elementary particle physics. {Quantum electrodynamics}}, + INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, + YEAR = 1990, NUMBER = {INP 90-71}} + +@TECHREPORT{Grozin:90b, + AUTHOR = {A. G. Grozin}, + TITLE = {{REDUCE} in elementary particle physics. {Quantum chromodynamics}}, + INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, + YEAR = 1990, NUMBER = {INP 90-62}} + +@TECHREPORT{Grozin:91, + AUTHOR = {A. G. Grozin}, + TITLE = {{REDUCE} in elementary particle physics. {Weak interactions}}, + INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, + YEAR = 1991, NUMBER = {INP 91-56}} + +@TECHREPORT{Grozin:91a, + AUTHOR = {A. G. Grozin}, + TITLE = {{REDUCE} in elementary particle physics. {Radiative corrections}}, + INSTITUTION = {Institute of Nuclear Physics, Novosibirsk}, + YEAR = 1991, NUMBER = {INP 91-46}} + +@ARTICLE{Gunion:72, + AUTHOR = "J. F. Gunion and S. J. Brodsky and R. Blankenbecler", + TITLE = "Composite Theory of Large Angle Scattering and New +Tests of Parton Concepts", + JOURNAL = "Phys. Lett.", + YEAR = 1972, VOLUME = "39B", PAGES = "649-653"} + +@TECHREPORT{Gunion:73, + AUTHOR = "J. F. Gunion and S. J. Brodsky and R. Blankenbecler", + TITLE = "Large Angle Scattering and the Interchange Force", + INSTITUTION = "SLAC", + YEAR = 1973, TYPE = "Report", NUMBER = "SLAC-PUB-1183"} + +@ARTICLE{Gunion:85, + AUTHOR = "J. F. Gunion and Z. Kunszt", + TITLE = "Improved Analytic Techniques for Tree Graph Calculations and +the $g g q {\bar q} l {\bar l}$ subprocess", + JOURNAL = "Phys. Lett.", + YEAR = 1985, VOLUME = "161B", PAGES = "333-340"} + +@ARTICLE{Hadinger:87, + AUTHOR = "G. Hadinger and Y. S. Tergimen", + TITLE = "Recurrence Relations for the {Dunham} Coefficients and Analytic +Expressions of the Diagonal Radial Matrix Elements for an Anharmonic +Oscillator", + JOURNAL = "Journ. Chem. Phys.", + YEAR = 1987, VOLUME = 87, NUMBER = 4, PAGES = "2143-2150", + COMMENT = {"As an illustrative application, all the set of $Y_{n}$ +coefficients previously published are found again by using the +computer algebraic manipulation language {REDUCE}. A number of diagonal +matrix elements of {CO, HBr and HCl} have been symbolically computed and +compared with previous available results." Their method depends on +some algebraic manipulation, and the main point is that automation +gives a simpler formulation of the problem.}} + +@ARTICLE{Handy:87, + AUTHOR = "N. C. Handy", + TITLE = "The Derivation of Vibration-Rotation Kinetic Energy Operators, +in Internal Coordinates", + JOURNAL = "Mol. Phys.", + YEAR = 1987, VOLUME = 61, PAGES = "207-223", + COMMENT = {{REDUCE USED} to produce a straightforward method for the +derivation of kinetic energy operators in molecular vibration-rotation. He +notes in the introduction "The purpose of this paper is to derive a simple and +straightforward procedure for which it is possible to make the +computer do all the hard work. After many years of investigating this +problem, this author believes that this must be the reliable way to +proceed."}} + +@PHDTHESIS{Harper:87, + AUTHOR = "David Harper", + TITLE = "Dynamics of the Outer Satellites of Saturn", + SCHOOL = "Univ. of Liverpool, England", + YEAR = 1987} + +@TECHREPORT{Harper:89, + AUTHOR = "David Harper and Chris Wooff and David Hodgkinson", + TITLE = "A Guide to Computer Algebra Systems", + INSTITUTION = "Computer Laboratory, The University of Liverpool, +Liverpool, England", YEAR = 1989, MONTH = "September", TYPE = "Report"} + +@ARTICLE{Harper:89a, + AUTHOR = "David Harper", + TITLE = "{Vector33:} A {REDUCE} Program for Vector Algebra and Calculus +in Orthogonal Curvilinear Coordinates", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1989, VOLUME = 54, NUMBER = "2 and 3", PAGES = "295-305", + MONTH = "June and July"} + +@ARTICLE{Harrington:77, + AUTHOR = "Steven J. Harrington", + TITLE = "A Symbolic Limit Evaluation Program in {REDUCE}", + YEAR = 1977, + ABSTRACT = {A program for the automatic evaluation of algebraic +limits, implemented in {MODE-REDUCE}, is described. The program +incorporates many of the techniques previously employed, including +the top-down recursive evaluation, power series expansion, and +L'Hopital's rule. It also introduces the concept of a special +algebraic form for limits.}} + +@ARTICLE{Harrington:77a, + AUTHOR = "S. J. Harrington", + TITLE = "{REDUCE} Solution to Problem \#8", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = "1977 and 1978", VOLUME = "11 and 12", NUMBER = "4 and 1", + PAGES = "7-8", MONTH = "November and February"} + +@ARTICLE{Harrington:79, + AUTHOR = "Steven J. Harrington", + TITLE = "A New Symbolic Integration System in {REDUCE}", + JOURNAL = "Comp. Journ.", + YEAR = 1979, VOLUME = 22, NUMBER = 2, PAGE = "127-131", + ABSTRACT = {A new integration system, employing both algorithmic and +pattern match integration schemes is presented. The organization of the +system differs from that of earlier programs in its emphasis on the +algorithmic approach to integration, its modularity, and its ease of +revision. The new {Norman-Risch} algorithm and its implementation at the +University of Cambridge are employed, supplemented by a powerful +collection of simplification and transformation rules. The facility for +user defined integrals and functions is also included. The program is +both fast and powerful, and can be easily modified to incorporate +anticipated developments in symbolic integration.}} + +@ARTICLE{Harrington:79a, + AUTHOR = "Steven J. Harrington", + TITLE = "A Symbolic Limit Evaluation Program in {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1979, VOLUME = 13, NUMBER = 1, PAGES = "27-31", MONTH = "February"} + +@ARTICLE{Hartley:91, + AUTHOR = "David Hartley and Robin W. Tucker", + TITLE = "A Constructive Implementation of the {Cartan-K{\"a}hler} Theory +of Exterior Differential Systems", + JOURNAL = "J. Symb. Comp.", + YEAR = 1991, VOLUME = 12, NUMBER = 6, PAGES = "655-667", + MONTH = "December", + ABSTRACT = {An efficient algorithm for the construction of a regular chain +of involutive integral elements for a general exterior differential system +is presented. It is based upon the existence theorems of the +{Cartan-}K{"\a}hler theory, and may be used to analyse partial differential +equations by formulating them as exterior differential systems.}} + +@ARTICLE{Hasenfratz:80, + AUTHOR = "Anna Hasenfratz and Peter Hasenfratz", + TITLE = "The Connection Between the Parameters of Lattice and +Continuum {QCD}", + JOURNAL = "Phys. Lett.", + YEAR = 1980, VOLUME = "93B", NUMBER = "1,2", PAGES = "165-169", + MONTH = "June"} + +@INPROCEEDINGS{Hearn:68, + AUTHOR = "Anthony C. Hearn", + TITLE = "{REDUCE}: A User-Oriented Interactive System for Algebraic +Simplification", + YEAR = 1968, PAGES = "79-90", + EDITOR = "M. Klerer and J. Reinfelds", + BOOKTITLE = "Interactive Systems for Experimental Applied Mathematics", + PUBLISHER = "Academic Press", ADDRESS = "New York"} + +@ARTICLE{Hearn:69, + AUTHOR = "A. C. Hearn and P. K. Kuo and D. R. Yennie", + TITLE = "Radiative Corrections to an Electron-Positron Scattering +Experiment", + JOURNAL = "Phys. Rev.", + YEAR = 1969, VOLUME = 187, PAGES = "2088-2096"} + +@INPROCEEDINGS{Hearn:69a, + AUTHOR = "Anthony C. Hearn", + TITLE = "The Problem of Substitution", + YEAR = 1969, PAGES = "3-19", + EDITOR = "R.G. Tobey", + BOOKTITLE = "Proc. of the 1968 Summer Institute on Symbolic Mathematical +Computation", + PUBLISHER = "IBM Boston Prog. Center", ADDRESS = "Cambridge, Mass", + COMMENT = "IBM Programming Laboratory Report No. FSC-69-0312"} + +@ARTICLE{Hearn:71, + AUTHOR = "Anthony C. Hearn", + TITLE = "Applications of Symbolic Manipulation in Theoretical Physics", + JOURNAL = "Comm. ACM", + YEAR = 1971, VOLUME = 14, PAGES = "511-516"} + +@INPROCEEDINGS{Hearn:71a, + AUTHOR = "Anthony C. Hearn", + TITLE = "{REDUCE} 2: A System and Language for Algebraic Manipulation", + YEAR = 1971, PAGES = "128-133", + EDITOR = "S.R. Petrick", + BOOKTITLE = "Proc. of Second Symposium on Symbolic and +Algebraic Manipulation", + PUBLISHER = "ACM, New York"} + +@INPROCEEDINGS{Hearn:71b, + AUTHOR = "Anthony C. Hearn", + TITLE = "Calculation of Traces of Products of Gamma Matrices", + YEAR = 1971, PAGES = "I-30 - I-44", + BOOKTITLE = "Proc. of the Second Colloquium on Advanced Computing +Methods in Theoretical Physics, {CNRS}, Marseilles", + ABSTRACT = {A survey of the algorithms available for the calculation of +traces of products of Dirac gamma matrices is presented.}} + +@INPROCEEDINGS{Hearn:71c, + AUTHOR = "Anthony C. Hearn", + TITLE = "The Computer Solution of Algebraic Problems by Pattern Matching", + YEAR = 1971, PAGES = "I-45 - I-57", + BOOKTITLE = "Proc. of the Second Colloquium on Advanced Computing +Methods in Theoretical Physics, {CNRS}, Marseilles", + ABSTRACT = {This paper discusses computer techniques for the solution of +algebraic problems in theoretical physics and related areas by pattern +matching.}} + +@INPROCEEDINGS{Hearn:72, + AUTHOR = "Anthony C. Hearn", + TITLE = "Computer Solution of Symbolic Problems in Theoretical Physics", + YEAR = 1972, PAGES = "567-596", + BOOKTITLE = "Computing as a Language of Physics, {IAEA}, Vienna", + ABSTRACT = {A survey of the computing techniques currently available for +the solution of nonnumerical problems in theoretical physics and related +areas is presented.}} + +@ARTICLE{Hearn:72a, + AUTHOR = "Anthony C. Hearn", + TITLE = "Improved Non-modular Polynomial {GCD} Algorithm", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1972, PAGES = "10-15", + ABSTRACT = {An improved non-modular algorithm for the calculation of the +greatest common divisor of two multivariate polynomials is presented.}} + +@ARTICLE{Hearn:72b, + AUTHOR = "Anthony C. Hearn", + TITLE = "A {REDUCE} Solution of Problem \#2 - The {Y(2n)} Functions", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1972, VOLUME = 14, + ABSTRACT = {A {REDUCE} solution to {SIGSAM} Problem \#2 is described.}} + +@INPROCEEDINGS{Hearn:73, + AUTHOR = "Anthony C. Hearn and R{\"u}diger G. K. Loos", + TITLE = "Extended Polynomial Algorithms", + YEAR = 1973, PAGES = "147-152", + BOOKTITLE = "Proc. {ACM} 73", + ABSTRACT = {It is shown that standard polynomial algorithms may be +applied to a much wider class of functions by making a straightforward +generalization of the concept of the exponent. The implementation of a +computer algebra system from a standard set of polynomial programs which +allows for any coefficient or exponent structure is also discussed.}} + +@INPROCEEDINGS{Hearn:73a, + AUTHOR = "Anthony C. Hearn", + TITLE = "The {REDUCE} Program for Computer Algebra", + YEAR = 1973, + BOOKTITLE = "Proc. of the Third Colloquium on Advanced Computing Methods +in Theoretical Physics, {CNRS}, Marseilles", + ABSTRACT = {The status of the {REDUCE} program for computer algebra in 1973 +is illustrated by a discussion of some aspects of its design philosophy.}} + +@INPROCEEDINGS{Hearn:74, + AUTHOR = "Anthony C. Hearn", + TITLE = " Polynomial and Rational Function Representations", + YEAR = 1974, PAGE = "211", + BOOKTITLE = "Proc. Math Software II, Purdue University", + ABSTRACT = {A survey of some current methods for computer manipulation of +polynomials and rational functions is presented. Particular emphasis +is placed on the desirability of writing programs which avoid explicit +reference to the data structures used in the manipulation."}} + +@INPROCEEDINGS{Hearn:74a, + AUTHOR = "Anthony C. Hearn", + TITLE = "A Mode Analyzing Algebraic Manipulation Program", + YEAR = 1974, PAGES = "722-724", + BOOKTITLE = "Proc. {ACM} 74", + COMMENT = {Describes a version of the {REDUCE} program for algebraic +manipulation which performs a complete mode analysis as a separate extension +of the parse.}} + +@ARTICLE{Hearn:76, + AUTHOR = "Anthony C. Hearn", + TITLE = "Scientific Applications of Symbolic Computation", + JOURNAL = "Computer Science and Scientific Comp.", + YEAR = 1976, PAGES = "83-108", + ABSTRACT = {This paper reviews the use of symbolic computation systems for +problem solving in scientific research.}} + +@INPROCEEDINGS{Hearn:76a, + AUTHOR = "A. C. Hearn", + TITLE = "A New {REDUCE} Model for Algebraic Simplification", + YEAR = 1976, PAGES = "46-52", + BOOKTITLE = "Proc. {SYMSAC} 76, {ACM}", + ABSTRACT = {This paper shows how the general concepts of mode analysis can +play a useful role in the design and implementation of programs +for algebraic simplification.}} + +@INPROCEEDINGS{Hearn:76b, + AUTHOR = "A. C. Hearn", + TITLE = "Symbolic Computation", + YEAR = 1976, PAGES = "201-211", + BOOKTITLE = "Proc. {CERN} 1976 Computing School, {CERN} Geneva", + COMMENT = {Lecture Notes.}} + +@INPROCEEDINGS{Hearn:77, + AUTHOR = "A. C. Hearn", + TITLE = "The Structure of Algebraic Computations", + YEAR = 1977, PAGES = "1-15", + BOOKTITLE = "Proc. of the Fourth Colloquium on Advanced Comp. +Methods in Theor. Physics. St. Maximin, France", + ABSTRACT = {Most algebraic computations which arise from physical problems +have considerable structure in their specification because of the many +physical conservation laws and the nature of our approximation techniques. +The exploitation of this structure is often the reason why hand +calculations of non-trivial problems are possible. However, most +available algebra systems do not preserve such structure in a consistent +manner, and consequently produce results which are far less comprehensible +than equivalent hand calculations. In this paper we shall describe +techniques which can utilize the algebraic structure more effectively and +apply them to several examples.}} + +@INPROCEEDINGS{Hearn:78, + AUTHOR = "Anthony C. Hearn", + TITLE = "Algebraic Manipulation by Computer", + YEAR = 1978, PAGES = "96-116", + BOOKTITLE = "Proc. Intern. Meeting on Programm. and Math. Meth. for +Solving Phys. Probs., Dubna, USSR", + ABSTRACT = {This paper reviews the use of algebraic manipulation by computer +as a tool for scientific problem solving.}} + +@INPROCEEDINGS{Hearn:79, + AUTHOR = "Anthony C. Hearn", + TITLE = "Non-Modular Computation of Polynomial {GCDs} Using Trial +Division", + YEAR = 1979, VOLUME = 72, PAGES = "227-239", + BOOKTITLE = "Proc. {EUROSAM} 79", + ABSTRACT = {This paper describes a new algorithm for the determination of +the {GCD} of two multivariate polynomials by non-modular means.}} + +@ARTICLE{Hearn:79a, + AUTHOR = "Anthony C. Hearn and Arthur C. Norman", + TITLE = "A One-Pass Prettyprinter", + JOURNAL = "Sigplan Notices, ACM 12", + YEAR = 1979, VOLUME = 14, PAGES = "50-58", + ABSTRACT = {We propose a new method for program formatting which is +described in terms of two coroutines.}} + +@INPROCEEDINGS{Hearn:80, + AUTHOR = "Anthony C. Hearn", + TITLE = "The Personal Algebra Machine", + YEAR = 1980, PAGES = "621-628", + BOOKTITLE = "Information Processing 80, Proc. {IFIP} +Congress 80"} + +@ARTICLE{Hearn:81, + AUTHOR = "Anthony C. Hearn and S. Watanabe", + TITLE = "Analytic Integration by Computer", + JOURNAL = "Information Processing Society of Japan 22", + YEAR = 1981, PAGES = "639-650"} + +@INPROCEEDINGS{Hearn:81a, + AUTHOR = "Anthony C. Hearn", + TITLE = "Symbolic Computation and its Application to +High-Energy Physics", + YEAR = 1981, PAGES = "390-406", + BOOKTITLE = "Proc. 1980 {CERN} School of Computing, Geneva"} + +@INPROCEEDINGS{Hearn:82, + AUTHOR = "Anthony C. Hearn", + TITLE = "{REDUCE} - A Case Study in Algebra System Development", + YEAR = 1982, VOLUME = 144, PAGES = "263-272", + BOOKTITLE = "Proc. of {EUROCAM} '82, Lecture Notes on Comp. +Science"} + +@INPROCEEDINGS{Hearn:82a, + AUTHOR = "Anthony C. Hearn and M. L. Griss and E. Benson", + TITLE = "Current Status of a Portable {LISP} Compiler", + YEAR = 1982, + BOOKTITLE = "Proc. {SIGPLAN} '82 Symp. on Compiler +Construction, ACM", PAGES = "276-283"} + +@INPROCEEDINGS{Hearn:85, + AUTHOR = "Anthony C. Hearn", + TITLE = "Structure: The Key to Improved Algebraic Computation", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "215-230"} + +@INPROCEEDINGS{Hearn:86, + AUTHOR = "Anthony C. Hearn", + TITLE = "Optimal Evaluation of Algebraic Expressions", + BOOKTITLE = "Proc. {AAECC}-3, Lecture Notes on Comp. Science", + PUBLISHER = "Springer Verlag", + YEAR = 1986, VOLUME = 229, PAGES = "392-403"} + +@TECHREPORT{Hearn:91, + AUTHOR = "Anthony C. Hearn", + TITLE = "{REDUCE} User's Manual, {Version} 3.6", + INSTITUTION = "RAND", + YEAR = 1995, TYPE = "Report", + NUMBER = "CP 78", MONTH = "July"} + +@INPROCEEDINGS{Hearn:93, + AUTHOR = "Anthony C. Hearn and Eberhard Schr{\"u}fer", + TITLE = "An Order-sorted Approach to Algebraic Computation", + BOOKTITLE = "Proc. {DISCO '93}, Lecture Notes on Comp. Science", + YEAR = 1993, VOLUME = 722, PAGES = "134-144", + PUBLISHER = "Springer-Verlag", + ABSTRACT = {This paper presents the prototype design of an algebraic +computation system that manipulates algebraic quantities as generic objects +using order-sorted algebra as the underlying model. The resulting programs +have a form that is closely related to the algorithmic description of a +problem, but with the secruity of full type checking in a compact, natural +style.}} + +@ARTICLE{Hearn:95, + AUTHOR = "Anthony C. Hearn and Eberhard Schr{\"u}fer", + TITLE = "A Computer Algebra System based on Order-sorted Algebra", + JOURNAL = "Journ. Symbolic Computation", + YEAR = 1995, VOLUME=19, PAGES = "65-77", + ABSTRACT = "This paper presents the prototype design of an algebraic +computation system that manipulates algebraic quantities as generic +objects using order-sorted algebra as the underlying model. The resulting +programs have a form that is closely related to the algorithmic +description of a problem, but with the security of full type checking in a +compact, natural style."} + +@ARTICLE{Hehl:92, + AUTHOR = "Friedrich W. Hehl and Hartmut Meyer", + TITLE = "Mit Buchstaben auf dem Computer rechnen", + JOURNAL = "Physikalische {Bl\"{a}tter}", + YEAR = 1992, VOLUME = "48", PAGES = "377-381", + COMMENT = {(in German) Describes the application of + symbolic computation using examples coded in {REDUCE}. The CA systems + of interest for physicists are classified. A series of problems + from physics which have successfully been solved with CA methods + is given}} + +@BOOK{Hehl:92a, + AUTHOR = "F.W. Hehl and V. Winkelmann and H. Meyer", + TITLE = "Computer-Algebra. Ein Kompaktkurs {\"{u}ber} die Anwendung von +REDUCE", + PUBLISHER = "Springer-Verlag, Berlin, Heidelberg, New York, + ISBN 3-540-55724-5", + YEAR = 1992} + +@ARTICLE{Hermann:83, + AUTHOR = "R. Hermann", + TITLE = "Geometric Construction and Properties of Some Families of +Solutions of Nonlinear Partial Differential Equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1983, VOLUME = 24, NUMBER = "3", PAGES = "510-521", + COMMENT = {First of series of papers on 19th century pde theory. The +presentation is aimed at including systems such as {MACSYMA} and {REDUCE} +as tools. This paper is on Lagrange-Charpit method. "I have in mind +developing the differential algebraic aspects of the formalism, going +beyond the 19th century with the aid of symbolic computer systems".}} + +@ARTICLE{Hess:84, + AUTHOR = "P. O. Hess and W. Greiner", + TITLE = "The Collective Modes of Nuclear Molecules", + JOURNAL = "Il Nuovo Cimento", + YEAR = 1984, VOLUME = "83A", PAGES = "76-177", + COMMENT = {A long paper, admits use of {REDUCE} (on page 101) to invert +11 x 11 matrix.}} + +@TECHREPORT{Hettich:77, + AUTHOR = "R. P. Hettich and J. A. van Hulzen", + TITLE = "Approximation with a Class of Rational Functions", + INSTITUTION = "Department of Applied Mathematics, Twente +University of Technology, The Netherlands", + YEAR = 1977, TYPE = "Memorandum", + NUMBER = 165, MONTH = "May"} + +@ARTICLE{Hietarinta:83, + AUTHOR = "J. Hietarinta", + TITLE = "A search for integrable two-dimensional {Hamiltonian} systems +with polynomial potential", + JOURNAL = "Phys. Lett.", + YEAR = 1983, VOLUME = "96A", PAGES = "273-278", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:83a, + AUTHOR = "J. Hietarinta", + TITLE = "Integrable Families of {Henon-Heiles} Type {Hamiltonians} and a +New Duality", + JOURNAL = "Phys. Rev. A", + YEAR = 1983, VOLUME = 28, PAGES = "3670-3672", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:84, + AUTHOR = "J. Hietarinta", + TITLE = "Classical versus quantum integrability", + JOURNAL = "J. Math. Phys.", + YEAR = 1984, VOLUME = 25, PAGES = "1833-1840", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:84a, + AUTHOR = "J. Hietarinta", + TITLE = "New integrable {Hamiltonians} with transcendental invariants", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1984, VOLUME = 52, PAGES = "1057-1060", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:84b, + AUTHOR = "J. Hietarinta and B. Grammaticos and B. Dorizzi and A. Ramani", + TITLE = "Coupling-Constant Metamorphosis and Duality between +Integrable {Hamiltonian} Systems", + JOURNAL = "Phys. Rev. Lett.", + YEAR = 1984, VOLUME = 53, PAGES = "1707-1710", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:85, + AUTHOR = "J. Hietarinta", + TITLE = "How to construct integrable {Fokker-Planck} and +electromagnetic {Hamiltonians} from ordinary integrable {Hamiltonians}", + JOURNAL = "J. Math. Phys.", + YEAR = 1985, VOLUME = 26, PAGES = "1970-1975", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:87, + AUTHOR = "J. Hietarinta", + TITLE = "Direct methods for the search of the second invariant", + JOURNAL = "Physics Reports", + YEAR = 1987, VOLUME = 147, PAGES = "87-154", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@ARTICLE{Hietarinta:87a, + AUTHOR = "J. Hietarinta", + TITLE = "A search of bilinear equations passing {Hirota's} three-soliton +condition: {I.} {KdV}-type bilinear equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1987, VOLUME = 28, PAGES = "1732-1742", + COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables +vanish on a affine manifold defined by {LET-rules}. Large scale +computation.}} + +@ARTICLE{Hietarinta:87b, + AUTHOR = "J. Hietarinta", + TITLE = "A search of bilinear equations passing {Hirota's} three-soliton +condition: {II.} {mKdV}-type bilinear equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1987, VOLUME = 28, PAGES = "2094-2101", + COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables +vanish on a affine manifold defined by {LET-rules}. Large scale +computation.}} + +@ARTICLE{Hietarinta:87c, + AUTHOR = "J. Hietarinta", + TITLE = "A search of bilinear equations passing {Hirota's} three-soliton +condition: {III.} {Sine-Gordon}-type bilinear equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1987, VOLUME = 28, PAGES = "2586-2592", + COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables +vanish on a affine manifold defined by {LET-rules}. Large scale +computation.}} + +@ARTICLE{Hietarinta:88, + AUTHOR = "J. Hietarinta", + TITLE = "A search of bilinear equations passing {Hirota's} three-soliton +condition: {IV.} Complex bilinear equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1988, VOLUME = 29, PAGES = "628-635", + COMMENT = {{REDUCE} is used to check when polynomials in 6 to 12 variables +vanish on a affine manifold defined by {LET-rules}. Large scale computation. +computation.}} + +@ARTICLE{Hietarinta:89, + AUTHOR = "J. Hietarinta and B. Grammaticos", + TITLE = "On the $\hbar^{2}$-correction terms in quantum integrability", + JOURNAL = "J. Phys. A: Mat. Gen.", + YEAR = 1989, VOLUME = "TBD", PAGES = "TBD", + COMMENT = {{REDUCE} is used to construct and verify constants of motion.}} + +@INPROCEEDINGS{Hietarinta:91, + AUTHOR = "J. Hietarinta", + TITLE = "From an analytical formula to a movie by way of {REDUCE} and {C}", + BOOKTITLE = "Proc. of the Workshop on Symbolic and Numeric Computation", + PUBLISHER = "Research Reports, Computing Centre of Helsinki University", + YEAR = 1991, PAGES = "117-126"} + +@TECHREPORT{Hietarinta:92, + AUTHOR = "Jarmo Hietarinta", + TITLE = "Solving the {Yang-Baxter} equation in 2 dimensions with massive +use of factorizing Gr{"\o}bner basis computations", + INSTITUTION = "University of Turku, Finland", YEAR = 1992, + MONTH = "January", TYPE = "Preprint", + COMMENT = {Submitted to ISSAC '92}, + ABSTRACT = {The complete solution to the constant (quantum) Yang-Baxter +equation was recently obtained in the two dimensional case +(= all indices range over 1,2). This amounts to solving a set of 64 +equations in 16 variables. We describe here how the problem was solved, +first by breaking it into smaller subproblems by using the symmetries of +the equation, and then by solving each subproblem by computing the +factorized Gr{"\o}bner basis using the {'grobner'-}package written by Melenk, +M{"\o}ller and Neun for REDUCE 3.4.}}. + +@TECHREPORT{Hietarinta:92a, + AUTHOR = "Jarmo Hietarinta", + TITLE = "Solving the two-dimensional constant quantum {Yang-Baxter} + equation", + INSTITUTION = "University of Turku, Finland", YEAR = 1992, + MONTH = "May", TYPE = "Report", NUMBER = "TURKU-FL-R7"} + +@BOOK{Hirota:89, + AUTHOR = "Ryogo Hirota and Masaaki Ito", + TITLE = "Introduction to {REDUCE --- Doing} Symbolic Computation on {PC}", + PUBLISHER = "Science sha, Tokyo", MONTH = "June", YEAR = 1989, + COMMENT = {(In Japanese).}} + +@TECHREPORT{Horowitz:75, + AUTHOR = "E. Horowitz and D. R. Musser", + TITLE = "The Synthesis and Use of Algebraic Specifications of Data +Structures", + INSTITUTION = "University of Southern California", + YEAR = 1975, TYPE = "Preprint"} + +@ARTICLE{Horwitz:83, + AUTHOR = "B. Horwitz", + TITLE = "Unequal Diameters and Their Effects on Time Varying Voltages +in Branched Neurons", + JOURNAL = "BioPhys. J.", + YEAR = 1983, VOLUME = 41, PAGES = "51-66", + COMMENT = {Theoretical biophysics. Much algebra, and used {REDUCE} to +decrease mental labor. "Crucial point is that the existence of such computer +techniques allows higher-order correction terms to be used."}} + +@ARTICLE{Hughes:90, + AUTHOR = "D. I. Hughes", + TITLE = "Symbolic Computation with Fermions", + JOURNAL = "J. Symbolic Computation", + YEAR = 1990, VOLUME = 10, NUMBER = 6, PAGES = "657-664", MONTH = "December", + ABSTRACT = {A set of {REDUCE} routines for manipulating operators which +anticommute amongst themselves is described. These routines have +applications in theories such as supergravity where anticommuting operators +are used to represent fermions. The Dirac bracket of the supersymmetry +constraints arising in a quantum cosmological model based on N = 1 +supergravtiy coupled to a massless scalar multiplet is calculated as an +example.}} + +@INPROCEEDINGS{Hulshof:84, + AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", + TITLE = "Automatic Error Cumulation Control", + BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes +in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "260-271", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Hulshof:85, + AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", + TITLE = "An Expression Compression Package for {REDUCE} based on +Factorization and Controlled Expansion", + BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes +in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "315-316", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Hulshof:81, + AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen and J. Smit", + TITLE = "Code Optimization Facilities Applied in the {Netform} Context", + INSTITUTION = "Department of Applied Mathematics, Twente +University of Technology, The Netherlands", + YEAR = 1981, TYPE = "Memorandum", NUMBER = 368, + MONTH = "December"} + +@ARTICLE{Hulshof:83, + AUTHOR = "B. J. A. Hulshof and J. A. van Hulzen", + TITLE = "Some {REDUCE} Facilities for Pretty Printing Subscripts and Formal +Derivatives", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "16-20", MONTH = "February"} + +@ARTICLE{Hunt:91, + AUTHOR = "R. E. Hunt and D. G. Crighton", + TITLE = "Instability of flows in spatially developing media", + JOURNAL = "Proc. Roy. Soc. Lond. A", +YEAR = 1991, VOLUME = 435, PAGES = "109-128", + COMMENT = {Uses {REDUCE} to find series solutions for two fluid-dynamical + problems, and then condenses the series into exact solutions}} + +@TECHREPORT{Husberg:81, + AUTHOR = "N. Husberg", + TITLE = "Preliminary {II} {REDUCE}-2 and {Analitik-74}, a Comparison", + INSTITUTION = "Helsinki University of Technology Computing +Center", YEAR = 1981, MONTH = "November"} + +% REDUCE BIBLIOGRAPHY + +% Part 3: I-O + +% Copyright (c) 1993 RAND. All Rights Reserved. + +% Additions and corrections are solicited. Please send them, in the +% same format as these entries if possible, to reduce at rand.org. + + +@TECHREPORT{Idesawa:77, + AUTHOR = "M. Idesawa and T. Yatagai", + TITLE = "General Theory of Projection-Type {Moir\'e} Topography", + INSTITUTION = "Institute of Physical and Chemical Research, +Wako-Shi, Saitama", YEAR = 1977, TYPE = "Scientific Papers", + NUMBER = 71, + ABSTRACT = {The configuration of equi-order surfaces in the projection-type +{Moire} topography is described in terms of system parameters +without any restrictions on the measurement condition.}} + +@INPROCEEDINGS{Ilyin:87, + AUTHOR = "V. A. Ilyin and A. P. Kryukov", + TITLE = "{DIMREG} - The Package for Calculations in the Dimensional +Regularization with {4-dimensional} $\gamma^{5}$ -matrix in Quantum Field +Theory", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "225-232", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Ilyin:89, + AUTHOR = "V. A. Ilyin and A. P. Kryukov and A. Ya. Rodioniov and +A. Yu. Taranov", + TITLE = "Fast Algorithm for Calculation of {Dirac}'s Gamma-Matrices Traces", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1989, VOLUME = 23, NUMBER = 4, PAGES = "15-24", MONTH = "October"} + +@INPROCEEDINGS{Ilyin:91, + AUTHOR = "V. A. Ilyin and A. P. Kryukov", + TITLE = "Symbolic Simplification of Tensor Expressions Using Symmetries, +Dummy Indices and Identities", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "224-228", + YEAR = 1991, + ABSTRACT = {The algorithm based on simple geometrical ideas is suggested +for simplification of tensor expressions which takes into account +symmetries, dummy indices, and linear identities with many terms. The +results of the realization in REDUCE system are adduced.}} + +@INPROCEEDINGS{Ilyin:91a, + AUTHOR = "V. A. Ilyin and A. P. Kryukov and A. Ya. Rodionov and A Yu. +Taranov", + TITLE = "{PC} Implementation of Fast {Dirac} Matrix Trace Calculations", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "456-457", + YEAR = 1991, + COMMENT = {We present an implementation of fast algorithm for Dirac +matrix trace calculations. This implementation is made for {IBM} i +compatible {PC} and works under {REDUCE 3.3.1}. Name of package is +{CVIT}. The algorithm itself was described in [1]. It is based on intense +use of Fierz identities in N-dimensional space (N is arbitrary natural +number or symbol) and may be considered as an extension of well known +Kahane algorithm [2] on higher space dimensions.}} + +@TECHREPORT{Inada:80, + AUTHOR = "Nobuyuki Inada", + TITLE = "Fortran-Based {LISP} System for {REDUCE}", + INSTITUTION = "Information Science Laboratory, The Institute +of Physical and Chemical Research", + YEAR = 1980} + +@TECHREPORT{Ioakimidis:90, + AUTHOR = "N. I. Ioakimidis", + TITLE = "Construction of the Equation of Caustics in Dynamic Plane +Elasticity Problems with the Help of {REDUCE}", + INSTITUTION = "Division of Applied Mathematics and Mechanics, School of +Engineering, University of Patras, Greece", + YEAR = 1990} + ABSTRACT = {The method of caustics has become a very efficient tool in +crack, hole and many additional plane elasticity problems. Unfortunately, +the fundamental equation of the caustics frequently requires complicated +algebraic computations including that of a Jacobian determinant. Here we +show that computer algebra software can prove very efficient in these +computations, using as a vehicle for this illustration the already known +fundamental equation of caustics in dynamic plane elasticity (both for crack +problems in fracture mechanics as well as for hole and additional problems). +We have used the programming capabilities of {REDUCE}, a very popular +computer algebra system, for our algebraic computations. Moreover, we +illustrate the "learning" abilities of {REDUCE} especially for the +derivation of the complex form of this equation. The case of static plane +elasticity results simply as a special case of dynamic plane elasticity. +Additional possibilities are suggested in brief.}} + +@TECHREPORT{Ioakimidis:90a, + AUTHOR = "N. I. Ioakimidis", + TITLE = "Construction of Singular Integral Equations for Interacting +Straight Cracks by Using {REDUCE}", + INSTITUTION = "Division of Applied Mathematics and Mechanics, School of +Engineering, University of Patras, Greece", + YEAR = 1990} + ABSTRACT = {The method of singular integral equations has been applied to +the solution of crack problems in plane and antiplane elasticity +hundreds of times during the last twenty years. Here we revisit the case of +an arbitrary number of interacting straight cracks in plane elasticity and +we illustrate the possibility of constructing (algebraically) the +corresponding system of singular integral equations by using computer +algebra software. We present a procedure (computer program) by using +{REDUCE} as well as several examples of application of the present approach, +extensions and generalizations of which follow rather trivially.}} + +@ARTICLE{Ito:85, + AUTHOR = "M. Ito", + TITLE = "A {REDUCE} Program for Evaluating a {Lax} Pair Form", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1985, VOLUME = 34, PAGES = "325-331", + COMMENT = {{REDUCE} in nonlinear equations.}} + +@ARTICLE{Ito:85a, + AUTHOR = "M. Ito and F. Kako", + TITLE = "A {REDUCE} Program for Finding Conserved Densities of Partial +Differential Equations with Uniform Rank", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1985, VOLUME = 38, PAGES = "415-419"} + +@ARTICLE{Ito:88, + AUTHOR = "Masaaki Ito", + TITLE = "A {REDUCE} Program for {Hirota's} Bilinear Operator and +{Wronskian} Operations", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1988, VOLUME = 50, NUMBER = 3, PAGES = "321-330", MONTH = "August"} + +@ARTICLE{Ito:90, + AUTHOR = "Nobuyasu Ito and Tetsuhiko Chikyu", + TITLE = "Multi-Spin-Flip Dynamics of the {Ising} Chain", + JOURNAL = "Physica A", + YEAR = 1990, VOLUME = 166, PAGES = "193-205", + ABSTRACT = {Two kinds of multi-spin-flip discrete-time dynamics of the +Ising chain are solved analytically. One dynamics is the two sublattice +type flip and each sublattice contains {\em n} sequential spins +alternately. The other has the overlapped multi-spin-flip sequence. The +state of {\em n} spins at the next time step is selected from ${2}^{n}$ +states using the heat-bath type transition probability. These dynamics of +the Ising chain are equivalent to the statics of the square-lattice Ising +model with a 1 x 2 unit cell or of the triangular-lattice Ising model. +The analytic solutions of the single spin relaxation time of these +dynamics are obtained using these equivalences.}} + +@ARTICLE{Ito:90a, + AUTHOR = "Nobuyasu Ito", + TITLE = "Discrete-Time and Single-Spin-Flip Dynamics of the {Ising} Chain", + JOURNAL = "Progress of Theoretical Physics", + YEAR = 1990, VOLUME = 83, NUMBER = 4, PAGES = "682-692", MONTH = "April", + ABSTRACT = {Some stochastic dynamics of the Ising chain are discussed +analytically and their flip-sequence dependences are studied in the +present paper. The dynamics are the discrete-time and single-spin-flip +dynamics. The flip sequence is of sequential or sublattice-type. Their +relaxation times of single spin expectation functions are calculated. The +sequential-flip dynamics of {\em n}-site chain has the same correlation +time as the {\em n}-sublattice dynamics. The relaxation becomes slow when +this {\em n} is made large. The static models equivalent to these dynamic +models are the Ising models on a triangular lattice with a skew boundary +condition which has the same couplings in two directions. Spin-spin +correlation lengths in the direction perpendicular to the anisotropic +direction are obtained for these equivalent models. They depend only on +the ratio of the lattice width to boundary skew.}} + +@ARTICLE{Ito:94, + AUTHOR = "Masaaki Ito", + TITLE = "{SYMCD} - a {REDUCE} package for finding symmetries and conserved +densitites of systems of nonlinear evolution equations", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1994, VOLUME = 79, NUMBER = 3, PAGES = "547-554", MONTH = "May"} + +@ARTICLE{Jansen:86, + AUTHOR = "Paul Jansen and Peter Weidner", + TITLE = "High-Accuracy Arithmetic Software--Some Tests of the +{ACRITH} Problem-Solving Routines", + JOURNAL = "{ACM} {TOMS}", + YEAR = 1986, VOLUME = 12, NUMBER = 1, PAGES = "62-70", MONTH = "March", + COMMENT = {A criticism of {ACRITH}, shows {REDUCE} bigfloats are more +accurate and comparable in speed.}} + +@ARTICLE{Janssen:87, + AUTHOR = "M. H. M. Janssen and D. H. Parker and S. Stolte", + TITLE = "Saturation in Laser-Induced Fluorescence: Effects on +Alignment Parameters", + JOURNAL = "Chemical Phys.", + YEAR = 1987, VOLUME = 113, PAGES = "357-382", + COMMENT = {"Computer algebra programs are used to generate simple analytical +expressions which account for the influence of saturation on +determining alignment parameters." The system is {REDUCE}.}} + +@ARTICLE{Jeffrey:84, + AUTHOR = "D. J. Jeffrey and Y. Onishi", + TITLE = "The Forces and Couples Acting on Two Nearly Touching Spheres +in Low-{Reynolds}-Number Flow", + JOURNAL = "Z. Ang. Math. Phys.", + YEAR = 1984, VOLUME = 35, PAGES = "634-641", + COMMENT = {Extends previous result from linear term to +O$\epsilon$ in $\epsilon$. "Otherwise the only new principle in the +calculation is the handling of long algebraic expressions, which was +accomplished by using the computer algebra systems {CAMAL} and {REDUCE}."}} + +@ARTICLE{Kadlecsik:88, + AUTHOR = "J. Kadlecsik", + TITLE = "New Approaches to the Axisymmetric Vacuum", + JOURNAL = "Zeitschrift {f\"{u}r} Physik C. Particles and Fields", + YEAR = 1988, VOLUME = 41, PAGES = "265-269"} + +@TECHREPORT{Kadlecsik:92, + AUTHOR = "Jo{\'o}zsef Kadlecsik", + TITLE = "Tensor Manipulation Package for General Relativity Calculations", + INSTITUTION = "Central Research Institute for Physics, Budapest", + YEAR = 1992, TYPE = "Preprint", NUMBER = "KFKI-1992-05/B+M", + ABSTRACT = {An experimental computer program is presented, which manipulates +tensor expressions symbolically in general relativity calculations.}} + +@ARTICLE{Kagan:85, + AUTHOR = "Y. Y. Kagan and L. Knopoff", + TITLE = "The First-Order Statistical Moment of the Seismic Moment Tensor", + JOURNAL = "Geophys. J. R. Astron. Soc.", + YEAR = 1985, VOLUME = 81, PAGES = "429-444"} + +@ARTICLE{Kagan:88, + AUTHOR = "Y. Y. Kagan", + TITLE = "Static Sources of Elastic Deformation in a Homogeneous +Half-Space", + JOURNAL = "J. Geophys. Res.", + YEAR = 1988, VOLUME = 93, NUMBER = "B9", PAGES = "10,560-10,574", + MONTH = "September"} + +@TECHREPORT{Kahn:69, + AUTHOR = "M. E. Kahn", + TITLE = "The Near-Minimum-Time Control of Open Loop Articulated +Kinematic Chains", + INSTITUTION = "Stanford University, Computer Science Dept.", + YEAR = 1969, TYPE = "Report", NUMBER = "AIM-106"} + +@TECHREPORT{Kamal:81, + AUTHOR = "A. N. Kamal and J. Kodaira and T. Muta", + TITLE = "Gluon Jets From Heavy Paraquarkonium", + INSTITUTION = "University of Alberta, Canada and Stanford +University, California and Fermi National Accelerator +Laboratory, Illinois", + YEAR = 1981, NUMBER = "SLAC-PUB-2725", MONTH = "April"} + +@TECHREPORT{Kamel:69, + AUTHOR = "A. A. Kamel", + TITLE = "Perturbation Method in the Theory of Non-Linear Oscillations", + INSTITUTION = "Stanford University, Dept. of Aeronautics +and Astronautics", YEAR = 1969, TYPE = "Report"} + +@TECHREPORT{Kamel:69a, + AUTHOR = "A. A. Kamel", + TITLE = "Perturbation Theory Based on {Lie} Transforms and Its +Application to the Stability of Motion Near {Sun}-Perturbed +{Earth-Moon} Triangular Libration Points", + INSTITUTION = "Stanford University, Dept. of Aeronautics and +Astronautics", YEAR = 1969, TYPE = "Report", NUMBER = "391"} + +@INPROCEEDINGS{Kamel:78, + AUTHOR = "A. A. Kamel", + TITLE = "Synchronous Satellite Ephemeris Due to Earth's +Triaxiality and Luni-Solar Effects", + YEAR = 1978, MONTH = "August", + BOOKTITLE = "{AIAA/AAS} Astrodynamics Conference, +Palo Alto, CA", + COMMENT = {Synchronous satellite ephemeris is developed in terms of +non-singular orbital elements.}} + +@ARTICLE{Kanada:81, + AUTHOR = "Yasumasa Kanada and Tateaki Sasaki", + TITLE = "{LISP-based} {big-float} system is not slow", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1981, VOLUME = 15, NUMBER = 2, PAGES = "13-19", MONTH = "May"} + +@TECHREPORT{Kanada:75, + AUTHOR = "Y. Kanada", + TITLE = "Implementation of {HLISP} and Algebraic Manipulation +Language {REDUCE} 2", + INSTITUTION = "University of Tokyo Information Science Lab", + YEAR = 1975, TYPE = "Report", NUMBER = "75-01"} + +@ARTICLE{Kaneko:89, + AUTHOR = "Toshiaki Kaneko and Setsuya Kawabata", + TITLE = "A Preprocessor for {Fortran} Source Code Produced by {REDUCE}", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1989, VOLUME = 55, NUMBER = 2, PAGES = "141-147", + MONTH = "September", PUBLISHER = "North Holland Publishing Company"} + +@ARTICLE{Kaps:85, + AUTHOR = "P. Kaps and S. W. H. Poon and T. D. Bui", + TITLE = "Rosenbrock Methods for Stiff {ODEs}: A Comparison of {Richardson} +Extrapolation and Embedding Techniques", + JOURNAL = "Computing", + YEAR = 1985, VOLUME = 34, PAGES = "17-40", + COMMENT = {Reference to {REDUCE} but not in text.}} + +@INPROCEEDINGS{Karr:85, + AUTHOR = "Michael Karr", + TITLE = "Canonical Form for Rational Exponential Expressions", + BOOKTITLE = "Proc. {EUROCAL} 1985, Lecture Notes +in Computer Science", YEAR = 1985, VOLUME = 204, PAGES = "585-594", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Katsura:85, + AUTHOR = "Shigetoshi Katsura", + TITLE = "Application of the Formula Manipulating System to Statistical + Mechanics", YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "155-180"} + +@PHDTHESIS{Kauffman:73, + AUTHOR = "S. K. Kauffman", + TITLE = "Ortho-Positronium Annihilation: Steps Toward Computing +the First Order Radiative Corrections", + SCHOOL = "California Institute of Technology", + YEAR = 1973} + +@INPROCEEDINGS{Kazasov:87, + AUTHOR = "C. Kazasov", + TITLE = "Laplace Transformations in {REDUCE} 3", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "132-133", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Keady:85, + AUTHOR = "Grant Keady", + TITLE = "The Power Concavity of Solutions of Some Semilinear Elliptic +{Boundary-Value} Problems", + JOURNAL = "Bull. Austral. Math. Soc.", + YEAR = 1985, VOLUME = 31, PAGES = "181-184"} + +@ARTICLE{Keener:83, + AUTHOR = "James P. Keener", + TITLE = "Oscillatory coexistence in the {chemostat:} a codimension two +unfolding", + JOURNAL = "{SIAM} J. Appl. Math.", + YEAR = 1983, VOLUME = 43, NUMBER = 5, PAGES = "1005-1018"} + +@ARTICLE{Keener:85, + AUTHOR = "James P. Keener", + TITLE = "Oscillatory coexistence in a food chain model with competing +predators", + JOURNAL = "J. Math. Biology", + YEAR = 1985, VOLUME = 22, PAGES = "123-135"} + +@ARTICLE{Keener:89, + AUTHOR = "James P. Keener", + TITLE = "Knotted scroll wave filaments in excitable media", + JOURNAL = "Physica D 34", + YEAR = 1989, PAGES = "378-390"} + +@ARTICLE{Keener:90, + AUTHOR = "James P. Keener", + TITLE = "Knotted vortex filaments in an ideal fluid", + JOURNAL = "J. Fluid Mech.", + YEAR = 1990, VOLUME = 211, PAGES = "629-651"} + +@ARTICLE{Kendall:88, + AUTHOR = "W. S. Kendall", + TITLE = "Symbolic Computation and the Diffusion of Shapes of Triads", + JOURNAL = "Adv. Appl. Prob.", + YEAR = 1988, VOLUME = 20, PAGES = "775-797"} + +@TECHREPORT{Kendall:89, + AUTHOR = "W. S. Kendall", + TITLE = "The Diffusion of {Euclidean} Shape", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1989, + TYPE = "Research Report", NUMBER = 161} + +@TECHREPORT{Kendall:89a, + AUTHOR = "W. S. Kendall", + TITLE = "Probability, Convexity, and Harmonic Maps with Small Image I: +Uniqueness and Fine Existence", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1989, + TYPE = "Research Report", NUMBER = 162} + +@ARTICLE{Kendall:90, + AUTHOR = "W. S. Kendall", + TITLE = "Computer Algebra and Stochastic Calculus", + JOURNAL = "Notices A.M.S.", + YEAR = 1990, VOLUME = 37, PAGES = "1254-1256"} + +@TECHREPORT{Kendall:91, + AUTHOR = "Wilfred S. Kendall", + TITLE = "Computer Algebra and Stochastic Calculus", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1991, + TYPE = "Research Report", NUMBER = 203} + +@TECHREPORT{Kendall:91a, + AUTHOR = "Wilfred S. Kendall", + TITLE = "Symbolic {It\^{o}} Calculus: An Introduction", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1991, + TYPE = "Research Report", NUMBER = 217} + ABSTRACT = {The ito procedures are an implementation of stochastic calculus +for the computer algebra package {REDUCE}. In this paper it is explained +how the implementation of ito grows naturally out of the formulation of +stochastic calculus using modules of stochastic differentials. Two examples +are given of ito in action: a simple example concerning various exponential +martingales and a more involved example concerning the escape rate of the +Bessel process of dimension exceeding 2. A basic subset of the ito +procedures is listed in six appendices; details are given of how to obtain +the full set from the author.}} + +@TECHREPORT{Kendall:93a, + AUTHOR = "Wilfred S. Kendall", + TITLE = "Probability, Convexity, and Harmonic Maps II: Smoothness via +Probabilistic Gradient Inequalities", + INSTITUTION = "University of Warwick, Dept. of Statistics", YEAR = 1993, + MONTH = "October", TYPE = "Research Report", NUMBER = 260, + ABSTRACT = {A conformal change of metric is used to construct a coupling +of two time-changed Riemannian Brownian motions, such that there is an +upper bound on the prabability of no coupling before either process leaves +a small geodesic ball, with the bound being linear in the distance between +the two starting points. This coupling is a more geometric (and +probabilistically less technical) alternative to that introduced by +Cranston (1991). Together with some modifications it is used to provide a +probabilistic approach to the regularity of harmonic maps, thus completing +the probabilistic construction of solutions to small-image harmonic map +Dirichlet problems described in Kendall (1990). The approach includes a +mild generalization to the case of harmonic maps defined using +non-Riemannian connections in the target manifold and smooth strictly +elliptic second-order differential operators in the domain.}} + +@INPROCEEDINGS{Kerner:75, + AUTHOR = "W. Kerner and R. C. Grimm", + TITLE = "{MHD} Spectra for {Tokamaks} with Non-circular Cross Sections", + YEAR = 1975, + BOOKTITLE = "Proc. Seventh Conference on +Numerical Simulation of Plasmas, Courant Institute, {NYU}"} + +@ARTICLE{Kersten:83, + AUTHOR = "P. H. M. Kersten", + TITLE = "Infinitesimal Symmetries and Conserved Currents for Nonlinear +{Dirac} Equation", + JOURNAL = "J. Math. Phys.", + YEAR = 1983, VOLUME = 24, PAGES = "2374-2376", + COMMENT = {Harrison-Estabrook and computer algebra, in {REDUCE}. Very like +{EXCALC} but predates it.}} + +@ARTICLE{Kersten:84, + AUTHOR = "P. Kersten and R. Martini", + TITLE = "The Harmonic Map and Killing Fields for Self-Dual {SU(3)} +{Yang-Mills} Equations", + JOURNAL = "J. Phys. A", + YEAR = 1984, VOLUME = 17, PAGES = "L227-L230", + COMMENT = {%"{\ldots}and the determination of the general solution of the +killing fields have been achieved by symbolic computations in a semi-automatic +way using software developed in the symbolic language {REDUCE}{\ldots}"}} + +@ARTICLE{Kersten:86, + AUTHOR = "P. H. M. Kersten", + TITLE = "Creating and Annihilating {Lie-B\"acklund} Transformations +of the {Federbush} Model", + JOURNAL = "J. Math. Phys.", + YEAR = 1986, VOLUME = 27, PAGES = "1139-1144", + COMMENT = {"We want to stress that all computations have been worked out on +a {DEC-20} computer using {REDUCE} and a software package to do these +calculations." Lie algebra and Gragert's package.}} + +@ARTICLE{Kersten:86a, + AUTHOR = "P. H. M. Kersten and H. M. M. Ten Eikelder", + TITLE = "Infinite Hierarchies of t-independent and t-dependent +Conserved Functionals of the {Federbush} Model", + JOURNAL = "J. Math. Phys.", + YEAR = 1986, VOLUME = 27, PAGES = "2140-2145", + COMMENT = {"We want to stress that all computations have been worked out on +a {DEC-20} computer using {REDUCE} and a software package to do these +calculations."}} + +@ARTICLE{Kersten:86b, + AUTHOR = "P. H. M. Kersten and H. M. M. Ten Eikelder", + TITLE = "An Infinite Number of Infinite Hierarchies of Conserved +Quantities of the {Federbush} Model", + JOURNAL = "J. Math. Phys.", + YEAR = 1986, VOLUME = 27, PAGES = "2791-2796"} + +@ARTICLE{Killalea:80, + AUTHOR = "M. K. Killalea and B. J. McCoy", + TITLE = "Concentration Distribution and Spatial Moments of +Moving Macromolecules Undergoing Isomerization", + JOURNAL = "Biopolymers", + YEAR = 1980, VOLUME = 19, PAGES = "1875-1886"} + +@TECHREPORT{Kinoshita:72, + AUTHOR = "T. Kinoshita and P. Cvitanovic", + TITLE = "Sixth Order Radiative Corrections to the Electron Magnetic Moment", + INSTITUTION = "Cornell Lab. for Nuclear Studies", YEAR = 1972, + TYPE = "Report", NUMBER = "CLNS-197", MONTH = "October"} + +@TECHREPORT{Kinoshita:73, + AUTHOR = "T. Kinoshita and P. Cvitanovic", + TITLE = "Feynman-{Dyson} Rules in Parametric Space", + INSTITUTION = "Cornell Lab. for Nuclear Studies", YEAR = 1973, + TYPE = "Report", NUMBER = "CLNS-209", MONTH = "January"} + +@ARTICLE{Kitatani:86, + AUTHOR = "H. Kitatani and S. Miyashita and M. Suzuki", + TITLE = "Reentrant Phenomena in Some {Ising} Spin Systems - Rigorous +Results and Effects of an External Field", + JOURNAL = "J. Phys. S. Japan", + YEAR = 1986, VOLUME = 55, NUMBER = 3, PAGES = "865-876", + COMMENT = {{REDUCE} used to calculate formula before numerical +calculation.}} + +@ARTICLE{Klimov:93, + AUTHOR = "D. M. Klimov and V. V. Leonov and V. M. Rudenko", + TITLE = "The Study of Motion for a Gyroscope with Gimbal Suspension: +Obtaining the Highest Approximations for a Drift of Magnus", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "73-78", MONTH = "January", + COMMENT = {Here we give a solution to the classic problem of the applied +mechanics of the gyroscope. The problem is reduced to using the computer +algebra system {REDUCE}. We show that symbolic computation is very +convenient for applied mechanics.}} + +@TECHREPORT{Kobayashi:84, + AUTHOR = "Hidestune Kobayashi", + TITLE = "Weierstrass Points on a Curve, $X^{7}_{0}+X^{7}_{1} ++X^{7}_{2}=0$", + INSTITUTION = "Research Institute of Science and Technology, Nihon +University", YEAR = 1984, TYPE = "Preprint", NUMBER = 28, MONTH = "March"} + +@INPROCEEDINGS{Kobayashi:88, + AUTHOR = "H. Kobayashi and S. Moritsugu and R. W. Hogan", + TITLE = "Solving Systems of Algebraic Equations", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "139-149"} + +@INPROCEEDINGS{Kodaira:85, + AUTHOR = "Hiroshi Kodaira and Hiroshi Toshima", + TITLE = "Gini Coefficient of Wealth in Life Cycle Model", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "119-151"} + +@ARTICLE{Koh:82, + AUTHOR = "I. G. Koh and Y. D. Kim and Y. J. Park and C. H. Kim and +Y. S. Kim", + TITLE = "Complete Set of {SU(5)} Monopole Solution", + JOURNAL = "J. Math. Phys.", + YEAR = 1982, VOLUME = 23, PAGES = "1210-1212", + COMMENT = {Calculation checked by {REDUCE} after hand calculation.}} + +@ARTICLE{Koelbig:81, + AUTHOR = "K. S. K{\"o}lbig and F. Schwarz", + TITLE = "On Positive Function Series", + JOURNAL = "Computing", + YEAR = 1981, VOLUME = 27, PAGES = "319-337", + COMMENT = {{REDUCE} for algebra on constraints on a functional form and +Jacobi polynomials.}} + +@ARTICLE{Koelbig:81b, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "A Program for Computing the Conical functions of the +First Kind ${P}^{m}_{-1/2+i\tau}(x)$ for $m = 0$ and $m = 1$", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1981, VOLUME = 23, PAGES = "51-61", + PUBLISHER = "North Holland Publishing Company"} + +@ARTICLE{Koelbig:82, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "Closed Expressions for $\int_{0}^{1} t^{-1} $log$^{n-1}t\, + $log$^{p}(1 - t) dt$", + JOURNAL = "Math. Comp.", + YEAR = 1982, VOLUME = 39, NUMBER = 160, PAGES = "647-654", + MONTH = "October", + COMMENT = {Closed form of integral for easy calculation. Used {REDUCE} for +manipulations. This class includes dilog, Spence functions etc. +Remarks that {REDUCE} is easier than {FORTRAN}.}} + +@ARTICLE{Koelbig:82a, + AUTHOR = "K. S. K{\"o}lbig and W. R{\"u}hl", + TITLE = "Complex Zeros of the Partition Function for +Two-Dimensional {U(N)} Lattice Gauge Theories", + JOURNAL = "Z. Phys. C - Particles and Fields", + YEAR = 1982, VOLUME = 12, PAGES = "135-143", + COMMENT = {The Complex Zeros of the Partition Function for Two-Dimensional +U(N) Lattice Gauge Theories.}} + +@ARTICLE{Koelbig:83, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "On the Integral $\int_{0}^{\pi/2} $log$^{n}$cos$\,x\,$ +log$^{p}$sin$\,x\,dx$", + JOURNAL = "Math. Comp.", + MONTH = "April", + YEAR = 1983, VOLUME = 40, PAGES = "565-570", + COMMENT = {A formula is derived for the integral in the title which allows +easy evaluation by formula manipulation on a computer.}} + +@ARTICLE{Koelbig:83a, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "On the Integral $\int_{0}^{\infty} e^{-\mu t} t^{\nu -1} + $log$^{m} t dt$", + JOURNAL = "Math. Comp.", + YEAR = 1983, VOLUME = 41, PAGES = "171-182", + COMMENT = {A recurrence relation is given for the integral in the title.}} + +@ARTICLE{Koelbig:84, + AUTHOR = "K. S. K{\"o}lbig and B. Schorr", + TITLE = "Asymptotic Expansions for the {Landau} Density and +Distribution Function", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1984, VOLUME = 32, PAGES = "121-131"} + +@ARTICLE{Koelbig:84a, + AUTHOR = "K. S. K{\"o}lbig and B. Schorr", + TITLE = "A Program Package for the {Landau} Distribution", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1984, VOLUME = 31, PAGES = "97-111"} + +@TECHREPORT{Koelbig:84b, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "Some Problems Involving Special Functions +Arising From Physics at {CERN}", + INSTITUTION = "CERN, Data Handling Division", + YEAR = 1984, NUMBER = "DD 84-14", MONTH = "September"} + +@TECHREPORT{Koelbig:85, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "On the Integral $\int_{0}^{1} x^{\nu -1} (1 - x)^{-\lambda} + $ln$^{m} x dx$", + INSTITUTION = "CERN, Data Handling Division", + YEAR = 1985, NUMBER = "DD/85/18", MONTH = "September"} + +@ARTICLE{Koelbig:85a, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "Explicit Evaluation of Certain Definite Integrals Involving +Powers of Logarithms", + JOURNAL = "J. Symbolic Computation", + YEAR = 1985, VOLUME = 1, NUMBER = 1, PAGES = "109-114", MONTH = "March"} + +@ARTICLE{Koelbig:86, + AUTHOR = "K. S. K{\"o}lbig", + TITLE = "On the Integral $\int_{0}^{\infty} x^{\nu -1} + (1 + \beta x)^{-\lambda} $ln$^{m} x dx$", + JOURNAL = "Journal of Comp. and Appl. Math.", + YEAR = 1986, VOLUME = 14, PAGES = "319-344"} + +@TECHREPORT{Koepf:94, + AUTHOR = "Wolfram Koepf and Dieter Schmersau", + TITLE = "Spaces of Functions Satisfying Simple Differential Equations", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1994, MONTH = "March", TYPE = "Preprint", NUMBER = "TR 94-2"} + +@TECHREPORT{Koepf:94a, + AUTHOR = "Wolfram Koepf", + TITLE = "Algebraische Darstellung transzendenter Funktionen (in {German})", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1994, MONTH = "October", TYPE = "Preprint", NUMBER = "SC 94-24"} + +@TECHREPORT{Koepf:94b, + AUTHOR = "Wolfram Koepf", + TITLE = "Algorithms for the Indefinite and Definite Summation", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1994, MONTH = "December", TYPE = "Preprint", NUMBER = "SC 94-33"} + +@ARTICLE{Koepf:95, + AUTHOR = "Wolfram Koepf", + TITLE = "{REDUCE} package for the Indefinite and Definite Summation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1995, VOLUME = 29, NUMBER = 1, PAGES = "14-30", MONTH = "January", +Abstract ={The {REDUCE} package {ZEILBERG} is a careful implementation of +the Gosper and Zeilberger algorithms for indefinite, and definite +summation of hypergeometric terms respectively. An expression $a_k$ is +called a hypergeometric term (or closed form) if $a_k/a_{k-1}$ is a +rational function with respect to $k$. Typical hypergeometric terms are +ratios of products of powers, factorial, Gamma function terms, binomial +coefficients, and shifted factorials (Pochhammer symbols) that are +integer-linear in their arguments. The package covers further extensions +of both Gosper's and Zeilberger's algorithms.}} + +@TECHREPORT{Koepf:95a, + AUTHOR = "Wolfram Koepf", + TITLE = "Identities for families of orthogonal polynomials and special +functions", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1995, MONTH = "January", TYPE = "Preprint", NUMBER = "SC 95-1", + ABSTRACT = {In this article we present new results for families of +orthogonal polynomials and special functions, that are determined by +algorithmical approaches. + +In the first section, we present new results, especially for discrete +families of orthogonal polynomials, obtained by an application of the +celebrated Zeilberger algorithm. + +Next, we present algorithms for holonomic families $f(n,x)$ of special +functions which possess a derivative rule. We call those families +admissible. A family $f(n,x)$ is holonomic if it satisfies a holonomic +recurrence equation with respect to n, and a holonomic differential +equation with respect to x, i.e. linear homogeneous equations with +polynomial coefficients. + +The rather rigid property of admissibility has many interesting +consequences, that can be used to generate and verify identities for these +functions by linear algebra techniques. On the other hand, many families +of special functions, in particular families of orthogonal polynomials, are +admissible. We moreover present a method that generates the derivative +rule from the holonomic representation of a holonomic family. + +As examples, we find new identities for the Jacobi polynomials and for the +Whittaker functions, and for families of discrete orthogonal polynomials by +the given approach. + +Finally, we present representations for the parameter derivatives of the +Gegenbauer and the generalized Laguerre polynomials.}} + +@ARTICLE{Koike:92, + AUTHOR = "F. Koike", + TITLE = "Explicit formulae of angular momentum coupling coefficients", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1992, VOLUME = 72, NUMBERS = "2 and 3", PAGES = "154-164", + MONTH = "November", + COMMENT = {A program has been developed to generate algebraic formulae of +the coupling coefficients of angular momenta. The algebraic programming +system {REDUCE} version 3.3 is used for programming. The program +consists of several {REDUCE} prefix operators. They carry out symbolic +reductions of Clebsch-Gordan coefficients. Racah coefficients, +X-coefficients, and related coefficients. Both variables and values of +angular momentum can be their arguments. The program allows one to use +these operators in the same way as the {REDUCE} built-in operators.}} + +@ARTICLE{Kolar:90, + AUTHOR = "M. Kol{\'a}\u{r} and M. K. Ali", + TITLE = "Trace maps associated with general {two-letter} substitution +rules", + JOURNAL = "Physical Review {A}", + YEAR = 1990, VOLUME = 42, NUMBER = 12, PAGES = "7112-7124", + MONTH = "December", + ABSTRACT = {Spectral properties, as determined by trace maps, of the +one-dimensional chains (layered structures) constructed according to +general two-letter substitution rules are investigated. In all trace maps +thus obtained an important role is played by the quantity +$I=x^{2}+y^{2}+z^{2}-xyz-4$ However, only a very small fraction of all +such trace maps are similar to the Fibonacci golden-mean trace map in that +I is their invariant. In addition to the known case of the precious-mean +lattices (precious means are ratios of the form +$^{1}_{2}[m+(m^{2}+4)^{1/2}]$, m being any positive integer; m=1 gives the +golden mean), we have identified two new large clases of substitution +rules that give trace maps with invariant I. One of them is a superset of +the precious-mean lattices. All other cases represent a vast assortment +of different trace maps (and thus the potential for various hitherto +unexplored spectral properties) with a unifying feature that the set I=0 +plays the role of an attractor in the trace space. In most (but not all) +cases, two chains with identical trace maps (and thus identical spectra) +are locally isomorphic. Generally, local isomorphism equivalence classes +seem to be subsets of identical spectrum equivalence classes.}} + +@TECHREPORT{Kornyak:87, + AUTHOR = "V. V. Kornyak and R. N. Fedorova", + TITLE = "A {REDUCE} Program to Calculate Determining Equations of +{Lie-Baecklund} Symmetries of Differential Equations", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1987, NUMBER = "P11-87-19"} + +@ARTICLE{Kotorynski:86, + AUTHOR = "W. P. Kotorynski", + TITLE = "Steady Laminar Flow Through a Twisted Pipe of Elliptical +Cross-Section", + JOURNAL = "Computers and Fluids", + YEAR = 1986, VOLUME = 14, PAGES = "433-444", + COMMENT = {Used {REDUCE} to perform the calculations for steady flow through +twisted pipes, but who also remarked that the techniques he developed +for this problem are applicable to a variety of other pipe flow tasks.}} + +@ARTICLE{Krack:82, + AUTHOR = "K. Krack", + TITLE = "Rechnerunterst{\"u}tzte {Entwicklung} der {Mittelbreitenformeln} +und Absch{\"a}tzung ihrer ellipsoidischen {Anteile} zur L{\"o}sung der +zweiten geod{\"a}tischen {Hauptaufgabe} auf dem {Rotationsellipsoid}", + JOURNAL = "Z. Vermessungswes.", + YEAR = 1982, VOLUME = 107, PAGES = "502-513", + COMMENT = {(In German) Used {REDUCE} to develop the Gauss mid-latitude +formulae for inverse positioning to the 7th order (Geodesy).}} + +@PHDTHESIS{Kraus:73, + AUTHOR = "J. Kraus", + TITLE = "Delbr{\"u}ckstreuung und Pr{\"u}fung der +Quantenelektrodynamik", + SCHOOL = "Ludwig-Maximilians-Universit{\"a}t zu M{\"u}nchen", + YEAR = 1973} + +@ARTICLE{Kredel:88, + AUTHOR = "Heinz Kredel", + TITLE = "Admissible termorderings used in Computer Algebra Systems", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1988, VOLUME = 22, NUMBER = 1, PAGES = "28-31", MONTH = "January"} + +@ARTICLE{Kruse:83, + AUTHOR = "Hans-Guenther Kruse and Karin Ohlsen", + TITLE = "About the Realization of an Extended, but Really Interactive +{REDUCE} by Integration of a Small Editing and Executing System", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "21-25", MONTH = "February"} + +@TECHREPORT{Kryukov, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", + TITLE = "Usage of {REDUCE} for Computations of Group-Theoretical Weight of +{Feynman} Diagrams in Non-Abelian Gauge Theories", + INSTITUTION = "Institute of Nuclear Physics, Moscow, USSR", YEAR = "TBD"} + +@ARTICLE{Kryukov:84, + AUTHOR = "A. P. Kryukov", + TITLE = "An Antitranslator of the {RLISP} Language", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1984, VOLUME = 18, NUMBER = 3, PAGES = "12-15", MONTH = "August"} + +@ARTICLE{Kryukov:85, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", + TITLE = "Dynamic-Debugging System for the {REDUCE} Programs", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "34-37", MONTH = "May"} + +@ARTICLE{Kryukov:85a, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", + TITLE = "Interactive {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "43-45", MONTH = "August"} + +@TECHREPORT{Kryukov:87, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and V. A. Rostovtsev", + TITLE = "Pattern Compilation in {REDUCE}", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1987, NUMBER = "P11-87-302"} + +@INPROCEEDINGS{Kryukov:87a, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", + TITLE = "{CTS} - Algebraic Debugging System for {REDUCE} Programs", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "233-243", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Kryukov:88, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and V. A. Rostovtsev", + TITLE = "New Programming Tools for Computing Substitution +Rules in {REDUCE} System", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1988, NUMBER = "P11-88-402", + COMMENT = {New programming tools allowing to compile patterns in +{REDUCE} system are described. A guide for using +these tools and examples of their working are presented.}} + +@ARTICLE{Kryukov:88a, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov", + TITLE = "Program {``COLOR''} for Computing the Group-Theoretic Weight +of {Feynman} Diagrams in {Non-Abelian} Gauge Theories", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1988, VOLUME = 48, NUMBER = 2, PAGES = "327-334", MONTH = "February"} + +@TECHREPORT{Kryukov:88b, + AUTHOR = "A. P. Kryukov and D. A. Slavnov", + TITLE = "The Role of the $gg \rightarrow c\overline{c}g$ Process in the +Cross Section of Production of Charmed Particles (in {Russian})", + INSTITUTION = "Moscow State University", + YEAR = 1988, NUMBER = "88-49/70", TYPE = "Preprint"} + +@BOOK{Kryukov:91, + AUTHOR = "A. P. Kryukov and A. Ya. Rodionov and A. Yu. Taranov and +E. Shablygin", + TITLE = "Programming in R-Lisp", + PUBLISHER = "Radio and Connective Publishers, Moscow", YEAR = 1991, + ABSTRACT = {Various Lisp dialects become more and more popular as +high-level programming languages. In this book basic Lisp concepts, its +data structures and build in functions are introduced using R-Lisp. +R-Lisp is the implementation language of a famous REDUCE computer algebra +system. All concepts are illustrated by simple but by no means trivial +programming examples. The description of compiler and full function +reference are included. The book will be interesting for beginners as +well as Lisp programmers. In Russian}} + +@TECHREPORT{Kuppers:71, + AUTHOR = "G. Kuppers and D. Pfirsch and H. Tasso", + TITLE = "{M.H.D.} - Stability of Axisymmetric Plasmas", + INSTITUTION = "Max-Planck-Institut fuer Plasmaphysik", + YEAR = 1971, TYPE = "Report", NUMBER = "CN -28/F-14"} + +@ARTICLE{Lambin:84, + AUTHOR = "P. Lambin and J. P. Vigneron", + TITLE = "Computation of Crystal {Green's} Functions in the Complex-Energy +Plane with the Use of the Analytical Tetrahedron Method", + JOURNAL = "Phys. Rev. B", + YEAR = 1984, VOLUME = 29, NUMBER = 6, PAGES = "3430-3437", + COMMENT = {Crystallography, {REDUCE}, quantum theory.}} + +@TECHREPORT{Lang:79, + AUTHOR = "C. B. Lang and W. Porod", + TITLE = "Symmetry Breaking and $\pi$ {K} Amplitudes in the Unphysical +Region", + INSTITUTION = "Institut f{\"u}r Theor. Physik, Univ. Graz", + YEAR = 1979, TYPE = "Report", NUMBER = "UNIGRAZ-UTP 08/79", + ABSTRACT = {We apply two different methods of analytic continuation +(fixed-t and hyperbolic dispersion relations with discrepancy) to +determine the expansion parameters of the pi K amplitudes in the +unphysical region near the symmetry point.}, + COMMENT = {To be published in Phys. Rev. D, September, 1979.}} + +@TECHREPORT{Laursen:79, + AUTHOR = "M. L. Laursen and M. A. Samuel", + TITLE = "The n-Bubble Diagram Contribution to the g-2 of the Electron - +{Mathematical} Structure of the Analytical Expression", + INSTITUTION = "Oklahoma State Univ. Quantum Theoretical Research Group", + YEAR = 1979, TYPE = "Research Note", NUMBER = "96", + ABSTRACT = {We obtain an exact integrated expression for the contribution +of the mass-independent n-bubble diagram to the leptonic g-2.}} + +@TECHREPORT{Laursen:80, + AUTHOR = "Morten L. Laursen and Mark A. Samuel", + TITLE = "Borel Transform Technique and the {n-Bubble} Diagram +Contribution to the Lepton Anomaly", + INSTITUTION = "Oklahoma State Univ. Quantum Theoretical Research Group", + YEAR = 1980, TYPE = "Research Note", NUMBER = 10, MONTH = "August", + ABSTRACT = {By using the {Borel} transform technique we calculate +analytically the muon anomaly from the mass-dependent n-bubble diagram in the +limit where the mass ratio is large.}} + +@ARTICLE{Laursen:81, + AUTHOR = "M. L. Laursen and M. A. Samuel", + TITLE = "The n-bubble Diagram Contribution to g-2", + JOURNAL = "J. Maths. Phys.", + YEAR = 1981, VOLUME = 22, PAGES = "1114-1126", + COMMENT = {Exact integration for contribution to mass indep. {n-bubble} +diagram to {leptonic g-2}. {REDUCE} used to calculate explicitly to {n=13}, +involves summing series and rational coefficients.}} + +@ARTICLE{Lecourtier:85, + AUTHOR = "Y. Lecourtier and A. Raksanyi", + TITLE = "Algebraic Manipulation Routines for Testing Structural Properties", + JOURNAL = "IFAC Identification and System Parameter Estimation", + YEAR = 1985, PAGES = "543-549"} + +@ARTICLE{Lee:85, + AUTHOR = "H-C Lee and M. S. Milgram", + TITLE = "On the Axial Gauge: Ward Identities and the Separation of +Infrared and Ultraviolet Singularities by Analytical Regularization", + JOURNAL = "J. Math. Phys.", + YEAR = 1985, VOLUME = 26, PAGES = "1793-1804", + COMMENT = {Yang-Mills theories on the axial gauge. Uses {SCHOONSCHIP} and +{REDUCE}.}} + +@ARTICLE{Leler:85, + AUTHOR = "Wm Leler and Neil Soiffer", + TITLE = "An Interactive Graphical Interface for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "17-23", MONTH = "August"} + +@ARTICLE{Lepage:83, + AUTHOR = "G. P. Lepage and P. B. Mackenzie and K. H. Streng and +P. M. Zernas", + TITLE = "Multiphoton Decays of Positronium", + JOURNAL = "Phys. Rev. A", + YEAR = 1983, VOLUME = 28, PAGES = "3090-3091", + COMMENT = {Same as Adkins and Brown (1983) but independent of it.}} + +@INPROCEEDINGS{Levi:70, + AUTHOR = "I. Levi and N. Hoff", + TITLE = "Non-Symmetric Creep Buckling of Circular +Cylindrical Shells in Axial Compression", + YEAR = 1970, MONTH = "August", + BOOKTITLE = "Proc. Intern. Symp. in Creep Effect in Structures, +Gotenburg, Sweden"} + +@INPROCEEDINGS{Levi:71, + AUTHOR = "I. M. Levi", + TITLE = "Symbolic Algebra by Computer - Applications to +Structural Mechanics", + YEAR = 1971, MONTH = "April", + BOOKTITLE = "{AIAA/ASME} 12th Structures, Structural Dynamics +and Materials Conference, Anaheim, California"} + +@ARTICLE{Liebermann:75, + AUTHOR = "R. Liebermann", + TITLE = "Traces of High Energy Processes in Strong Magnetic Fields", + JOURNAL = "J. Comp. Phys.", + YEAR = 1975} + +@ARTICLE{Liska:84, + AUTHOR = "R. Liska", + TITLE = "Program for Stability and Accuracy Analysis of +Finite Difference Methods", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1984, VOLUME = 34, PAGES = "175-186"} + +@INPROCEEDINGS{Liska:87, + AUTHOR = "R. Liska and D. Drska", + TITLE = "Evaluation of Plasma Fluid Equations Collision Integrals Using +{REDUCE}", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = 178, + PUBLISHER = "Springer-Verlag"} + +@InProceedings{Liska90, + author = "R. Liska and L. Drska", + title = "{FIDE}: A {REDUCE} package for automation of {FI}nite + difference method for solving {pDE}", + booktitle = "Proceedings of the 1990 International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "169-176", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@INPROCEEDINGS{Liska:91, + AUTHOR = "Richard Liska and Michail Yu. Shashkov", + TITLE = "Algorithms for Difference Schemes Construction on Non-orthogonal +Logically Rectangular Meshes", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", + PUBLISHER = "ACM Press", ADDRESS = "Maryland", PAGES = "419-426", + YEAR = 1991, + ABSTRACT = {The paper deals with the formalization of the basic operator +method for construction of difference schemes for the numerical solving +of partial differential equations. The strength of the basic operator +method lies on the fact that it produces fully conservative difference +schemes. The difference mesh can be non-orthogonal but has to be logically +orthogonal. Algorithms for working with grid functions and grid operators +in symbolic form which are necessary in the basic operator method are +described. The algorithms have been implemented in the computer algebra +system REDUCE.}} + +@ARTICLE{Lloyd:90, + AUTHOR = "N. G. Lloyd and J. M. Pearson", + TITLE = "{REDUCE} and the Bifurcation of Limit Cycles", + JOURNAL = "J. Symbolic Computation", + YEAR = 1990, VOLUME = 9, NUMBER = 2, PAGES = "215-224", MONTH = "February"} + +@INPROCEEDINGS{Loe:85, + AUTHOR = "Kia Fock Loe and Noritaka Ohsawa and Eiichi Goto", + TITLE = "Circuit Simulation Code Generation by Computer Algebra", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "87-103"} + +@INPROCEEDINGS{London:74, + AUTHOR = "R. London and D. R. Musser", + TITLE = "The Application of a Symbolic Mathematical System +to Program Verification", + YEAR = 1974, PAGES = "265-273", + BOOKTITLE = "Proc. {ACM} 74"} + +@ARTICLE{Loos:72, + AUTHOR = "R{\"u}diger Loos", + TITLE = "Analytic Treatment of Three Similar {Fredholm} Integral +Equations", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1972, VOLUME = 11, PAGES = "32-40", + ABSTRACT = {A {REDUCE} solution to {SIGSAM} Problem \#1 is presented.}} + +@INPROCEEDINGS{Lottati, + AUTHOR = "Itzhak Lottati and Isaac Elishakoff", + TITLE = "Refined Dynamical Theories of Beams, Plates +and Shells and Their Applications", + BOOKTITLE = "Proc. Euromech-Colloquium 219"} + +@ARTICLE{Louw:86, + AUTHOR = "J. A. Louw and F. Schwarz and W. H. Steeb", + TITLE = "First Integrals and {Yoshida} Analysis of {Nahm}'s Equation", + JOURNAL = "J. Phys. A", + YEAR = 1986, VOLUME = 19, PAGES = "L569-L573", + COMMENT = {Monopole solutions in Yang-Mills theories explicitely given in +special cases. {REDUCE} used for polynomial first integrals and +Kowalewski exponents. An application of spde.}} + +@ARTICLE{Luegger:73, + AUTHOR = "J. Luegger and H. Melenk", + TITLE = "Darstellung und {Bearbeitung} Umfangreicher {LISP-Programme}", + JOURNAL = "Angewandte Informatik", + YEAR = 1973, MONTH = "June", PAGES = "257-263"} + +@TECHREPORT{Luegger:91, + AUTHOR = "Joachim L{\"u}gger and Wolfgang Dalitz", + TITLE = "Verteilung mathematischer {Software} mittels elektronischer +{Netze:} {Die} elektronische {Softwarebibliothek} {eLib}", + INSTITUTION = "Konrad-Zuse-Zentrum {f\"u}r Informationstechnik Berlin", + YEAR = 1991, MONTH = "February", TYPE = "Preprint", NUMBER = "TR 91-2"} + +@TECHREPORT{Lukacs, + AUTHOR = "B. Luk{\'a}cs and Z. Perj{\'e}s and +A. Sebesty{\'e}n and A. Valentini", + TITLE = "Stationary Vacuum Fields with a Conformally Flat +Three-Space, II. Proof of Axial Symmetry", + INSTITUTION = "Central Research Institute for Physics, +Budapest, Hungary", + YEAR = 1982, NUMBER = "KFKI-1982-19"} + +@ARTICLE{Lukaszuk:87, + AUTHOR = "L. L{\'u}kaszuk and D. M. Siemienczuk and L. Szymanowski", + TITLE = "Evaluation of Helicity Amplitudes", + JOURNAL = "Phys. Rev. D", + YEAR = 1987, VOLUME = 35, PAGES = "326-329"} + +@PHDTHESIS{Lux:75, + AUTHOR = "Augustin Lux", + TITLE = "Etude d'un Modele Abstrait pour une Machine {LISP} et de +son Implantation", + SCHOOL = "Universit{\'e} Scientifique et Medicale de Grenoble", + YEAR = 1975, MONTH = "March", + COMMENT = {Thesis presented to Universit{\'e} Scientifique et Medicale de +Grenoble, Institut National Polytechnique de Grenoble.}} + +@BOOK{MacCallum:86, + AUTHOR = "M. A. H. MacCallum", + TITLE = "Dynamical Spacetimes and Numerical Relativity", + PUBLISHER = "Cambridge University Press", YEAR = 1986} + +@TECHREPORT{MacCallum:86a, + AUTHOR = "M. A. H. MacCallum", + TITLE = "Algebraic Computing in Relativity", + INSTITUTION = "Queen Mary College, University of London", + YEAR = 1986, NUMBER = "TAU 86-04"} + +@INPROCEEDINGS{MacCallum:87, + AUTHOR = "M. A. H. MacCallum", + TITLE = "Symbolic Computation in Relativity Theory", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "34-43", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{MacCallum:88, + AUTHOR = "M. A. H. MacCallum", + TITLE = "An Ordinary Differential Equation Solver for {REDUCE}", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "196-205"} + +@ARTICLE{MacCallum:89, + AUTHOR = "Malcolm A. H. MacCallum", + TITLE = "Comments on the performance of algebra systems in general +relativity and a recent paper by {Nielsen} and {Pedersen}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1989, VOLUME = 23, NUMBER = 2, PAGES = "22-25", MONTH = "April"} + +@BOOK{MacCallum:91, + AUTHOR = "Malcolm MacCallum and Francis Wright", + TITLE = "Algebraic Computing with {REDUCE}", + PUBLISHER = "Oxford University Press", YEAR = 1991, + ISBN = "0-19-853444-2, 0-19-853443-4 (paperback)"} + +@ARTICLE{MacCallum:92, + AUTHOR = "M. A. H. MacCallum and S. T. C. Siklos", + TITLE = "Algebraically special hypersurface-homogeneous {Einstein} spaces +in general relativity", + JOURNAL = "Journal of Geometry and Physics", + YEAR = 1992, VOLUME = 8, PAGES = "221-242"} + +@BOOK{MacDonald:94, + AUTHOR = "N. MacDonald", + TITLE = "{REDUCE} for Physics", + PUBLISHER = "Institute of Physics Publishing", + ADDRESS = "Bristol, England", + YEAR = 1994, MONTH = "March", + NOTE = "ISBN 0 7503 0277 1", + COMMENT = {This book provides an introduction to {REDUCE} with the needs +of physicists primarily in mind. Each chapter introduces some aspects of +{REDUCE} and illustrates them with applications from various branches of +physics including mechanics, dynamics, dimensional analysis, quantum +mechanics, plasma physics. Exercises to test understanding are included +throughout. The emphasis is on hands-on working with {REDUCE} as a tool to +tackle real physical problems. The book takes account of changes to +{REDUCE} for Version 3.4. +Students and researchers in the physical sciences and engineering using +{REDUCE} for the first time should find this book useful.}} + +@PHDTHESIS{Mack:73, + AUTHOR = "D. Mack", + TITLE = "Nichtnumerische Verfahren und deren Anwendung +in der Elementarteilchen-Physik", + SCHOOL = "University of Tuebingen", + YEAR = 1973} + +@ARTICLE{Mack:73a, + AUTHOR = "D. Mack and H. Mitter", + TITLE = "Calculation of Electron-Electron-Bremsstrahlung Cross-Sections", + JOURNAL = "Phys. Lett.", + YEAR = 1973, VOLUME = "44A", PAGES = "71-72"} + +@ARTICLE{Maclaren:89, + AUTHOR = "N. M. Maclaren", + TITLE = "The Generation of Sequences of Multiple Independent Sequences +of Pseudorandom Numbers", + JOURNAL = "Applied Statistics {JRSS Series C}", + YEAR = 1989, VOLUME = 38, NUMBERS = 2, PAGES = "351-359"} + +@MASTERSTHESIS{Maguire:81, + AUTHOR = "Gerald Quentin {Maguire Jr.}", + TITLE = "Program Transformation in {REDUCE} Using Rule Sequencing", + SCHOOL = "Department of Computer Science, The University of Utah", + YEAR = 1981, MONTH = "March"} + +@INPROCEEDINGS{Malm:82, + AUTHOR = "Bengt Malm", + TITLE = "A Program in {REDUCE} for Finding Explicit Solutions", + BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes +in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "289-293", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Man:93, + AUTHOR = "Yiu-Kwong Man", + TITLE = "On Computing Closed Forms for Indefinite Summations", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, MONTH = "October", VOLUME = 16, NUMBER = 4, PAGES = "355 - 376", + COMMENT = {A decision procedure for finding closed forms for indefinite +summation of polynomials, rational functions, quasipolynomials and +quasirational functions is presented. It is also extended to deal with +some non-hypergeometric sums with rational inputs, which are not summable +by means of Gosper's algorithm. Discussion of its implementation, analysis +of degree bounds and some illustrative examples are included.}} + +@ARTICLE{Man:93a, + AUTHOR = "Yiu-Kwong Man", + TITLE = "Computing Closed Form Solutions of First Order {ODE}s Using the +{Prelle-Singer} Procedure", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, MONTH = "November", VOLUME = 16, NUMBER = 5, PAGES = "423 - 443", + COMMENT = {The {Prelle-Singer} procedure is an important method for formal +solution of first order ODEs. Two different REDUCE implementations (PSODE +versions 1 & 2) of this procedure are presented in this paper. The aim is +to investigate which implementation is more efficient in solving different +types of ODEs (such as exact, linear, separable, linear in coefficients, +homogeneous or Bernoulli equations). The test pool is based on Kamke's +collection of first order and first degree ODEs. Experimental results, +timings and comparison of efficiency and solvability with the present +REDUCE differential equation solver (ODESOLVE) and a MACSYMA implementation +(ODEFI) of the {Prelle-Singer} procedure are provided. Discussion of +technical difficulties and some illustrative examples are also included.}} + +@InProceedings{Man:94, + author = {Yiu-Kwong Man and Francis J. Wright}, + title = {Fast Polynomial Dispersion Computation and its + Application to Indefinite Summation}, + booktitle = {Symbolic and Algebraic Computation}, + editor = {}, + series = {ISSAC}, + year = {1994}, + organization = {SIGSAM}, + publisher = {ACM}, + pages = {175--180} +} + +@ARTICLE{Marti:78, + AUTHOR = "Jed Marti", + TITLE = "The {META/REDUCE} Translator Writing System", + JOURNAL = "Sigplan Notices", + YEAR = 1978, VOLUME = 13, PAGES = "42-49", + COMMENT = {The {META/REDUCE} translator writing system operates in a +{LISP} and {REDUCE} syntax. The language supports: {BNF} like syntax, +recursive descent parsing schemes, lexical primitives, symbol table +primitives and automatic syntax error message generation.}} + +@ARTICLE{Marti:79, + AUTHOR = "J. B. Marti and A. C. Hearn and M. L. Griss and C. Griss", + TITLE = "Standard {Lisp} Report", + JOURNAL = "Sigplan Notices, ACM", + YEAR = 1979, VOLUME = 14, NUMBER = 10, PAGES = "48-68", + ABSTRACT = {A description of Standard {LISP} primitive data structures and +functions is presented.}} + +@ARTICLE{Marti:80, + AUTHOR = "J. Marti and A. C. Hearn and M. L. Griss and C. Griss", + TITLE = "Standard {Lisp} Report", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1980, VOLUME = 14, NUMBER = 1, PAGES = "23-41", MONTH = "February"} + +@ARTICLE{Marti:83, + AUTHOR = "Jed Marti and John Fitch", + TITLE = "{REDUCE} 2 for {CP/M}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "26-27", MONTH = "February"} + +@ARTICLE{Marti:85, + AUTHOR = "Jed B. Marti and Anthony C. Hearn", + TITLE = "{REDUCE} as a {LISP} Benchmark", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "8-16", MONTH = "August"} + +@INPROCEEDINGS{Marti:85a, + AUTHOR = "Jed B. Marti", + TITLE = "The Role of Explanation in Symbolic Computation", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "13-34"} + +@INPROCEEDINGS{Marti:88, + AUTHOR = "J. Marti", + TITLE = "A Graphics Interface to {REDUCE}", + BOOKTITLE = "Proc. {AAECC-6} 1988, Lecture Notes in Computer Science", + YEAR = 1988, VOLUME = 357, PAGES = "274-296", + PUBLISHER = "Springer-Verlag"} + +@BOOK{Marti:93a, + AUTHOR = "Jed Marti", + TITLE = "{RLISP} '88 An Evolutionary Approach to Program Design and Reuse", + PUBLISHER = "World Scientific", + ADDRESS = "Singapore", + YEAR = 1993, + NOTE = "SBN 981-02-14790"} + +@INPROCEEDINGS{Marzinkewitsch:91, + AUTHOR = "Reiner Marzinkewitsch", + TITLE = "Operating Computer Algebra Systems by Handprinted Input", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "411-413", YEAR = 1991, + ABSTRACT = {A prototype of a workstation is presented for calculation +with mathematical formulas by hand and support by computer algebra systems. +Keywords: Character recognition, neural network, computer algebra system, +context free grammar, parsing of two dimensional structures.}} + +@ARTICLE{Matveev:87, + AUTHOR = "V. A. Matveev and Ya. Z. Darbaidze and +Z. V. Merebashvili and L. A. Slepchenko", + TITLE = "Gluon Fusion in {SUSY QCD}", + JOURNAL = "Phys. Lett. B", + YEAR = 1987, VOLUME = 191, NUMBER = "1 and 2", PAGES = "179-181", + MONTH = "June"} + +@ARTICLE{Maurer:86, + AUTHOR = "M. Maurer and A. Hayd and H. J. Kaeppeler", + TITLE = "Quasi-Analytical Method for Solving Nonlinear Differential +Equations for Turbulent Self-Confined Magneto-Plasma", + JOURNAL = "J. Comp. Phys.", + YEAR = 1986, VOLUME = 66, PAGES = "151-172", + COMMENT = {Mixed {REDUCE} and {FORTRAN}. Enthusiastic about this style of +mixed working.}} + +@TECHREPORT{Mazepa:85, + AUTHOR = "N. E. Mazepa and S. I. Serdyukova", + TITLE = "The Stability Investigation of Some Difference Boundary Problem +with the Application of Symbolic Computation System", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1985, NUMBER = "E5-85-39"} + +@ARTICLE{Mazzarella:85, + AUTHOR = "Giuseppe Mazzarella", + TITLE = "Improved Simplification of Odd and Even Functions in {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "29-30", MONTH = "May"} + +@ARTICLE{McCrea:81, + AUTHOR = "J. D. McCrea", + TITLE = "The {Petrov} Type of a Static Vacuum Spacetime Near a +Normal-Dominated Singularity", + JOURNAL = "J. Phys.", + YEAR = 1981, VOLUME = "A14", PAGES = "1351-1356"} + +@ARTICLE{McCrea:82, + AUTHOR = "J. D. McCrea", + TITLE = "A Stationary Cylindrically Symmetric Electrovac Spacetime", + JOURNAL = "J. Phys.", + YEAR = 1982, VOLUME = "A15", PAGES = "1587-1590"} + +@ARTICLE{McCrea:83, + AUTHOR = "J. D. McCrea", + TITLE = "Static, Vacuum, Cylindrical and Plane Symmetric Solutions +of the Quadratic {Poincar{\'e}} Gauge Field Equations", + JOURNAL = "J. Phys.", + YEAR = 1983, VOLUME = "A16", PAGES = "997-1004"} + +@ARTICLE{McCrea:84, + AUTHOR = "J. D. McCrea", + TITLE = "A {NUT}-Like Solution of the Quadratic-{Poincar{\'e}} Gauge +Field Equations", + JOURNAL = "Phys. Lett.", + YEAR = 1984, VOLUME = "100A", PAGES = "397-399"} + +@INPROCEEDINGS{McCrea:84a, + AUTHOR = "J. D. McCrea", + TITLE = "The Use of {REDUCE} in Finding Exact Solutions of the +Quadratic {Poincar{\'e}} Gauge Field Equations", + BOOKTITLE = "Classical General Relativity", + PUBLISHER = "Cambridge University", YEAR = 1984, PAGES = "173-182"} + +@INPROCEEDINGS{McCrea:87, + AUTHOR = "J. D. McCrea", + TITLE = "{Poincar{\'e}} Gauge Theory of Gravitation: Foundations, +Exact Solutions and Computer Algebra", + YEAR = 1987, PAGES = "16", + BOOKTITLE = "Differential Geometric Methods in Mathematical +Physics, Proc. {14th} International Conference, +Salamanca, 1985 (Springer Lecture Notes in Mathematics, No. 1251)"} + +@ARTICLE{McCrea:87a, + AUTHOR = "J. D. McCrea and P. Baekler and M. Guerses", + TITLE = "A {Kerr}-Like Solution of the {Poincar{\'e}} Gauge Field +Equations", + JOURNAL = "Il Nuovo Cim", + YEAR = 1987, VOLUME = "99B", PAGES = "171-177"} + +@ARTICLE{McCrea:88, + AUTHOR = "J. D. McCrea and E. W. Mielke and F. W. Hehl", + TITLE = "A Remark on the Axisymmetric {Chen} et al. Solution of the +{Poincar{\'e}} Gauge Theory", + JOURNAL = "Phys. Lett.", + YEAR = 1988, VOLUME = "127A", PAGES = "65-69"} + +@ARTICLE{McIsaac:85, + AUTHOR = "Kevin McIsaac", + TITLE = "Pattern Matching Algebraic Identities", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 2, PAGES = "4-13", MONTH = "May"} + +@TECHREPORT{Melenk:88, + AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", + TITLE = "On {Gr{\"o}bner} Bases Computation on a Supercomputer +Using {REDUCE}", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik +Berlin", + YEAR = 1988, TYPE = "Preprint", NUMBER = "SC 88-2", MONTH = "January"} + +@ARTICLE{Melenk:89, + AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", + TITLE = "Symbolic Solution of Large Stationary Chemical +Kinetics Problems", + JOURNAL = "Impact of Computing in Science and Engineering", + YEAR = 1989, VOLUME = 1, NUMBER = 2, PAGES = "138-167", MONTH = "June"} + +@TECHREPORT{Melenk:89a, + AUTHOR = "Herbert Melenk and Winfried Neun", + TITLE = "Implementation of {Portable Standard LISP} for the {SPARC} +Processor", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1989, TYPE = "Preprint", NUMBER = "SC 89-6", MONTH = "July"} + +@ARTICLE{Melenk:89b, + AUTHOR = "Herbert Melenk and Winfried Neun", + TITLE = "Parallel Polynomial Operations in the Large {Buchberger} +Algorithm", + JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora +and J. Fitch", + YEAR = 1989, PAGES = "143-158", PUBLISHER = "Academic Press, London"} + +@ARTICLE{Melenk:90, + AUTHOR = "H. Melenk", + TITLE = "Solving Polynomial Equation Systems by {Groebner} Type Methods", + JOURNAL = "CWI Quarterly", + YEAR = 1990, VOLUME = 3, NUMBER = 2, PAGES = "121-136", MONTH = "June"} + +@INPROCEEDINGS{Melenk:91, + AUTHOR = "H. Melenk", + TITLE = "Practical Application of {Gr{\"o}bner} Bases for the Solution + of Polynomial Equation Systems", + BOOKTITLE = "IV. International Conference on Computer Algebra in + Physical Research, 1990", + EDITOR = "D. V. Shirkov, V. A. Tostovtsev, V. P. Gerdt", + YEAR = "1991", PAGES = "230-235", PUBLISHER="World Scientific", + ADDRESS="Singapore"} + +@TECHREPORT{Melenk:93, + AUTHOR = "Herbert Melenk", + TITLE = "Algebraic Solution of Nonlinear Equation Systems in {REDUCE}", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1993, TYPE = "Preprint", NUMBER = "TR 93-2", MONTH = "January"} + +@InProceedings{Melenk:93a, + author = "H. Melenk", + title = "Automatic Symbolic Solution of Nonlinear Equation Systems in + {REDUCE}", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "175-180", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + comment = {Mathematical background and algorithmic structure of the + nonlinear system part of the {REDUCE} 3.4.1 SOLVE package.} +} + +@TECHREPORT{Melenk:94, + AUTHOR = "Herbert Melenk", + TITLE = "The Complexity Barrier in {REDUCE} a Case Study", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1994, TYPE = "Preprint", NUMBER = "TR 94-6", MONTH = "January"} + +@ARTICLE{melfo:92, + AUTHOR = "A. Melfo and L. A. N\'u\~nez", + TITLE = "Checking Collineation Vectors with {REDUCE}", + JOURNAL = "Gen. Rel. Grav.", + YEAR = "1992", + VOLUME = "24", + NUMBER = "11", + PAGES = "1125--1129", + NOTE = "A package of programs for writing and checking the solutions +to the equations for various types of collineations (symmetries of the +metric, christoffel, riemman and ricci tensors) is presented. Some +examples of previously found collineations that have been checked are +given, and new results reported."} + +@ARTICLE{Mirie:84, + AUTHOR = "R. M. Mirie and C. H. Su", + TITLE = "Internal Solitary Waves and Their Head-On Collision Part I", + JOURNAL = "J. Fluid Mechanics", + YEAR = 1984, VOLUME = 147, PAGES = "213-231", + COMMENT = {Lengthy calculation "acknowledge the use of {REDUCE-2}." +Perturbation and integration.}} + +@INPROCEEDINGS{Molenkamp:91, + AUTHOR = "J.H.J. Molenkamp and V.V. Goldman and J.A. van Hulzen", + TITLE = "An Improved Approach to Automatic Error Cumulation Control", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "414-418", YEAR = 1991, + ABSTRACT = {For evaluation of arithmetical expressions using multiple +precision floating-point arithmetic, a method is given to automatically +perform error cumulation control prior to the actual computations. +Individual errors and their effects are identified, and it is shown how to +compute these effects efficiently via automatic differentiation. In the +presented approach these effects are used to determine which precisions have +to be chosen during the real computations, in order to limit error cumulation +to admissible, user chosen error bounds.}} + +@TECHREPORT{Moller:89, + AUTHOR = "H. Michael M{\"o}ller", + TITLE = "Multivariate Rational Interpolation Reconstruction of Rational +Functions", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik +Berlin", + YEAR = 1989, TYPE = "Preprint", NUMBER = "SC 89-4", MONTH = "July"} + +@TECHREPORT{Moller:92, + AUTHOR = "H. Michael M{\"o}ller", + TITLE = "On Decomposing Systems of Polynomial Equations With Finitely +Many Solutions", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik +Berlin", + YEAR = 1992, TYPE = "Preprint", NUMBER = "SC 92-15", MONTH = "June"} + +@INPROCEEDINGS{Moritsugu:85, + AUTHOR = "S. Moritsugu and N. Inada and E. Goto", + TITLE = "Symbolic {Newton} Iteration and its Application", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "105-117"} + +@TECHREPORT{Moritsugu:88, + AUTHOR = "S. Moritsugu and E. Goto", + TITLE = "A Proposal for Improvement of Facilities of {REDUCE}", + INSTITUTION = "Department of Information Science, +University of Tokyo, Japan", + YEAR = 1988, MONTH = "December"} + +@ARTICLE{Moritsugu:89, + AUTHOR = "Shuichi Moritsugu and Eiichi Goto", + TITLE = "A Note on the Preconditioning for Factorization of Homogeneous +Polynomials", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1989, VOLUME = 23, NUMBER = 1, PAGES = "9-12", MONTH = "January"} + +@ARTICLE{Moritsugu:89a, + AUTHOR = "Shuichi Moritsugu and Makoto Matsumoto", + TITLE = "A Note on the Numerical Evaluation of Arctangent Function", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1989, VOLUME = 23, NUMBER = 3, PAGES = "8-12", MONTH = "July"} + +@ARTICLE{Muroa:91, + AUTHOR = "Hirokazu Murao", + TITLE = "Vectorization of symbolic determinant calculation", + JOURNAL = "Supercomputer", + YEAR = 1991, VOLUME = "43,VIII-3", PAGES = "36-48"} + +@ARTICLE{Mueller:81, + AUTHOR = "R. M{\"u}ller and H. J. W. M{\"u}ller-Kirsten", + TITLE = "Iteration of Single- and Two-Channel {Schr{\"o}dinger} Equations", + JOURNAL = "J. Math. Phys.", + YEAR = 1981, VOLUME = 22, PAGES = "733-749", + ABSTRACT = {{\dots} we describe an iteration procedure which has already +been applied to a large number of other problems. With the help of +{REDUCE} it is now possible to do these algebraic computations on the +computer, so that the necessary expressions are obtained within a +reasonable time.}} + +@InProceedings{Mueller-Hoissen:93, + author = "F. Mueller-Hoissen", + title = "Noncommutative Differential Calculus, Quantum Groups and + Computer Algebra", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "97-102", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France" +} + +@ARTICLE{Murzin:85, + AUTHOR = "F. A. Murzin", + TITLE = "Syntactic Properties of the {REFAL} Language", + JOURNAL = "Int. J. Computer Maths.", + YEAR = 1985, VOLUME = 17, PAGES = "123-139", + COMMENT = {{SNOBOL-like} special purpose algebra system. Designed for +Cartan work. "{REFAL} is rather an unusual programming language. It is +natural to ask in which situations it is useful." Concludes {MACSYMA} +or {REDUCE} for standard manipulations, {REFAL} for nonstandard.}} + +@TECHREPORT{Nagata:82, + AUTHOR = "Morio Nagata and Makoto Shibayama", + TITLE = "{COSMOS:} A Conversational Algebraic System", + INSTITUTION = "Department of Administration Engineering, +Keio University", + YEAR = 1982, TYPE = "Technical Report", NUMBER = "No. 8201", + MONTH = "March"} + +@INPROCEEDINGS{Nagata:85, + AUTHOR = "Morio Nagata and Makoto Shibayama", + TITLE = "An Interactive Algebraic System for Personal Computing", + YEAR = 1985, + BOOKTITLE = "IEEE International Symposium on New Directions +in Computing"} + +@BOOK{Nakamura:89, + AUTHOR = "Hideharu Nakamura and Shouichi Matsui", + TITLE = "Symbolic Computation in Structural Mechanics using {REDUCE}", + PUBLISHER = "Gihodo Shuppan Company Ltd.", ADDRESS = "1-11-41, +Akasaka, Minato-Ku, 107 Tokyo, {Japan}", YEAR = 1989} + +@ARTICLE{Nakashima:84, + AUTHOR = "T. T. Nakashima and R. E. D. McClung and B. K. John", + TITLE = "A Simple Method for the Determination of the Deuterium +Decoupler Pulse Angle", + JOURNAL = "J. Magnetic Resonance", + YEAR = 1984, VOLUME = 56, PAGES = "262-274", + COMMENT = {{REDUCE} used in theoretical part. "All density matrix +calculations presented here were performed on a digital computer using +REDUCE-2." Essentially matrix products.}} + +@ARTICLE{Nakashima:84a, + AUTHOR = "T. T. Nakashima and R. E. D. McClung and B. K. John", + TITLE = "Experimental and Theoretical Investigation of +$_{2}D-_{13}C$ DEPT Spectra on $CD_{N}$", +JOURNAL = "J. Magnetic Resonance", + YEAR = 1984, VOLUME = 58, PAGES = "27-36", + COMMENT = {"All calculations were performed using {REDUCE-2}."}} + +@ARTICLE{Namba:86, + AUTHOR = "Kenji Namba", + TITLE = "Some Improvements on {Utah} {Standard} {Lisp}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "29-36", + MONTH = "February and May"} + +@ARTICLE{Nemeth:82, + AUTHOR = "G. N{\'e}meth and M. Zim{\'a}nyi", + TITLE = "Polynomial Type {Pad\'e} Approximants", + JOURNAL = "Math. Comp.", + YEAR = 1982, VOLUME = 38, PAGES = "553-565", + COMMENT = {Looking for approximants where $R_{n}(x)$ is +$P_{n}(x)$/P_{n-1}(x)$. Applied in special functions. Used +REDUCE and FORMAC mainly for bignum calculations.}} + +@INPROCEEDINGS{Nemeth:87, + AUTHOR = "G. N{\'e}meth and M. Zim{\'a}nyi", + TITLE = "Computation of Generalized {Pad\'e} Approximants", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "450-451", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Neun:89, + AUTHOR = "W. Neun and H. Melenk", + TITLE = "Implementation of the {LISP-}Arbitrary Precision Arithmetic +for a vector Processor", + JOURNAL = "Computer Algebra and Parallelism", EDITOR = "J. Della Dora +and J. Fitch", + YEAR = 1989, PAGES = "75-89", PUBLISHER = "Academic Press, London"} + +@ARTICLE{Neutsch:85, + AUTHOR = "W. Neutsch and E. Schr{\"u}fer and A. Jessner", + TITLE = "Note on Efficient Integration on the Hypersphere", + JOURNAL = "J. Comp. Phys.", + YEAR = 1985, VOLUME = 59, PAGES = "167-175", + COMMENT = {{REDUCE} used for integration on 4-D hypersphere. {REDUCE} +use rather small.}} + +@ARTICLE{Neutsch:86, + AUTHOR = "W. Neutsch and E. Schr{\"u}fer", + TITLE = "Simple Integrals for Solving {Kepler}'s Equation", + JOURNAL = "Astrophysics and Space Science", + YEAR = 1986, VOLUME = 125, PAGES = "77-83", + COMMENT = {Uses {REDUCE} to verify calculations to give integral form which +is numerically good, involving only rationals and exponentials.}} + +@ARTICLE{Ng:89, + AUTHOR = "Tze Beng Ng", + TITLE = "Computation of the Cohomology of ${B\hat{S}O_{n}<16>}$ for +$23 \leq n \leq 26$ using {REDUCE}", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 7, NUMBER = 1, PAGES = "93-99", MONTH = "January"} + +@ARTICLE{Niki:84, + AUTHOR = "Naoto Niki and Sadanori Konishi", + TITLE = "Higher Order Asymptotic Expansions for the +Distribution of the Sample Correlation Coefficient", + JOURNAL = "Comm. Statist.-Simula. Comp.", + YEAR = 1984, VOLUME = 13, NUMBER = 2, PAGES = "169-182"} + +@TECHREPORT{Nikityuk:87, + AUTHOR = "N. M. Nikityuk", + TITLE = "Some Questions of Using Coding Theory and Analytical +Calculation Methods on Computers", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1987, NUMBER = "E11-87-10"} + +@ARTICLE{Noor:79, + AUTHOR = "A. K. Noor and C. M. Andersen", + TITLE = "Computerized Symbolic Manipulation in Structural Mechanics - +Progress and Potential", + JOURNAL = "Computers and Structures", + YEAR = 1979, VOLUME = 10, PAGES = "95-118", + COMMENT = {Concentrates on {MACSYMA} but mentions {FORMAC} and {REDUCE} +as also having been used in structures. Mainly finite elements. Includes +program and output.}} + +@INPROCEEDINGS{Norman:77, + AUTHOR = "A. C. Norman and P. M. A. Moore", + TITLE = "Implementing the New {Risch} Integration Algorithm", + YEAR = 1977, MONTH = "March", + BOOKTITLE = "Proc. of the Fourth Colloquium on Advanced Comp. +Methods in Theor. Phys., St. Maximin, France"} + +@ARTICLE{Norman:78, + AUTHOR = "Arthur Norman", + TITLE = "Towards a {REDUCE} solution to {SIGSAM} Problem 7", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1978, VOLUME = 12, NUMBER = 4, PAGES = "14-18", MONTH = "November"} + +@INPROCEEDINGS{Norman:79, + AUTHOR = "A. C. Norman and J. H. Davenport", + TITLE = "Symbolic Integration - The Dust Settles?", + BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes +in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "398-407", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Norman:83, + AUTHOR = "Arthur C. Norman and Paul S. Wang", + TITLE = "A Comparison of {Vaxima} and {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "28-30", + MONTH = "February"} + +@InProceedings{Norman90, + author = "A. C. Norman", + title = "A Critical-Pair/Completion based Integration Algorithm", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "201-205", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@INPROCEEDINGS{Norman:93, + AUTHOR = "A. C. Norman", + TITLE = "Compact Delivery Support for {REDUCE}", + BOOKTITLE = "Proc. {DISCO '93}, Lecture Notes on Comp. Science", + YEAR = 1993, VOLUME = 722, PAGES = "331-340", + PUBLISHER = "Springer-Verlag", + ABSTRACT = {The {CSL} Lisp system is one designed primarily for delivering +Lisp applications to users. It thus emphasises robustness, portability and +small size rather than support for an integrated programming environment. +Both portability and compactness are served by making CSL compile the bulk +of applications code into a compact byte-code instruction set which is then +emulated. The speed penalities inherent in this are offset by providing +instrumentation that makes it easy to identify code hot-spots, and a second +compiler that translates critical parts of the original Lisp into C for +incorporation in the CSL kernel. For use with REDUCE it is found that +compiling about 5% of the source code into C led to overall performance +competetive with other Lisp implementations.}} + +@ARTICLE{Norman:95, + AUTHOR = "A.C. Norman", + TITLE = "Compact Delivery Support for {REDUCE}", + JOURNAL = "Journ. Symbolic Computation", + YEAR = 1995, VOLUME=19, PAGES = "133-143", + ABSTRACT = "{CSL} is a {Lisp} system specifically designed to support the +{REDUCE} algebra system. This paper views the {Lisp} system upon which a +{Lisp-coded} algebra system is coded as in effect a micro-kernel -- it +provides basic compilation, storage management and extended arithmetic +capabilities that algebra needs, but is not much concerned with higher level +algebraic algorithms or with user interfaces. The description of {CSL} +given here discusses the major design decisions embodied in the system, and +shows the extent to which it has been possible to resolve conflicting goals +of simplicity, small size, portability and high performance."} + +@ARTICLE{Norton:80, + AUTHOR = "Lewis M. Norton", + TITLE = "A Note About {Laplace} Transform Tables for Computer Use", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1980, VOLUME = 14, NUMBER = 2, PAGES = "30-31", MONTH = "May"} + +@TECHREPORT{Nucci:90, + AUTHOR = "M. C. Nucci", + TITLE = "Interactive {REDUCE} Programs for Calculating Classical, +Non-Classical and {Lie-B{\"a}cklund} Symmetries of Differential Equations", + INSTITUTION = "Georgia Institute of Technology, School of Mathematics", + YEAR = 1990, TYPE = "Preprint", NUMBER = "Math: 062090-051"} + +@BOOK{Ochiai:90, + AUTHOR = "Mitsuyuki Ochiai and Kiyokazu Nagatomo", + TITLE = "Linear Algebra using {REDUCE}", + PUBLISHER = "Kindai Kagaku sha, Tokyo", MONTH = "January", YEAR = 1990, + COMMENT = {In Japanese.}} + +@ARTICLE{Ogilvie:82, + AUTHOR = "J. F. Ogilvie", + TITLE = "Applications of Computer Algebra in Physical Chemistry", + JOURNAL = "Computers in Chemistry", + YEAR = 1982, VOLUME = 6, NUMBER = 4, PAGES = "169-172", + COMMENT = {After distinguishing between algebraic and numerical +computing, the author outlines the facilities of some +algebraic or symbolic processors and provides some +instances of how some important features can be applied +to problems in physical chemistry.}} + +@ARTICLE{Ogilvie:89, + AUTHOR = "J. F. Ogilvie", + TITLE = "Computer algebra in modern physics", + JOURNAL = "Computers in Physics", + YEAR = 1989, MONTH = "January/February", PAGES = "66-74"} + +@TECHREPORT{Ono:1979, + AUTHOR = "Kiyoshi Ono", + TITLE = "{BFORT} -- A {Fortran} System with Arbitrary +Precision Integer and Real Arithmetic", + INSTITUTION = "Department of Physics, University of Tokyo", + YEAR = 1979, MONTH = "January"} + +@TECHREPORT{Ozieblo, + AUTHOR = "A. Ozieblo", + TITLE = "Application of {REDUCE 2} in General Theory of Relativity", + INSTITUTION = "Cyfronet - Krakow, Poland", + COMMENT = {Application of {REDUCE 2} in all calculations typical for +General Theory of Relativity is shown here. The most +spectacular usage of {REDUCE 2} appears to be in various +aspects of tensor calculus including differentiation +operations.}} + +% REDUCE BIBLIOGRAPHY + +% Part 4: P-Z + +% Copyright (c) 1993 RAND. All Rights Reserved. + +% Additions and corrections are solicited. Please send them, in the +% same format as these entries if possible, to reduce at rand.org. + + +@InProceedings{Padget90, + author = "Julian Padget and Alan Barnes", + title = "Univariate Power Series Expansions in {REDUCE}", + booktitle = "Proceedings of the International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "82-87", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@ARTICLE{Pankau:73, + AUTHOR = "E. Pankau and W. Nakel", + TITLE = "Measurement of the Absolute Cross Section of the +Elementary Process of Electron-Electron Bremsstrahlung at 300 {keV}", + JOURNAL = "Phys. Lett.", + YEAR = 1973, VOLUME = "44A", PAGES = "65-67"} + +@ARTICLE{Pankau:73a, + AUTHOR = "E. Pankau and W. Nakel", + TITLE = "Eine {Koinzidenzmessung} zum {Elementarprozess} +der {Elektron-Elektron-Bremsstrahlung} bei 300 {keV}", + JOURNAL = "Z. Physik", + YEAR = 1973, VOLUME = 264, PAGES = "139-153"} + +@ARTICLE{Parsons:68, + AUTHOR = "R. G. Parsons", + TITLE = "An Estimate of the Sixth Order Contribution to the +Anomalous Magnetic Moment of the Electron", + JOURNAL = "Phys. Rev.", + YEAR = 1968, VOLUME = 168, PAGES = "1562-1567"} + +@TECHREPORT{Parsons:71, + AUTHOR = "R. G. Parsons", + TITLE = "S-Channel Transformation Matrices for Helicity and +Invariant Amplitudes for lambda + N to O + B", + INSTITUTION = "Center for Particle Theory, University of Texas", + YEAR = 1971, TYPE = "Memo", NUMBER = "CPT-88", MONTH = "January"} + +@ARTICLE{Pasini:91, + AUTHOR = "P. Pasini and F. Semeria and C. Zannoni", + TITLE = "Symbolic computation of orientational correlation function +moments", + JOURNAL = "J. Symbolic Computation", + YEAR = 1991, VOLUME = 12, NUMBER = 2, PAGES = "221-231", MONTH = "August"} + COMMENTS = {Symbolic manipulation (REDUCE and SCHOONSCHIP) has been +applied to the analytic evaluation of the coefficients in the Taylor series +expansion of time-correlation functions. These expressions are derived +for cylindrically and biaxially symmetric particles reorienting in a +uniaxial fluid. The possibility of using computer algebra to determine +correlation-function moments should make it applicable to various problems +in statistical physics.}} + +@ARTICLE{Pattnaik:83, + AUTHOR = "P. C. Pattnaik and G. Fletcher and J. L. Fry", + TITLE = "Improved Numerical Stability for Norm-Conserving ion-{Ure} +Pseudopotentials", + JOURNAL = "Phys. Rev. B", + YEAR = 1983, VOLUME = 28, NUMBER = 6, PAGES = "3364-3365", + COMMENT = {{REDUCE} and {FORTRAN}; inverting a matrix algebraically would +be more accurate than a numerical inverse, and used {REDUCE} for this part of +their work.}} + +@ARTICLE{Pearce:81, + AUTHOR = "P. D. Pearce and R. J. Hicks", + TITLE = "The Application of Algebraic Optimisation Techniques to +Algebraic Mode Programs for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1981, VOLUME = 15, NUMBER = 4, PAGES = "15-22", + MONTH = "November"} + +@ARTICLE{Pearce:83, + AUTHOR = "P. D. Pearce and R. J. Hicks", + TITLE = "Data Structures and Execution Times of Algebraic Mode +Programs for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "31-37", MONTH = "February"} + +@ARTICLE{Perjes:84, + AUTHOR = "Z. Perj{\'e}s", + TITLE = "Stationary Vacuum Fields with a Conformally Flat +Three-Space. {III}. {Complete} Solution", + JOURNAL = "General Relativity and Gravitation", + YEAR = 1984, VOLUME = 18, PAGES = "531-547", + COMMENT = {{REDUCE} used to perform the necessary calculations.}} + +@ARTICLE{Perjes:84a, + AUTHOR = "Z. Perj{\'e}s and B. Luk{\'a}cs and A. Sebesty{\'e}n +and A. Valentini", + TITLE = "Solution of the Stationary Vacuum Equations of +Relativity for Conformally Flat 3-Spaces", + JOURNAL = "Phys. Lett.", + YEAR = 1984, VOLUME = {100A}, NUMBER = 8, PAGES = "405-406", + MONTH = "February"} + +@TECHREPORT{Perjes:84b, + AUTHOR = "Z. Perj{\'e}s", + TITLE = "Improved Characterization of the {Kerr} Metric", + INSTITUTION = "Hungarian Academy of Sciences, Central +Research Institute for Physics", + YEAR = 1984, NUMBER = "KFKI-1984-115"} + +@TECHREPORT{Perjes:84c, + AUTHOR = "Z. Perj{\'e}s", + TITLE= "Stationary Vacuum Fields with a Conformally Flat Three-Space. +{IV}. {Complete} Solution", + INSTITUTE = "Institute for Nuclear Study, University of Tokyo", + YEAR = 1984, NUMBER = "INS-REP.-487", MONTH = "January"} + +@TECHREPORT{Perjes:86, + AUTHOR = "Z. Perj{\'e}s", + TITLE = "Ernst Coordinates", + INSTITUTION = "Hungarian Academy of Sciences, Central +Research Institute for Physics", + YEAR = 1986, TYPE = "Preprint", NUMBER = "KFKI-1986-33/B"} , + +@ARTICLE{Perjes:86a, + AUTHOR = "Z. Perj{\'e}s", + TITLE = "Stationary Vacuum Fields with a Conformally +Flat Three-Space. {II}. {Proof} of Axial Symmetry", + JOURNAL = "General Relativity and Gravitation", + YEAR = 1986, VOLUME = 18, NUMBER = 5, PAGES = "511-530", + MONTH = "May"} + +@ARTICLE{Perjes:88, + AUTHOR = "Z. Perj{\'e}s", + TITLE = "Approaches to Axisymmetry by Man and Machine", + JOURNAL = "Relativity Today", + YEAR = 1988, EDITOR = "Z. Perjes", PUBLISHER = "World Scientific, + Singapore"} + +@ARTICLE{Perlt:90, + AUTHOR = "H. Perlt and J. Ranft and J. Heinrich", + TITLE = "Calculation of {QED} graphs with the {Spinor} technique", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1990, VOLUME = 56, NUMBER = 3, PAGES = "385-390", MONTH = "January"} + +@TECHREPORT{Perrottet:78, + AUTHOR = "M. Perrottet", + TITLE = "Signature for {W} Boson Production From Jet Analysis +In e+e- $\rightarrow$ {W+W-} $\rightarrow$ Hadrons", + INSTITUTION = "CPT 2, CNRS, Marseille", YEAR = 1978, + TYPE = "Preprint", NUMBER = "78/P.1019", MONTH = "June", + ABSTRACT = {We have computed the ratio +o(e+e- $\rightarrow$ W+W- $\rightarrow$ Hadrons)/ o(e+e- $\rightarrow$ +G,Z $\rightarrow$ Hadrons) as a function of the {CM} energy in the +Weinberg-Salam model.}} + +@TECHREPORT{Pesic:73, + AUTHOR = "P. D. Pesic", + TITLE = "Two-Photon Cross Section for {W}-Pair Production +by Colliding Beams", + INSTITUTION = "Stanford University", YEAR = 1973, TYPE = "Report", +NUMBER = "SLAC-PUB-1188", + COMMENT = {Stanford University Linear Accelerator Report.}} + +@PHDTHESIS{Pictiaw:69, + AUTHOR = "Chen Pictiaw", + TITLE = "An Analytical Investigation of Infinitesimal Spatial +Motion Theory and its Application to Three-Dimensional Linkages", + SCHOOL = "Dept. of Mech. Eng., Stanford University", + YEAR = 1969, MONTH = "March"} + +@ARTICLE{Piessens:84, + AUTHOR = "R. Piessens", + TITLE = "A Series Expansion for the First Positive Zero of the {Bessel} +Function", + JOURNAL = "Math. Comp.", + YEAR = 1984, VOLUME = 42, PAGES = "195-197", + COMMENT = {Gives explicit series for first positive zero for 4 terms, using +{REDUCE}.}} + +@ARTICLE{Piessens:86, + AUTHOR = "R. Piessens and S. Ahmed", + TITLE = "Note on Approximation for the Turning Points of {Bessel} +Functions", + JOURNAL = "J. Comp. Phys.", + YEAR = 1986, VOLUME = 64, PAGES = "253-257", + COMMENT = {{REDUCE} used to differentiate and give expansions.}} + +@ARTICLE{Pignataro:85, + AUTHOR = "M. Pignataro and A. Luongo and N. Rizzi", + TITLE = "On the Effect of the Local Overall Interaction on the +Postbuckling of Uniformly Compressed Channels", + JOURNAL = "Thin-Walled Structures", + YEAR = 1985, VOLUME = 3, PAGES = "292-321", + COMMENT = {{REDUCE} generating {FORTRAN}, but also used to investigate the +form of the solutions.}} + +@MASTERSTHESIS{Podgorzak:84, + AUTHOR = "E. Podg{\'o}rak and I. Romanowska", + TITLE = "Application of {REDUCE} 2 to the Construction of +Recurrence Relations", + SCHOOL = "Institute of Computer Science, University of Wroclaw", + YEAR = "1984"} + +@ARTICLE{Price:84, + AUTHOR = "S. L. Price and A. J. Stone and M. Alderton", + TITLE = "Explicit Formulae for the Electrostatic Energy, Forces and +Torques Between a Pair of Molecules of Arbitrary Symmetry", + JOURNAL = "Molecular Phys.", + YEAR = 1984, VOLUME = 52, PAGES = "987-1001", + COMMENT = {"The substitution of the complex multipoles and the S +functions into the expression for the electrostatic energy was +facilitated by the use of the symbolic algebraic manipulation program +{REDUCE}." Involves heavy calculations.}} + +@TECHREPORT{Quarton, + AUTHOR = "D. C. Quarton and A. D. Garrad", + TITLE = "Some Comments on the Stability Analysis of Horizontal +Axis Wind Turbines", + INSTITUTION = "Wind Energy Group, Taylor Woodrow Construction Ltd."} + +@TECHREPORT{Quarton:84, + AUTHOR = "D. C. Quarton and A. D. Garrad", + TITLE = "Symbolic Computing as a Tool in Wind Turbine Dynamics", + INSTITUTION = "Wind Energy Group, Taylor Woodrow Construction Ltd.", + YEAR = 1984, + COMMENT = {Presented at the European Wind Energy Conference and Exhibition +22-26 Oct 1984, Hamburg.}} + +@MASTERSTHESIS{Rao:85, + AUTHOR = "R. H. Rao", + TITLE = "Deformation of a Fluid-Filled Cylindrical Membrane by a +Slow Viscous Shear Flow", + SCHOOL = "Washington University", + ADDRESS = "Dept. of Mech. Eng., Washington University, St. Louis", + YEAR = "1985", + COMMENT = {Draws attention to the use of classical perturbation +techniques combined with computer algebra as an alternative to +numerical calculation.}} + +@BOOK{Rayna:87, + AUTHOR = "G. Rayna", + TITLE = "{REDUCE}: A System for Computer Algebra", + PUBLISHER = "Springer-Verlag", + YEAR = 1987} + +@INPROCEEDINGS{Renner:91, + AUTHOR = "Friedrich Renner", + TITLE = "Nonlinear Evolution Equations and the {Painlev{\'e}} Analysis: +A constructive Approach with {REDUCE}", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "289-294", + ABSTRACT = {A number of necessary conditions for a class of nonlinear +partial differential equations to pass the Painlev{\'e} test with the +Kruskal ansatz is given. Using these we can (theoretically) construct all +evolution equations of certain form and this property with a computer algebra +package based on {REDUCE}.}} + +@ARTICLE{Renner:92, + AUTHOR = "Friedrich Renner", + TITLE = "A constructive {REDUCE} package based upon the {Painlev{\'e}} +analysis of nonlinear evolutions equations in Hamiltonian and/or normal +form", + JOURNAL = "Computer Physics Communications", + YEAR = 1992, VOLUME = 70, NUMBER = 2, PAGES = "409-416", MONTH = "June", + ABSTRACT = {A number of necessary conditions for scalar nonlinear evolution +equations of normal or certain Hamiltonian form to pass the {Painlev{\'e}} +test in one (or two) branches with the Kruskal ansatz is used to write a +{REDUCE} package able to construct (theoretically) all equations with this +property. Starting with a given leading order, a degree of homogeneity +and (in the Hamiltonian case) a skew-adjoint differential operator, the +system generates al admissible resonance patterns, adapts (if possible) +the free parameters of the equation according to the chosen pattern and the +constraints of the compatibility conditions. In the {Painlev{\'e}} case, +the general inhomogeneous equation is generated and also examined. For +help and further investigations a set of utility procedures is supplied.}} + +@ARTICLE{Reusch:86, + AUTHOR = "M. F. Reusch and G. H. Neilson", + TITLE = "Torodially Symmetric Polynomial Multipole Solutions +of the Vector {Laplace} Equation", + JOURNAL = "J. Comp. Phys.", + YEAR = 1986, VOLUME = 64, PAGES = "416-432", + COMMENT = {{REDUCE} (plasma MHD) algebraic form of multipoles, then +numerical.}} + +Marcelo Ribeiro +Departamento de Astrofisica +Observatorio Nacional - CNPq +Rua General Jose Cristino 77 +Rio de Janeiro, RJ 20921-400 +BRAZIL +;N arpa mbr obsn.on.br + +@PHDTHESIS{Rink:71, + AUTHOR = "R. A. Rink", + TITLE = "Application of a Digital Computer to Solve Analytically +Special Classes of Linear and Nonlinear Differential Equations", + SCHOOL = "Stanford University", + YEAR = 1971} + +@ARTICLE{Rizzi:85, + AUTHOR = "N. Rizzi and A. Tatone", + TITLE = "Symbolic Manipulation in Buckling and Postbuckling Analysis", + JOURNAL = "Computers and Structures", + YEAR = 1985, VOLUME = 21, PAGES = "691-700", + COMMENT = {Gives {REDUCE} program and output for generating {FORTRAN}.}} + +@ARTICLE{Rodionov:84, + AUTHOR = "A. Ya. Rodionov", + TITLE = "Work with {non-commutative} variables in the {REDUCE-2} +system for analytical calculations", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1984, VOLUME = 18, NUMBER = 3, PAGES = "16-19", MONTH = "August"} + +@ARTICLE{Rodionov:87, + AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", + TITLE = "Computation of Covariant Derivatives of the Geodetic +Interval within the Coincident Arguments", + JOURNAL = "Class. Quantum Grav.", + YEAR = 1987, VOLUME = 4, PAGES = "1767-1775", + COMMENT = {Used {REDUCE} to calculate the geodetic interval of the +Riemannian manifold by calculating the multiple covariant derivatives of +orders 7 and 8. Direct use of {REDUCE} was not sufficient, but some +investigations of the structure of the problem produced some +recurrence relations.}} + +@INPROCEEDINGS{Rodionov:87a, + AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", + TITLE = "Combinatorial Aspects of Simplification of Algebraic Expressions", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "192-201", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Rodionov:88, + AUTHOR = "A. Ya. Rodionov and A. Yu. Taranov", + TITLE = "{RTENSOR - Packet} for work with tensoric expressions", + INSTITUTION = "Moscow State University, Scientific Research Institute +of Nuclear Physics", YEAR = 1988, TYPE = "Preprint", NUMBER = "88-29/50"} + +@INPROCEEDINGS{Roelofs:91, + AUTHOR = "Marcel Roelofs and Peter K.H. Gragert", + TITLE = "Implementation of multilinear operators in {REDUCE} and +applications in mathematics", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "390-396", + ABSTRACT = {In this paper we introduce and implement a concept for dealing +with mathematical bases of linear spaces and mappings (multi)linear with +respect to such bases, in {REDUCE}. Using this concept we give some +examples how to implement some well known (multi)linear mappings in +mathematics with very little effort. Moreover we implement a procedure +operatorcoeff similar to the standard {REDUCE} procedure coeff, but now +for linear spaces instead of polynomial rings.}} + +@BOOK{Rogers:89, + AUTHOR = "C. Rogers and W. F. Ames", + TITLE = "Nonlinear Boundary Value Problems in Science and Engineering", + PUBLISHER = "Academic Press, Inc.", + YEAR = 1989} + +@ARTICLE{Roque:88, + AUTHOR = "Waldir L. Roque and Renato P. dos Santos", + TITLE = "Computa\c{c}\~{a}o alg\'{e}brica: ``um assistente matem\~{a}tico''", + JOURNAL = "Ci\^{e}ncia e Cultura", + YEAR = 1988, VOLUME = 40, NUMBER = 9, PAGES = "843-852", MONTH = +"September", + ABSTRACT = {In this paper we discuss in a simple and +informative way the theme ``algebraic computing'' in an attempt to encourage +the Brasilian scientific community to make use of this new tool{\ldots}. Many +algebraic computing systems have been developed in a variety of research +fields. Some of these systems, their main characteristics and applications +will be discussed.}, + COMMENT = {In Portuguese}} + +@ARTICLE{Roque:91, + AUTHOR = "Waldir L. Roque and Renato P. dos Santos", + TITLE = "Computer algebra in spacetime embedding", + JOURNAL = "J. Symbolic Computation", + YEAR = 1991, VOLUME = 12, NUMBER = 3, PAGES = "381-389", MONTH = +"September", + ABSTRACT = {In this paper we describe an algorithm to determine the vectors +normal to a space-time ${V}_{4}$ embedded in a pseudo-Euclidean manifold +${M}_{4+N}$. An application of this algorithm is given considering the +Schwarzchild spacetime geometry embedded in a 6 dimensional pseudo-Euclidean +manifold, using the algebraic computing system REDUCE.}} + +@ARTICLE{Ronveaux:88, + AUTHOR = "A. Ronveaux and G. Thiry", + TITLE = "Polynomial Solution of Recurrence Relation and Differential +Equation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1988, VOLUME = 22, NUMBER = 4, PAGES = "9-19", MONTH = "October"} + +@ARTICLE{Ronveaux:89, + AUTHOR = "A. Ronveaux and G. Thiry", + TITLE = "Differential Equations of Some Orthogonal Families in {REDUCE}", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 8, NUMBER = 5, PAGES = "537-541", MONTH = "November"} + +@INPROCEEDINGS{Rudenko:91, + AUTHOR = "V.M. Rudenko and V.V. Leonov and A.F. Bragazin and +I.P Shmyglevsky", + TITLE = "Application of Computer Algebra to the Investigation of the +Orbital Satellite Motion", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "450-451"} + +@ARTICLE{Saez:83, + AUTHOR = "A. E. Saez and B. J. McCoy", + TITLE = "Transient Analysis of Packed-Bed Thermal Storage Systems", + JOURNAL = "Int. J. Heat Mass Transfer", + YEAR = 1983, VOLUME = 26, NUMBER = 1, PAGES = "49-54"} + +@ARTICLE{Sage:88, + AUTHOR = "Martin L. Sage", + TITLE = "An Algebraic Treatment of Quantum Vibrations", + JOURNAL = "J. Symbolic Computation", + YEAR = 1988, VOLUME = 5, NUMBER = 3, PAGES = "377-384", MONTH = "June"} + +@ARTICLE{Sarlet:92, + AUTHOR = "W. Sarlet and J. Vanden Bonne", + TITLE = "{REDUCE-}procedures for the study of adjoint symmetries of +second-order differential equations", + JOURNAL = "J. Symbolic Computation", + VOLUME = 13, NUMBER = 6, YEAR = 1992, MONTH = "June", PAGES = "683-693", + ABSTRACT = {Two {REDUCE} programs are presented which should be of +assistance in computing and studying so-called adjoint symmetries of +second-order ordinary differential equations. The first program essentially +serves to construct the determining equations for adjoint symmetries, +whose leading coefficients are allowed to be polynomial functions of the +velocities. The second program runs various tests concerning the possible +construction of a first integral or a lagrangian for the given system.}} + +@INPROCEEDINGS{Sasaki:79, + AUTHOR = "Tateaki Sasaki", + TITLE = "An Arbitrary Precision Real Arithmetic Package in {REDUCE}", + BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes +in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "358-368", + PUBLISHER = "Springer-Verlag", + ABSTRACT = {A {REDUCE} arbitrary precision real arithmetic package is +described which will become a part of the kernel of an algebraic-numeric +system being developed for {REDUCE}.}} + +@ARTICLE{Savage:90, + AUTHOR = "Stuart B. Savage", + TITLE = "Symbolic computation of the flow of granular avalanches", + JOURNAL = "J. Symbolic Computation", + YEAR = 1990, VOLUME = 9, NUMBER = 4, PAGES = "515-530", MONTH = "April"} + +@ARTICLE{Sayers:87, + AUTHOR = "C. M. Sayers", + TITLE = "The Elastic Anisotropy of Polycrystalline Aggregates +of Zirconium and Its Alloys", + JOURNAL = "J. Nuclear Materials", + YEAR = 1987, VOLUME = 144, PAGES = "211-213", + COMMENT = {Used {REDUCE} for calculations of tensor products.}} + +@ARTICLE{Sayers:87a, + AUTHOR = "C. M. Sayers", + TITLE = "Elastic Wave Anisotropy in the Upper Mantle", + JOURNAL = "Geophysical J. R. Ast. Soc.", + YEAR = 1987, VOLUME = 88, PAGES = "417-424", + COMMENT = {Used {REDUCE} in calculations. "Theoretical expressions for +angular dependence of the longitudinal and shear wave velocities in an +axially symmetric aggregate{\ldots}"}} + +@INPROCEEDINGS{Schlegel:91, + AUTHOR = "H. Schlegel", + TITLE = "Determination of the Root System of Semisimple {Lie} Algbras from +the {Dynkin} Diagram", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "239-240"} + +@INPROCEEDINGS{Schmuck:77, + AUTHOR = "P. Schmuck", + TITLE = "Verification of the Transient, Two Phase Fluid +Flow Program {Kachina} using Computerized Similarity Analysis", + YEAR = 1977, MONTH = "October", + BOOKTITLE = "Second {GAMM} Conference on Numerical Methods +in Fluid Mechanics, k{\"o}ln"} + +@TECHREPORT{Schoebel:92, + AUTHOR = "Franziska Schoebel", + TITLE = "The Symbolic Classification of Real Four-Dimensional + Lie Algebras", NUMBER = "Preprint 27/92", YEAR = 1992, + INSTITUTION = "Naturwissenschaftlich-Theoretisches Zentrum, Universitaet + Leipzig, Germany"} + +@TECHREPORT{Schoepf:91, + AUTHOR = "Rainer Sch{\"o}pf and Peter Deuflhard", + TITLE = "{OCCAL} A mixed symbolic-numeric {Optimal Control CALculator}", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1991, TYPE = "Preprint", NUMBER = "SC 91-13", MONTH = "December", + ABSTRACT = {The numerical solution of optimal control problems by indirect +methods (such as multiple shooting or collocation) requires a considerable +amount of analytic calculation to establish a numerically tractable system. +These analytic calculations, though being rather tedious in realistic +examples, are nowadays mostly still done by hand--and thus prone to +calculation errors. The paper aims at automating this analytic processing +to a reasonable extent by means of a modern symbolic manipulation language +(here: REDUCE). In its present stage of development the package OCCAL +(mnemotechnically for Optimal Control CALculator) permits an interactive +use, covering tasks like automatic determination of control and, in case of a +singular control, of its order. In simpler problems, the present version of +OCCAL automatically produces the full subroutine input for a MULtiple +shooting code (MULCON) with adaptive numerical CONtinuation. + +In more complicated problems where singular sub-arcs may occur or where the +sequence of sub-arcs of the optimal trajectory is unclear OCCAL is a +significant help in reducing analytic pre-processing. Examples illustrate +the performance of OCCAL/MULCON.}} + +@ARTICLE{Schruefer:81, + AUTHOR = "E. Schr{\"u}fer and H. Heintzmann", + TITLE = "Lorentz-Covariant Eikonal Method in Magnetohydrodynamics +{II} - The Determination of the Wave Amplitude", + JOURNAL = "Phys. Lett.", + YEAR = 1981, VOLUME = {81A}, NUMBER = 9, PAGES = "501-506", + MONTH = "February", + COMMENT = {Used {REDUCE} for "rather tedious algebra."}} + +@ARTICLE{Schruefer:82, + AUTHOR = "E. Schr{\"u}fer", + TITLE = "An Implementation of the Exterior Calculus in {REDUCE:} +A Status Report", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "27-31", MONTH = "November"} + +@ARTICLE{Schruefer:87, + AUTHOR = "E. Schr{\"u}fer and F. W. Hehl and J. D. McCrea", + TITLE = "Exterior Calculus on the Computer: The {REDUCE}-Package +{EXCALC} Applied to General Relativity and to the {Poincar{\'e}} +Gauge Theory", + JOURNAL = "General Relativity and Gravitation", + YEAR = 1987, VOLUME = 19, NUMBER = 2, PAGES = "197-218", + MONTH = "February", + COMMENT = {Application of {EXCALC/REDUCE}, including review of other +systems, and description of {EXCALC}.}} + +@ARTICLE{Schruefer:88, + AUTHOR = "E. Schr{\"u}fer", + TITLE = "A Note on {Einstein} Metrics", + JOURNAL = "SIGSAM Bulletin", + YEAR = 1988, VOLUME = 22, NUMBER = 3, PAGES = "22-26", MONTH = "July"} + +@ARTICLE{Schwarz:80, + AUTHOR = "F. Schwarz", + TITLE = "An Approximation Scheme for Constructing $\pi_{0}\pi$ +Amplitudes from {ACU} Requirements", + JOURNAL = "Fortschritte der Physik", + YEAR = 1980, VOLUME = 28, PAGES = "201-235", + COMMENT = {"To derive the equations expressing the threshold and the +asymptotic behaviour one relies heavily on the programming system +{REDUCE}."}} + +@ARTICLE{Schwarz:82, + AUTHOR = "F. Schwarz", + TITLE = "Symmetries of the Two Dimensional {Korteweg-De Vries} Equation", + JOURNAL = "J. Phys. S. Japan", + YEAR = 1982, VOLUME = 51, NUMBER = 8, PAGES = "2387-2388", + COMMENT = {{REDUCE} used in the {SPDE} package.}} + +@ARTICLE{Schwarz:82a, + AUTHOR = "F. Schwarz", + TITLE = "A {REDUCE} Package for Determining {Lie} Symmetries of +Ordinary and Partial Differential Equations", + JOURNAL = "Computer Physics Communications", + YEAR = 1982, VOLUME = 27, PAGES = "179-186", + COMMENT = {Preliminary description of {REDUCE} packages {SODE} and +{SPDE}.}} + +@ARTICLE{Schwarz:83, + AUTHOR = "Fritz Schwarz", + TITLE = "A {REDUCE} Package for Series Analysis by {Hadamard's} +Theorem and {QD} Schemes", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1983, VOLUME = 17, NUMBER = 1, PAGES = "38-44", MONTH = "February"} + +@INPROCEEDINGS{Schwarz:83a, + AUTHOR = "Fritz Schwarz", + TITLE = "Automatically Determining Symmetries of Ordinary Differential +Equations", + BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes +in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "45-54", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Schwarz:84, + AUTHOR = "F. Schwarz", + TITLE = "The {Riquier-Janet} Theory and Its Application to Nonlinear +Evolution Equations", + JOURNAL = "Physica", + YEAR = 1984, VOLUME = "11D", PAGES = "243-251", + COMMENT = {Prologation methods in {REDUCE}. Points to existence of +{REDUCE} system.}} + +@ARTICLE{Schwarz:84a, + AUTHOR = "F. Schwarz and W. H. Steeb", + TITLE = "Symmetries and First Integrals for Dissipative Systems", + JOURNAL = "J. Phys. {A:} Math. Gen.", + YEAR = 1984, VOLUME = 17, PAGES = "L819-L823"} + +@ARTICLE{Schwarz:85, + AUTHOR = "F. Schwarz", + TITLE = "Automatically Determining Symmetries of Partial Differential +Equations", + JOURNAL = "Computing", + YEAR = 1985, VOLUME = 34, PAGES = "91-106", + COMMENT = {Describes the {SPDE} package for {REDUCE}.}} + +@ARTICLE{Schwarz:85a, + AUTHOR = "Fritz Schwarz", + TITLE = "An Algorithm for Determining Polynomial First Integrals of +Autonomous Systems of Ordinary Differential Equations", + JOURNAL = "J. Symbolic Computation", + YEAR = 1985, VOLUME = 1, NUMBER = 2, PAGES = "229-233", MONTH = "June"} + +@ARTICLE{Schwarz:86, + AUTHOR = "F. Schwarz", + TITLE = "A {REDUCE} Package for Determining First Integrals of +Autonomous Systems of Ordinary Differential Equations", + JOURNAL = "Computer Physics Communications", + YEAR = 1986, VOLUME = 39, PAGES = "285-296", + COMMENT = {Description of package {DISSYS} in {REDUCE}.}} + +@INPROCEEDINGS{Schwarz:87, + AUTHOR = "F. Schwarz", + TITLE = "Symmetries and Involution Systems: Some Experiments in +Computer Algebra", + YEAR = 1987, MONTH = "August", + BOOKTITLE = "Topics in Soliton Theory and Exactly Solvable Nonlinear +Equations", PUBLISHER = "World Science Press", ADDRESS = "Singapore", + COMMENT = {Description of algorithm {INVSYS} and applications.}} + +@ARTICLE{Schwarz:88, + AUTHOR = "F. Schwarz", + TITLE = "Symmetries of Differential Equations: From {Sophus Lie} to +Computer Algebra", + JOURNAL = "Siam Review", + YEAR = 1988, VOLUME = 30, PAGES = "450-481", + COMMENT = {Review article on applying the {REDUCE} package {SPDE}.}} + +@ARTICLE{Schwarz:94, + AUTHOR = "F. Schwarz", + TITLE = "Efficient Factorization of Linear {ODE's}", + JOURNAL = "Sigsam Bulletin", + YEAR = 1994, VOLUME = 28, NUMBER = 1, PAGES = "9-17", + ABSTRACT = {Factorization and testing for irreducibility has turned out to +be one of the most important algorithms for handling linear ode's. The +main hindrance for applying it is its trmendous complexity originating to a +large extent from solving certain Riccati equations which occur during the +factorization. The solution procedure for these Riccati equations is much +more manageable if it is subdivided into two major parts. At first so +called solution candidates are determined each of which depends only on the +parameters of a single irreducible denominator or the behavior at infinity. +In a second step it is tried to complete each candidate into a genuine +solution of the Riccati equation, possibly including an unspecified number +of additional first order poles. Furthermore a scheme is proposed for +running the factorization procedure in parallel on a two-processor machine +in which possible factors are searched for both from the right and the left +at the same time.}} + +@ARTICLE{Seiler:91, + AUTHOR = "Werner M. Seiler", + TITLE = "{SUPERCALC-} a {REDUCE} package for commutator calculations", + JOURNAL = "Computer Physics Communications", + YEAR = 1991, VOLUME = 66, PAGES = "363-376", + COMMENT = {A {REDUCE} package for commutator calculations in sypersymmetric +theories (including ordered products) and for infinite sums is presented +and an application to the computation of anomalies in string theory is +given.}} + +@INPROCEEDINGS{Shablygin:87, + AUTHOR = "E. Shablygin", + TITLE = "Integral Equation with Hidden Eigenparameter Solver: +{REDUCE} and {FORTRAN} in Tandem", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "186-191", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Shmueli:83, + AUTHOR = "U. Shmueli and A. J. C. Wilson", + TITLE = "Generalized Intensity Studies: The Subcentric Distribution +and Effects of Dispersion", + JOURNAL = "Acta Cryst.", + YEAR = 1983, VOLUME = "A39", PAGES = "225-233", + COMMENT = {Uses {REDUCE} for series expansion to high order as convergence +is slow.}} + +@ARTICLE{Shmueli:83a, + AUTHOR = "U. Shmueli and U. Kaldor", + TITLE = "Moments of the Trigonometric Structure Factor", + JOURNAL = "Acta Cryst.", + YEAR = 1983, VOLUME = "A39", PAGES = "615-621", + COMMENT = {Eight moment of magnitude of trigonometric structure factor. +Used {REDUCE}. Description of {REDUCE} in appendix.}} + +@TECHREPORT{Shtokhamer:75, + AUTHOR = "R. Shtokhamer", + TITLE = "Canonical Form of Polynomials in the Presence of +Side Relations", + INSTITUTION = "Technion", + YEAR = 1975, NUMBER = "Technion-PH-76-25"} + +@TECHREPORT{Shtokhamer:77, + AUTHOR = "R. Shtokhamer", + TITLE = "The Use of {``LET''} Statements in Producing Short +Comprehended Outputs", + INSTITUTION = "Department of Physics, Technion-Israel +Institute of Technology, Haifa, Israel", + YEAR = 1977, NUMBER = "Technion-PH-77-36", + ABSTRACT = {It is shown that an algebraic implementation of {"LET"} +statements may be useful in producing comprehended outputs. +The suggested algorithm is based on solving large set of +linear equations over a field.}} + +@INPROCEEDINGS{Smit:79, + AUTHOR = "J. Smit", + TITLE = "New Recursive Minor Expansion Algorithms, A Presentation in +a Comparative Context", + BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes +in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "74-87", +PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Smit:81, + AUTHOR = "J. Smit and J. A. van Hulzen and B. J. A. Hulshof", + TITLE = "{NETFORM} and Code Optimizer Manual", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1981, VOLUME = 15, NUMBER = 4, PAGES = "23-32", + MONTH = "November"} + +@INPROCEEDINGS{Smit:82, + AUTHOR = "J. Smit and J. A. van Hulzen", + TITLE = "Symbolic Numeric Methods in Microwave Technology", + BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes +in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "281-288", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{Smit:87, + AUTHOR = "J. Smit and S. H Gerez and R. Mulder", + TITLE = "Application of a Structured {LISP} System to Computer Algebra", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "149-160", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Soderstrand:72, + AUTHOR = "M. A. Soderstrand and D. C. Huey", + TITLE = "Sensitivities of Fourth-Order Filters Obtained by a +Low-Pass to Band-Pass Transformation", + INSTITUTION = "University of California, Davis", + YEAR = 1972, TYPE = "Report"} + +@INPROCEEDINGS{Soderstrand:72a, + AUTHOR = "M. A. Soderstrand and S. K. Mitra", + TITLE = "Computer-aided Sensitivity Analysis of Higher Filters", + YEAR = 1972, MONTH = "July", + BOOKTITLE = "Proc. Second Symposium on Network Theory, +Herzegnovia, Yugoslavia"} + +@TECHREPORT{Soderstrand:74, + AUTHOR = "M. A. Soderstrand and J. F. Lathrop", + TITLE = "Two Computer Programs for the Sensitivity Analysis +of Higher Order Filters", + INSTITUTION = "Sandia Laboratories", YEAR = 1974, + TYPE = "Report", NUMBER = "SLL-73-0225", MONTH = "January"} + +@ARTICLE{Soma:77, + AUTHOR = "T. Soma", + TITLE = "Relativistic Aberration Formulas for Combined +Electric-Magnetic Focusing-Deflection System", + JOURNAL = "Optik", + YEAR = 1977, VOLUME = 49, PAGES = "255-262", + COMMENT = {Existence of a vertical landing electron beam deflecting +system free of all deflection induced aberrations is +presented analytically.}} + +@INPROCEEDINGS{Soma:85, + AUTHOR = "Takashi Soma", + TITLE = "Recent Applications of {REDUCE} in {RIKEN}", + YEAR = 1985, + BOOKTITLE = "Proc. of the Second {RIKEN} International +Symposium on Symbolic and Algebraic Computation by Computers", + PUBLISHER = "World Scientific", ADDRESS = "Singapore", PAGES = "181-182"} + +@INPROCEEDINGS{Spiridonova:87, + AUTHOR = "M. Spiridonova", + TITLE = "Some extensions and Applications of {REDUCE} System", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "136-137", + PUBLISHER = "Springer-Verlag"} + +@TECHREPORT{Squire, + AUTHOR = "W. Squire", + TITLE = "Some Applications of Symbolic Matrix Inversion", + INSTITUTION = "Dept. of Mechanical and Aerospace Engineering, +West Virginia University"} + +@BOOK{Steeb:92b, + AUTHOR = "Willi-Hans Steeb and Dirk Lewien", + TITLE = "Algorithms and Computation with {REDUCE}", + PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", YEAR = 1992, + ABSTRACT ={This book gives a collection of 75 standard methods + in mathematics, physics and engineering together with their + programs in {REDUCE} 3.4. Each item consists of a one page mathematical + description and one page {REDUCE} algebraic source text (in most cases + a few lines only). The book is an introduction by example + to algebraic programming in {REDUCE} and a collection of + ready to use solutions for many mathematical subtasks}} + +@BOOK{Steeb:92c, + AUTHOR = "Willi-Hans Steeb", + TITLE = "Chaos and Fractals: Algorithms and Computations", + PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", + YEAR = 1992, + COMMENT = "This book includes 26 Turbo C and C++, 47 Turbo PASCAL +and 23 REDUCE programs"} + +@ARTICLE{Steeb:92d, + AUTHOR = "W-H Steeb", + TITLE = "Computer Algebra and Its Applications in Physics", + JOURNAL = "International Journal of Modern Physics C", + YEAR = 1992, VOLUME = 3, NUMBER = 6, PAGES = "1333-1350", + COMMENT = {Computer algebra is a powerful tool in the study of a wide +class of problems in mathematics, physics, and engineering. The primary +domain of computer algebra is the solution of large scale formal problems. +We give an introduction and survey on computer algebra. In particular we +show with examples how problems in physics can be solved. We also show +with an example how object-oriented programming can be used in such +problems.}} + +@ARTICLE{Steeb:93, + AUTHOR = "W-H Steeb", + TITLE = "Fermi Systems and Computer Algebra", + JOURNAL = "International Journal of Modern Physics C", + YEAR = 1993, VOLUME = 4, NUMBER = 4, PAGES = "841-846", + COMMENT = {Computer algebra is a helpful tool in studying Fermi systems. +We show how the anticommutation relations can be implemented with computer +algebra. Then we give an application to the Hubbard model.}} + +@BOOK{Steeb:93a, + AUTHOR = "W.-H Steeb", + TITLE = "Invertible Point Transformations and Nonlinear Differential +Equations", + PUBLISHER = "World Scientific Publishing", + YEAR = 1993} + +@BOOK{Steeb:94, + AUTHOR = "W.-H Steeb", + TITLE = "Chaos und Quantenchaos in dynamischen Systemen", + PUBLISHER = "Bi-Wissenschaftsverlag, Mannheim", + YEAR = 1994} + +@BOOK{Steeb:94a, + AUTHOR = "W.-H Steeb", + TITLE = "Quantum Mechanics using Computer Algebra", + PUBLISHER = "World Scientific Publishing, Singapore", + YEAR = 1994} + +@ARTICLE{Steeb:94b, + AUTHOR = "W-H Steeb", + TITLE = "Applications of Computer Algebra in Quantum Groups", + JOURNAL = "International Journal of Modern Physics C", + YEAR = 1994, VOLUME = 6, PAGES = "701-706"} + +@ARTICLE{Steeb:94c, + AUTHOR = "W-H Steeb", + TITLE = "Extended {Lorenz} Models and Time Dependent First Integrals", + JOURNAL = "Zeitschrift fuer Naturforschung", + YEAR = 1994, VOLUME = "49a", PAGES = "751-753"} + +@ARTICLE{Steeb:95, + AUTHOR = "W-H Steeb", + TITLE = "{Bose-Fermi} Systems and Computer Algebra", + JOURNAL = "Foundations of Physics Letters", YEAR = 1995} + +@ARTICLE{Steinberg:82, + AUTHOR = "Stanly Steinberg", + TITLE = "Mathematics and Symbol Manipulation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 3, PAGES = "11-15", MONTH = "August"} + +@InProceedings{Steinberg:93, + author = "S. Steinberg and R. Liska", + title = "Stability Analysis and Quantifier Elimination", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "62-67", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + comment = {Stability of time-stepping numerical schemes for partial + differential equations based on the {REDUCE} package FIDE + and the SACLIB package QEPCAD.} +} + +@ARTICLE{Steuerwald, + AUTHOR = "J. Steuerwald and W. Kerner", + TITLE = "A Contribution to the Efficient Solution of +Extensive Symbolic Computations", + JOURNAL = "Comp. Phys. Comm."} + +@ARTICLE{Stoutemyer:74, + AUTHOR = "D. Stoutemyer", + TITLE = "Automatic Error Analysis Using the Computer Symbolic +Manipulation Language", + JOURNAL = "TOMS 3", + YEAR = 1977, VOLUME = 3, NUMBER = 1, PAGES = "26-43", + MONTH = "March", + ABSTRACT = {This paper shows how the inherent error and the fixed-point +or floating-point roundoff of chopoff error of an expression can be +determined automatically using a computer algebra language such as +{REDUCE}.}} + +@TECHREPORT{Stoutemyer:75, + AUTHOR = "David R. Stoutemyer", + TITLE = "Symbolic Computer Solution of an Equation in Finite Terms", + INSTITUTION = "Dept. of Comp. Science, Univ. of Utah", + TYPE = "Report", YEAR = 1975, NUMBER = "UCP-33", + ABSTRACT = {This report contains a program listing together with +documentation, a demonstration, and discussion of a {REDUCE} program for the +exact solution of an equation in finite terms. Capable of treating certain +equations involving elementary transcendental functions, radicals, +and polynomials, the program incorporates several solution techniques +not implemented in existing analogous programs written in other +computer algebra languages. The program is also capable of solving +linear or linear fractional in the unknowns. In this case it simply +used the built-in matrix equation solver, but permitting input as +lists of expressions rather than matrices, which is convenient for +sparse or small linear systems.}} + +@ARTICLE{Stoutemyer:77, + AUTHOR = "David R. Stoutemyer", + TITLE = "Analytically Solving Integral Equations by Using Computer +Algebra", + JOURNAL = "TOMS", + YEAR = 1977, VOLUME = 3, NUMBER = 2, PAGES = "128-146", + MONTH = "June", + ABSTRACT = {This report describes how a computer algebra language, such as +{REDUCE}, may be used to automatically construct closed-form and series +analytical solutions of integral equations.}} + +@ARTICLE{Stroscio:74, + AUTHOR = "M. A. Stroscio and J. M. Holt", + TITLE = "Radiative Corrections to the Decay Rate of Orthopositronium", + JOURNAL = "Phys. Rev. A", + YEAR = 1974, MONTH = "September", VOLUME = 10, PAGES = "749-755"} + +@ARTICLE{Stuart:88, + AUTHOR = "Robin G. Stuart", + TITLE = "Algebraic Reduction of one-loop {Feynman} Diagrams to +Scalar Integrals", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1988, VOLUME = 48, NUMBER = 3, PAGES = "367-389", MONTH = "March"} + +@ARTICLE{Stuart:90, + AUTHOR = "Robin G. Stuart and A. G{\'o}ngora-T", + TITLE = "Algebraic Reduction of one-loop {Feynman} Diagrams to +Scalar Integrals II", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1990, VOLUME = 56, NUMBER = 3, PAGES = "337-350", MONTH = "January"} + +@ARTICLE{Suppes:89, + AUTHOR = "Patrick Suppes and Shuzo Takahashi", + TITLE = "An Interactive Calculus Theorem-prover for Continuity +Properties", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 7, NUMBER = 6, PAGES = "573-590", MONTH = "June"} + +@ARTICLE{Surguladze:89, + AUTHOR = "L.R. Surguladze and F.V. Tkachov", + TITLE = "{LOOPS:} Procedures for Multiloop Calculations in Quantum Field +Theory for the {REDUCE} System", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1989, VOLUME = 55, NUMBER = 2, PAGES = "205-215", + MONTH = "September", PUBLISHER = "North Holland Publishing Company"} + +@INPROCEEDINGS{Surguladze:91, + AUTHOR = "Levan R. Surguladze and Mark A. Samuel", + TITLE = "Algebraic Perturbative Calculations in High Energy Physics +Methods, algorithms, computer programs and physical applications", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "439-447", + ABSTRACT = {The methods and algorithms for high order algebraic +perturbative calculations in theoretical high energy physics are briefly +reviewed. The {SCHOONSCHIP} program {MINCER} and the {REDUCE} program +{LOOPS} for analytical computation of arbitrary massless, one-, two- +and three-loop Feynman diagrams of the propagator type are described. +The version of the program {LOOPS} for personal computers and the extended +version of the program {MINCER} for four-loop renormalization group +calculations are presented. The new program for algebraic perturbative +calculations is also discussed. This program is written on the new +algebraic programming system {FORM}. Some recent results of application +to the high energy physics are given.}} + +@ARTICLE{Tallents:84, + AUTHOR = "G. J. Tallents", + TITLE = "The Relative Intensities of Hydrogen-Like Fine Structure", + JOURNAL = "J. Phys. B", + YEAR = 1984, VOLUME = 17, PAGES = "3677-3691", + COMMENT = {{REDUCE} used to check a formula; also checked numerically.}} + +@InProceedings{Tao90, + author = "Qingsheng Tao", + title = "Symbolic and Algebraic manipulation for Formulae of + Interpolation and Quadrature", + booktitle = "Proceedings of the 1990 International Symposium on + Symbolic and Algebraic Computation", + year = "1990", + editor = "S. Watanabe and Morio Nagata", + pages = "306", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@TECHREPORT{Tasso:76, + AUTHOR = "H. Tasso and J. Steuerwald", + TITLE = "Subroutine for Series Solutions of Linear Differential Equations", + INSTITUTION = "Max Planck Institut for Plasmaphysik", + YEAR = 1976, NUMBER = "IPP 6/143"} + +@TECHREPORT{Thas:89, + AUTHOR = "C. Thas", + TITLE = "A collection of {REDUCE} and {MACSYMA} programs about college +geometry. Part 1", + INSTITUTION = "State University of Gent", + YEAR = 1989, NUMBER = 5, MONTH = "September"} + +@TECHREPORT{Thas:89a, + AUTHOR = "C. Thas", + TITLE = "A collection of {REDUCE} and {MACSYMA} programs about college +geometry. Part 2", + INSTITUTION = "State University of Gent", + YEAR = 1989, NUMBER = 5, MONTH = "September"} + +@INPROCEEDINGS{Todd:88, + AUTHOR = "P. H. Todd and G. W. Cherry", + TITLE = "Symbolic Analysis of Planar Drawings", + BOOKTITLE = "Proc. of {ISSAC} '88", PUBLISHER = "Springer-Verlag", + YEAR = 1988, VOLUME = 358, PAGES = "344-355"} + +@ARTICLE{Toth:86, + AUTHOR = "K. T{\'o}th and K. Szeg{\"o} and A. Margaritis", + TITLE = "Radiative Corrections for Semileptonic Decays of {Hyperons: +`Model-Independent' Part}", + JOURNAL = "Physical Review D", YEAR = 1986, VOLUME = 33, NUMBER = 11, + PAGES = "3306-3315", MONTH ="June"} + +@INPROCEEDINGS{Tournier:79, + AUTHOR = "Evelyne Tournier", + TITLE = "An Algebraic Form of a Solution of a System +of Linear Differential Equations with Constant Coefficients", + BOOKTITLE = "Proc. {EUROSAM} 1979, Lecture Notes +in Computer Science", YEAR = 1979, VOLUME = 72, PAGES = "153-163", + PUBLISHER = "Springer-Verlag", + ABSTRACT = {In this paper we describe an algorithm for finding an +algebraic form for the solution of a system of linear differential +equations with constant coefficients, using the properties of elementary +divisors of a polynomial matrix.}} + +@PHDTHESIS{Tournier:87, + AUTHOR = "Evelyne Tournier", + TITLE = "Solutions Formelles D'Equations Differentielles, +le Logiciel de Calcul Formel: {DESIR} Etude Theorique +et Realisation", + SCHOOL = "L'Universit{\'e} Scientifique, Technologique et +Medicale de Grenoble", + YEAR = 1987, MONTH = "April"} + +@INPROCEEDINGS{Trenkov:91, + AUTHOR = "I. Trenkov and M. Spiridonova and M. Daskalova", + TITLE = "An Application of the {REDUCE} System for Solving a Mathematical +Geodesy Problem", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "448-449"} + +@INPROCEEDINGS{Trotter:89, + AUTHOR = "H. F. Trotter", + TITLE = "Use of Symbolic Methods in Analyzing an Integral Operator", + BOOKTITLE = "Proc. of Computers and Mathematics '89", + EDITOR = "E. Kaltofen and S. M. Watt", + YEAR = 1989, PAGES = "82-90", PUBLISHER = "Springer-Verlag, New York"} + +@ARTICLE{Tsai:65, + AUTHOR = "Y. S. Tsai and A. C. Hearn", + TITLE = "Differential Cross-Section for e+ + e- $\rightarrow$ {W+} + +{W-} $\rightarrow$ e- + $\overline{\nu}_{e} + \mu + \nu_{\mu}$", + JOURNAL = "Phys. Rev.", + YEAR = 1965, VOLUME = 140, PAGES = "B721-B729"} + +@ARTICLE{Tsai:74, + AUTHOR = "Y. S. Tsai", + TITLE = "Pair Production and Bremsstrahlung of Charged Leptons", + JOURNAL = "Rev. Mod. Phys.", + YEAR = 1974, VOLUME = 46, PAGES = "815-851"} + +@ARTICLE{Ucoluk:82, + AUTHOR = "G. {\"U}\c{c}oluk and A. Hacinliyan", + TITLE = "A Proposal for Extensions to {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 2, PAGES = "4-14", MONTH = "May", + ABSTRACT = {Three classes of extensions are proposed for {REDUCE}: A +facility for evaluating arbitrary functions of matrices; a facility for +grouping, modifying or restoring the status of various flags +in {REDUCE}; further extensions and modifications for separating +terms, coefficients of expressions, concatenation, and non- +commuting algebra.}} + +@BOOK{Ueberberg:92, + AUTHOR = "Johannes Ueberberg", + TITLE = "Einf{\"u}hrung in die computeralgebra mit {REDUCE}", + PUBLISHER = "BI-Wissenschaftsverlag, Mannheim", + YEAR = 1992} + +@ARTICLE{Umeno:89, + AUTHOR = "Takaji Umeno and Syuichi Yamashita and Osami Saito and +Kenichi Abe", + TITLE = "Symbolic Computation Application for the Design of Linear +Multivariable Control Systems", + JOURNAL = "J. Symbolic Computation", + YEAR = 1989, VOLUME = 8, NUMBER = 6, PAGES = "581-588", MONTH = "December"} + +@INPROCEEDINGS{Urintsev:91, + AUTHOR = "A.L. Urintsev and A.V. Samoilov", + TITLE = "Complex Reduce-programs for analytic solution of some problems of +beam transport systems", + YEAR = 1991, + BOOKTITLE = "In: 4th International Conference on Computer Algebra in +Physical Research", + EDITOR = "D.V. Shirkov and V.A. Rostovtsev and V.P. Gerdt", + PUBLISHER = "World Scientific", ADDRESS = "Singapore, New Jersey, London, +Hong Kong", PAGES = "438-442"} + +@ARTICLE{vandenHeuvel:86, + AUTHOR = "Pim van den Heuvel", + TITLE = "Adding Statements to {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1986, VOLUME = 20, NUMBER = "1 and 2", PAGES = "8-14", + MONTH = "February and May"} + +@TECHREPORT{vandenHeuvel:86a, + AUTHOR = "Pim van den Heuvel", + TITLE = "Some Experiments in {REDUCE} Related to the +Calculation of {Groebner} Bases", + INSTITUTION = "Department of Computer Science, Twente +University of Technology, The Netherlands", + YEAR = 1986, MONTH = "June"} + +@INPROCEEDINGS{vandenHeuvel:87, + AUTHOR = "P. van den Heuvel and J. A. van Hulzen and V. V. Goldman", + TITLE = "Automatic Generation of {FORTRAN}-Coded {Jacobians} and +{Hessians}", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "120-131", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{vandenHeuvel:87a, + AUTHOR = "P. van den Heuvel and B. J. A. Hulshof and J. A. van Hulzen", + TITLE = "Some Simple Pretty-Print Facilities for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1987, VOLUME = 21, NUMBER = 1, PAGES = "14-17", MONTH = "February"} + +@TECHREPORT{vanHeerwaarden, + AUTHOR = "M. C. van Heerwaarden and J. A. van Hulzen", + TITLE = "Pretty Print Facilities for {REDUCE}", + INSTITUTION = "Department of Computer Science, University +of Twente, The Netherlands", + YEAR = 1988, TYPE = "Memorandum", + NUMBER = "INF-88-36", MONTH = "August"} + +@ARTICLE{vanHulzen:80, + AUTHOR = "J. A. van Hulzen", + TITLE = "Computational Problems in Producing {Taylor} Coefficients +for the Rotating Disk Problem", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1980, VOLUME = 14, NUMBER = 2, PAGES = "36-49", MONTH = "May"} + +@TECHREPORT{vanHulzen:81, + AUTHOR = "J. A. van Hulzen", + TITLE = "Breuer's Grow Factor Algorithm in Computer Algebra", + INSTITUTION = "Department of Applied Mathematics, Twente University +of Technology, The Netherlands", + YEAR = 1981, TYPE = "Memorandum", NUMBER = 332, MONTH = "April", + COMMENT = {A shorter version appears in: Proceedings SYMSAC 81 + (Paul S. Wang, ed.) ACM, August 1981.}} + +@ARTICLE{vanHulzen:82, + AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof", + TITLE = "An Expression Analysis Package for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1982, VOLUME = 16, NUMBER = 4, PAGES = "32-44", MONTH = "November"} + +@INPROCEEDINGS{vanHulzen:82a, + AUTHOR = "J. A. van Hulzen", + TITLE = "Computer Algebra Systems Viewed by a Notorious User", + BOOKTITLE = "Proc. {EUROCAM} 1982, Lecture Notes +in Computer Science", YEAR = 1982, VOLUME = 144, PAGES = "166-180"} + +@INCOLLECTION{vanHulzen:83, + AUTHOR = "J. A. van Hulzen and J. Calmet", + TITLE = "Computer Algebra Systems", + EDITOR = "B. Buchberger and G. E. Collins and R. Loos and R. Albrecht", + BOOKTITLE = "Computer Algebra and Symbolic and Algebraic Computation", + EDITION = "2nd", PUBLISHER = "Springer-Verlag", YEAR = 1983} + +@INPROCEEDINGS{vanHulzen:83a, + AUTHOR = "J. A. van Hulzen", + TITLE = "Code Optimization of Multivariate Polynomial Schemes: A +Pragmatic Approach", + BOOKTITLE = "Proc. {EUROCAL} 1983, Lecture Notes +in Computer Science", YEAR = 1983, VOLUME = 162, PAGES = "286-300", + PUBLISHER = "Springer-Verlag"} + +@INPROCEEDINGS{vanHulzen:87, + AUTHOR = "J. A. van Hulzen", + TITLE = "Program Generation Aspects of the Symbolic-Numeric Interface", + BOOKTITLE = "Proc. Third Intern. Conf. on Computer Algebra and its +applications in Theor. Phys, 1985", YEAR = 1987, PAGES = "104-113", + PUBLISHER = "{J.I.N.R., Dubna, USSR}"} + +@TECHREPORT{vanHulzen:88, + AUTHOR = "J. A. van Hulzen", + TITLE = "Formule Manipulatie m.b.v. {REDUCE} (in {Dutch})", + INSTITUTION = "Department of Computer Science, Twente University +of Technology, The Netherlands", + YEAR = 1988, MONTH = "October"} + +@INPROCEEDINGS{vanHulzen:89, + AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof and B. L. Gates and +M. C. Van Heerwaarden", + TITLE = "A Code Optimization Package for {REDUCE}", + BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", + YEAR = 1989, PAGES = "163-170", + COMMENT = {Lecture Notes.}} + +@TECHREPORT{vanHulzen:89a, + AUTHOR = "J. A. van Hulzen", + TITLE = "Computer Algebra and Numerical Mathematics: The Odd Couple?", + INSTITUTION = "Department of Computer Science, Twente University +of Technology, The Netherlands", + NUMBER = "Informatica 89-40", + YEAR = 1989, MONTH = "June"} + +@TECHREPORT{VanProeyan:76, + AUTHOR = "A. Van Proeyen", + TITLE = "Quantum Gravity Corrections on the Anomalous +Magnetic and Quadrupole Moments of a Spin-1 Particle", + INSTITUTION = "Instituut voor Theor. Fys., Leuven", + YEAR = 1976, MONTH = "October"} + +@TECHREPORT{VanProeyan:79, + AUTHOR = "A. Van Proeyan", + TITLE = "Gravitational Divergences of the Electromagnetic +Interactions of Massive Vectorparticles", + INSTITUTION = "Universiteit Leuven", + YEAR = 1979, TYPE = "Preprint", NUMBER = "KUL-TF-79/032", + MONTH = "October", + ABSTRACT = {In a search for the explanation of the finite quantum +gravity corrections to anomalous moments we examined a +spontaneous broken 0(3) model with Yang-Mills particles +and Higgs scalars coupled to gravitons.}} + +@INPROCEEDINGS{Vega:91, + AUTHOR = "Laureano Gonz{\'a}lez Vega", + TITLE = "Working with Real Algebraic Plane Curves in {REDUCE:} the +{GCUR} package", + YEAR = 1991, MONTH = "July", + BOOKTITLE = "Proc. of the 1991 International Symposium on Symbolic and +Algebraic Computation", + EDITOR = "Stephen M. Watt", PUBLISHER = "ACM Press", ADDRESS = "Maryland", + PAGES = "397-402"} + +@TECHREPORT{Vinitsky:87, + AUTHOR = "S. I. Vinitsky and V. A. Rostovtsev", + TITLE = "A Use of {REDUCE} System in Problems of +Hydrogen Atom in an Electric Field", + INSTITUTION = "J.I.N.R., Dubna", TYPE = "Preprint", + YEAR = 1987, NUMBER = "P11-87-303"} + +@ARTICLE{Viry:93, + AUTHOR = "Guy Viry", + TITLE = "Factorization of Multivariate Polynomials with Coefficients in +$F_{p}$", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, VOLUME = 15, NUMBER = 4, PAGES = "371-391", MONTH = "November", + COMMENT = {The ring of polynomials in $X,X_{1}, \1dots ,X_{m}$ are denoted +by $F_{p}[X,X_{1}, \1dots ,X_{m}]$ in $F_{p}$, that is the field of +integers defined modulo $p$. In the usual factorization algorithm defined +by Wang, the given polynolmial $P$ is first factorized modulo $\Delta^{n}$, +where $\Delta^{n}$ is an ideal. This algorithm uses a generalization of +Hensel's Lemma. If there are no extraneous factors, then the factors +defined modulo $\delta^[{n}$ correspond to the factors of $P$ in +$F_{p}[X,X_{1}, \1dots ,X_{m}]$ or else the defined factors must be +regrouped to find the factors of $P$ in $F_{p}[X,X_{1}, \1dots ,X_{m}]$. +In this paper, a mapping that transforms the product of the factors into a +sum is defined. A theorem that determines whether a subproduct of the +factors of $P$ corresponds to a factor of $P$ in $F_{p}[X,X_{1}, \1dots +,X_{m}]$ is given. Therefore the regrouping of the factors of $P$ reduces +to solving a system of linear equations, as in the univariate case, with +Berlekamp's algorithm.}} + +@ARTICLE{Voros:77, + AUTHOR = "A. Voros", + TITLE = "Asymptotic K-Expansions of Stationary Quantum States", + JOURNAL = "Ann. Inst. H. Poincare", + YEAR = 1977, VOLUME = "26A", PAGE = "343"} + +@TECHREPORT{Wanas, + AUTHOR = "M. I. Wanas", + TITLE = "The Third Face of Computer -- Computer Solution +of Symbolic Problems", + INSTITUTION = "Military Technical College, Cairo, Egypt", + NUMBER = "CAP-3 837"} + +@INPROCEEDINGS{Wanas:85, + AUTHOR = "M. I. Wanas", + TITLE = "Manipulation of Parameters Indicating the +Physical Significance of any Absolute Parallelism +Space Using {REDUCE} 2", + YEAR = 1985, + BOOKTITLE = "Tenth International Congress for Statistics, +Computer Science, Social and Demographic Research"} + +@INPROCEEDINGS{Wang:84, + AUTHOR = "Paul S. Wang and T. Y. P. Chang and J. A. van Hulzen", + TITLE = "Code Generation and Optimization for Finite Element Analysis", + BOOKTITLE = "Proc. {EUROSAM} 1984, Lecture Notes +in Computer Science", YEAR = 1984, VOLUME = 174, PAGES = "237-247", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Wang:93, + AUTHOR = "Jian-Xiong Wang", + TITLE = "Automatic calculation of {Feynman loop-diagrams}, I. Generation +of a simplified form of the amplitude", + YEAR = 1993, VOLUME = 77, NUMBER = 2, PAGES = "263-285", MONTH = "October"} + ABSTRACT = {In order to develop an automatic system to calculate loop +diagrams in renormalizable theories, we present the first part of a +complete system written in {REDUCE} and {RLISP}. It can generate the tensor +and gamma matrix basis which is able to cast the total amplitude into a +simpler form with the help of gauge invariance and symmetry among identical +particles.} + +@ARTICLE{Wassam:87, + AUTHOR = "W. A. {Wassam, Jr.} and Go. Torres-Vega", + TITLE = "Dual {Lanczos} Transformation Theory: Closed Set of Algebraic +Equations Connecting {Lanczos} Parameters with Moments in Moment +Expansions of Time-Dependent Quantities", + JOURNAL = "Chemical Phys. Lett.", + YEAR = 1987, VOLUME = 134, NUMBER = 4, PAGES = "355-360", + COMMENT = {"The utility of this set of equations is illustrated by using +them with the aid of symbolic manipulation on a computer to construct a +previously unknown exact continued fraction for the spectral density +of the incoherent scattering function{\ldots}" The system used is {REDUCE} +on a Burroughs. Appear enthusiastic about the possibilities for +computer algebra in related fields.}} + +@ARTICLE{Wassam:87a, + AUTHOR = "W. A. {Wassam, Jr.} and Go. Torres-Vega and J. Neito-Frausto", + TITLE = "Dual {Lanczos} Transformation Theory: Exact Continued +Fraction Expression for Resonant $\gamma$-ray Absorption Spectrum of a +Harmonically Bound Atom Executing Classical Motion Described by +{Smoluchowski} Dynamics", + JOURNAL = "Chemical Phys. Lett.", + YEAR = 1987, VOLUME = 136, NUMBER = 1, PAGES = "26-30", + COMMENT = {"{\ldots}with the aid of symbolic manipulation techniques, we +construct a previously unknown exact continued fraction for the resonance +$\gamma$-ray absorption spectrum{\dots}" The system used is {REDUCE} +on a Burroughs.}} + +@TECHREPORT{Watanabe:85, + AUTHOR = "Yoichi Watanabe", + TITLE = "Symbolic Manipulation of Structure Functions +in Availability Analysis", + INSTITUTION = "Fusion Technology Institute, University of +Wisconsin, Madison, Wisconsin", + YEAR = 1985, NUMBER = "UWFDM-658", MONTH = "November"} + +@ARTICLE{Watanabe:76, + AUTHOR = "Shunro Watanabe", + TITLE = "Formula Manipulations Solving Linear Ordinary +Differential Equations {II}", + JOURNAL = "Publications of the Research Institute for +Mathematical Sciences, Kyoto University", + YEAR = 1976, VOLUME = 11, NUMBER = 2, PAGES = "297-337"} + +@ARTICLE{Watanabe:79, + AUTHOR = "Shunro Watanabe", + TITLE = "A Verification for Non-existence of Movable Branch Points of Six +Painlev{\'e} Transcendents by Formula Manipulations", + JOURNAL = "Tokyo Journal of Mathematics", + YEAR = 1979, VOLUME = 2, NUMBER = 2, PAGES = "285-291"} + +@ARTICLE{Weber:79, + AUTHOR = "Lawrence A. Weber and Gerhard Rayna", + TITLE = "Problem \#11 Solved in {REDUCE:} A Case Study in Program +Translation", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1979, VOLUME = 13, NUMBER = 4, PAGES = "21-24", MONTH = "November"} + +@ARTICLE{Wehner:86, + AUTHOR = "M. F. Wehner and W. G. Wolfer", + TITLE = "The Pressure of a Hard Sphere Fluid on a Curved Surface", + JOURNAL = "J. Statistical Phys.", + YEAR = 1986, VOLUME = 42, PAGES = "509-521", + COMMENT = {Integral equation approach and perturbation expansions in +{REDUCE}. "Therefore, in order to avoid errors, the integrations have been +done in closed form with the algebraic manipulation routine {REDUCE}."}} + +@InProceedings{Weispfenning:94, + author = {Volker Weispfenning}, + title = {Quantifier elimination for real algebra -- the cubic case}, + booktitle = {Symbolic and Algebraic Computation}, + editor = {}, + series = {ISSAC}, + year = {1994}, + organization = {SIGSAM}, + publisher = {ACM}, + pages = {258--263} +} + +@INCOLLECTION{Winkelmann:89, + AUTHOR = "Volker Winkelmann and Friedrich W. Hehl", + TITLE = "{REDUCE} for Beginners. Six Lectures on the +Application of Computer Algebra", + EDITOR = "D. Stauffer and F. W. Hehl and V. Winkelmann and +J. G. Zabolitzky", + BOOKTITLE = "Computer Simulation and Computer Algebra. +Lectures for Beginners", + CHAPTER = 3, EDITION = "2nd", PUBLISHER = "Springer-Verlag", + YEAR= 1989} + +@TECHREPORT{Winkler:88, + AUTHOR = "F. Winkler and B. Kutzler and F. Lichtenberger", + TITLE = "Computeralgebrasysteme (in {German})", + INSTITUTION = "RISC - LINZ, Austria", TYPE = "Report", + YEAR = 1988, NUMBER = "88-10"} + +@ARTICLE {Witham:77, + AUTHOR = "C. R. Witham and S. Dubowsky", + TITLE = "An Improved Symbolic Manipulation Technique for +the Simulation of Nonlinear Dynamic Systems With Mixed +Time-Varying and Constant Terms", + JOURNAL = "Journal of Dynamic Systems, Measurement, and Control", + YEAR = 1977, MONTH = "September", PAGES = "157-165", + ABSTRACT = {The time domain behavior of nonlinear dynamic systems +often is obtained by numerical integration on the digital +computer. These solutions are usually expensive and limit +the scope of the dynamic study. The proposed improved +technique results in a substantial increase in the computational +efficiency by using automatic symbolic manipulation to generate +explicit equations of motion algebraically prior to numerical +integration.}} + +@TECHREPORT{Wolf:95, + AUTHOR = "Thomas Wolf", + TITLE = "Programs for Applying Symmetries of PDEs", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1995, TYPE = "Preprint", NUMBER = "SC 95-5", MONTH = "February", + ABSTRACT = {In this paper the programs APPLYSYM, QUASILINPDE and DETRAFO +are described which aim at the utilization of infinitesimal symmetries of +differential equations. The purpose of QUASILINPDE is the general solution +of quasilinear PDEs. This procedure is used by APPLYSYM for the +application of point symmetries for either + +calculating similarity variables to perform a point transformation which +lowers the order of an ODE or effectively reduces the number of explicitly +occuring independent variables in a PDE(-system) or for + +generalizing given special solutions of ODEs/PDEs with new constant +parameters. + +The program DETRAFO performs arbitrary point- and contact transformations +of ODEs/PDEs and is applied if similarity and symmetry variables have been +found. The program APPLYSYM is used in connection with the program LIEPDE +for formulating and solving the conditions for point- and contact +symmetries which is described in [4]. The actual problem solving is done +in all these programs through a call to the package CRACK for solving +overdetermined PDE-systems.}} + +@ARTICLE{Wood:89, + AUTHOR = "John C. Wood", + TITLE = "Harmonic Two Spheres in the Unitary Group", + YEAR = 1989, + JOURNAL = "Proc. London Math. Soc.", + VOLUME = 3, NUMBER = 58, PAGES = "608-624"} + +@TECHREPORT{Wright:84, + AUTHOR = "F. J. Wright and G. Dangelmayr", + TITLE = "Explicit Iterative Algorithms to Reduce a Univariate Catastrophe +to Normal Form", + INSTITUTION = "Universit{\"a}t T{\"u}bingen", + YEAR = 1984} + +@TECHREPORT{Wulkow:90, + AUTHOR = "Michael Wulkow and Peter Deuflhard", + TITLE = "Towards an efficient computational treatment of heterogeneous +polymer reactions", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik Berlin", + YEAR = 1990, TYPE = "Preprint", NUMBER = "SC 90-1", MONTH = "January"} + +@INPROCEEDINGS{Yamamoto:87, + AUTHOR = "T. Yamamoto and Y. Aoki", + TITLE = "{REDUCE} 3.2 on {iAPX 86/286}-based Personal Computers", + BOOKTITLE = "Proc. {EUROCAL} '87, Lecture Notes +in Computer Science", YEAR = 1987, VOLUME = 378, PAGES = "134-135", + PUBLISHER = "Springer-Verlag"} + +@ARTICLE{Yamartino:91, + AUTHOR = "Robert J. Yamartino and Richard Pavelle", + TITLE = "An Application of Computer Algebra to a Problem in Stratified +Fluid Flow", + JOURNAL = "J. Symb. Comp.", + YEAR = 1991, VOLUME = 12, NUMBER = 6, PAGES = "669-672", MONTH = "December", + ABSTRACT = {The computationally tedious problem of considering trial Green's +function solutions to the fourth-order partial differential equation for a +stratified atmosphere flowing over a hill is approached using MACSYMA. +Significance of the problem, solution methodologies and CPU time +intercomparisons using various computer platforms and other algebra systems +are discussed.}} + +@ARTICLE{Yannouleas:88, + AUTHOR = "C. Yannouleas and J. M. Pacheco", + TITLE = "An Algebraic Program for the States Associated with the +${U(5)} \supset {O(5)} \supset {O(3)}$ Chain of Groups", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1988, VOLUME = 52, NUMBER = 1, PAGES = "85-92", MONTH = "December"} + +@ARTICLE{Yannouleas:89, + AUTHOR = "C. Yannouleas and J. M. Pacheco", + TITLE = "Algebraic Manipulation of the States Associated with the +${U(5)} \supset {O(5)} \supset {O(3)}$ Chain of {groups:} +Orthonormalization and Matrix Elements", + JOURNAL = "Comp. Phys. Comm.", + YEAR = 1989, VOLUME = 54, NUMBER = "2 and 3", PAGES = "315-328", +MONTH = "June and July"} + +@ARTICLE{Zacrep:75, + AUTHOR = "Douglas Zacrep and Bing-Lin Young", + TITLE = "Trace and {Ward-Takahashi} Identity Anomalies +in an {SU}(3) Current Model with Energy-Momentum Tensor", + JOURNAL = "Phys. Rev. D", + YEAR = 1975, VOLUME = 12, PAGES = "513-522"} + +@ARTICLE{Zahalak:87, + AUTHOR = "G. I. Zahalak and P. R. Rao and S. P. Sutera", + TITLE = "Large Deformations of a Cylindrical Liquid-Filled Membrane +by a Viscous Shear Flow", + JOURNAL = "J. Fluid Mech.", + YEAR = 1987, VOLUME = 179, PAGES = "283-305", + COMMENT = {Draws attention to the use of classical perturbation +techniques combined with computer algebra as an alternative to +numerical calculation.}} + +@ARTICLE{Zeng:84, + AUTHOR = "{Wan-zhen} Zeng and {Bail-lin} Hao", + TITLE = "Scaling Property of Period-n-Tupling +Sequences in One-Dimensional Mappings", + JOURNAL = "Commun. in Theor. Phys., Beijing, China", + YEAR = 1984, VOLUME = 3, NUMBER = 3, PAGES = "283-295"} + +@ARTICLE{Zharkov:93, + AUTHOR = "A. Yu. Zharkov", + TITLE = "Computer Classification of the Integrable Coupled {Kdv}-like +Systems with Unit Main Matrix", + JOURNAL = "J. Symbolic Computation", + YEAR = 1993, VOLUME = 15, NUMBER = 1, PAGES = "85-90", MONTH = "January", + COMMENT = {The classification of 2-component systems of equations for +the form $u^{i}_{t}=u^{i}_{xxx}+c_{ij}u^{i}u^{j}_{x}(i,j=1,2)$ which +possess higher symmetries is given. A new class of such integrable +KdV-like systems is obtained. All the computations have been done using +the {REDUCE}computer algebra system.}} + +@InProceedings{Zharkov:93a, + author = "A. Yu. Zharkov and Yu. A. Blinkov", + title = "Involution Approach to Solving Systems of Algebraic +Equations", + booktitle = "Proceedings of the 1993 International IMACS Symposium on + Symbolic Computation", + year = "1993", + editor = "G. Jacob and N. E. Oussous and S. Steinberg", + pages = "11-16", + organization ="IMACS", + publisher = "Laboratoire d'Informatique Fondamentale de Lille, France", + + comment = {An "involutive set" is a canonical basis of a 0-dim + polynomial ideal based on Janet division and well suited for + equation solving. It can be transformed into a + lexicographic Groebner basis by linear algebra tools. + The algorithms for computing involutive sets has been + developed using {REDUCE}.} +} + +@TECHREPORT{Zhidkova:78, + AUTHOR = "I. E. Zhidkova and I. P. Nedyalkov and V. A. Rostovtsev", + TITLE = "On Applicability Limits of the Experimental Method +for Investigating Strong Gravitational Fields", + INSTITUTION = "J.I.N.R., Dubna", + YEAR = 1978, NUMBER = "P2 - 11589", + COMMENT = {Mechanical effects of tidal forces on the physical apparatus +exploring strong gravitational fields are investigated.}} + Index: r36/doc/BIBL.TEX ================================================================== --- r36/doc/BIBL.TEX +++ r36/doc/BIBL.TEX @@ -1,870 +1,870 @@ -% The following UNIX script will create a hard copy version of the -% REDUCE bibliography from this file and the bibliography files -% bibl-*.bib. It creates the files tmp.* in the process. -% -% # Make REDUCE bibliography -% rm tmp.* -% cat bibl.tex > tmp.tex -% cat bibl*.bib > tmp.bib -% bib2tex tmp | sed 1,5d >> tmp.tex -% latex tmp -% bibtex tmp > tmp.blog -% latex tmp -% latex tmp -% -\documentstyle [11pt]{article} -\def\thebibliography#1{\section*{}\list - {[\arabic{enumi}]}{\settowidth\labelwidth{[#1]}\leftmargin\labelwidth - \advance\leftmargin\labelsep - \usecounter{enumi}} - \def\newblock{\hskip .11em plus .33em minus .07em} - \sloppy\clubpenalty4000\widowpenalty4000 - \sfcode`\.=1000\relax} -\textwidth 6.6in\textheight 9in\columnwidth\textwidth -\hoffset-2cm -\begin{document} -\setcounter{page}{0} -\title{REDUCE Bibliography} -\author{Anthony C. Hearn\\ -RAND \\ -Santa Monica CA 90407-2138 \vspace {.5cm} \\ -July 1995} -\date{} -\maketitle -\vspace{1cm} -This document contains a list of all known references to REDUCE. It no doubt -contains errors and omissions. Please report these by regular mail -(preferably in BibTeX format) to the REDUCE Secretary, RAND, P.O. Box 2138, -Santa Monica CA 90407-2318, or by electronic mail to reduce@rand.org. An -electronic copy of the bibliography in BibTeX format is also available from -the latter address. -\begin{center} -\vspace{9.0cm} -RAND Publication CP162 (Rev. 7/95) \vspace*{.5cm} \\ -Copyright \copyright 1995 RAND. All rights reserved. -\end{center} -\newpage -\voffset-2.5cm - -\nocite{Abbott:85} -\nocite{Abbott:86} -\nocite{Abbott:87} -\nocite{Abbott:87a} -\nocite{Abbott:88} -\nocite{Abbott:88a} -\nocite{Abbott:89} -\nocite{Abbott:89a} -\nocite{Abdali:88} -\nocite{Abiezzi:83} -\nocite{Abramov:91} -\nocite{Abramov:91a} -\nocite{Adamchik90} -\nocite{Adams:83} -\nocite{Adkins:83} -\nocite{Adkins:83a} -\nocite{Adkins:85} -\nocite{Aguilera-Navarro:87} -\nocite{Akselrod:90} -\nocite{Aldins:69} -\nocite{Alekseev:86} -\nocite{Alekseev:87} -\nocite{Alekseev:87a} -\nocite{Alfeld:82} -\nocite{Amirkhanov:87} -\nocite{Amirkhanov:91} -\nocite{Antweiler:89} -\nocite{Appelquist:70} -\nocite{Arbuzov:86} -\nocite{Kendall:93} -\nocite{Aso:81} -\nocite{Atherton:73} -\nocite{Aurenche:84} -\nocite{Aurenche:84a} -\nocite{Autin:89} -\nocite{Baekler:84} -\nocite{Baekler:84a} -\nocite{Baekler:86} -\nocite{Baekler:87} -\nocite{Baekler:87a} -\nocite{Baekler:87b} -\nocite{Baekler:88} -\nocite{Baekler:88a} -\nocite{Baekler:88b} -\nocite{Bahrdt:90} -\nocite{Baier:81} -\nocite{Baier:85} -\nocite{Baier:90} -\nocite{Bajla:78} -\nocite{Balian:78} -\nocite{Baker:81} -\nocite{Barbier:92} -\nocite{Barfoot:86} -\nocite{Barfoot:87} -\nocite{Barfoot:88} -\nocite{Bark:78} -\nocite{Barthes-Biesel:73} -\nocite{Barton:72} -\nocite{Bateman:86} -\nocite{Belkov:91} -\nocite{Bennett:88} -\nocite{Bennett:93} -\nocite{Berends:81} -\nocite{Berkovich:89} -\nocite{Berkovich:90} -\nocite{Berman:63} -\nocite{Berndt:91} -\nocite{Bessis:85} -\nocite{Bilge:92} -\nocite{Billoire:78} -\nocite{Biro:86} -\nocite{Biro:87} -\nocite{Birrell:77} -\nocite{Biswas:75} -\nocite{Bittencourt:90} -\nocite{Blum:93} -\nocite{Bocko:92} -\nocite{Boege:86} -\nocite{Bogdanova:88} -\nocite{Bordoni:81} -\nocite{Borst:94} -\nocite{Bowyer:87} -\nocite{Boyd:78} -\nocite{Boyd:93} -\nocite{Brackx:87} -\nocite{Brackx:87a} -\nocite{Brackx:89} -\nocite{Brackx:92} -\nocite{Bradford:86} -\nocite{Bradford:88} -\nocite{Bradford90} -\nocite{Broadhurst:83} -\nocite{Broadhurst:84} -\nocite{Broadhurst:85} -\nocite{Broadhurst:85a} -\nocite{Broadhurst:86} -\nocite{Broadhurst:87} -\nocite{Broadhurst:90} -\nocite{Broadhurst:91} -\nocite{Broadhurst:91a} -\nocite{Broadhurst:91b} -\nocite{Broadhurst:92} -\nocite{Broadhurst:92a} -\nocite{Broadhurst:93} -\nocite{Broadhurst:93a} -\nocite{Broadhurst:94} -\nocite{Brodsky:62} -\nocite{Brodsky:67} -\nocite{Brodsky:69} -\nocite{Brodsky:70} -\nocite{Brodsky:71} -\nocite{Brodsky:72} -\nocite{Brodsky:72a} -\nocite{Brodsky:72b} -\nocite{Brodsky:73} -\nocite{Broughan:82} -\nocite{Broughan:91} -\nocite{Brown:79} -\nocite{Bryan-Jones:87} -\nocite{Burnel} -\nocite{Burnel:94} -\nocite{Burnel:94a} -\nocite{Calmet:72} -\nocite{Calmet:72a} -\nocite{Calmet:74} -\nocite{Calmet:83} -\nocite{Campbell:67} -\nocite{Campbell:68} -\nocite{Campbell:70} -\nocite{Campbell:70a} -\nocite{Campbell:74} -\nocite{Campbell:87} -\nocite{Caprasse:84} -\nocite{Caprasse:85} -\nocite{Caprasse:86} -\nocite{Caprasse:86a} -\nocite{Caprasse:88} -\nocite{Caprasse:89a} -\nocite{Caprasse:90} -\nocite{Caprasse:91} -\nocite{Carlson:80} -\nocite{Carroll:73} -\nocite{Carroll:75} -\nocite{Cejchan} -\nocite{Chaffy:88} -\nocite{Chinnick:86} -\nocite{Cline:90} -\nocite{Cohen:76} -\nocite{Cohen:76a} -\nocite{Cohen:77} -\nocite{Cohen:79} -\nocite{Cohen:84} -\nocite{Cohen:89} -\nocite{Connor:84} -\nocite{Connor:84a} -\nocite{Conwell:84} -\nocite{Cowan:79} -\nocite{Cox:92} -\nocite{Cung:75} -\nocite{Darbaidze:86} -\nocite{Darbaidze:86a} -\nocite{Darbaidze:88} -\nocite{Darbaidze:89} -\nocite{Dautcourt:79} -\nocite{Dautcourt:80} -\nocite{Dautcourt:81} -\nocite{Dautcourt:83} -\nocite{Davenport:81} -\nocite{Davenport:82} -\nocite{Davenport:82a} -\nocite{Davenport:85} -\nocite{Davenport:88} -\nocite{Davenport:88a} -\nocite{Davenport:88b} -\nocite{Davenport:88c} -\nocite{Della-Dora:81} -\nocite{Della-Dora:84} -\nocite{Della-Dora:85} -\nocite{Demaret:89} -\nocite{DeMenna:87} -\nocite{Demichev:85} -\nocite{Demichev:86} -\nocite{deRop:88} -\nocite{DeVos:89} -\nocite{DeVos:93} -\nocite{Dewar:89} -\nocite{Dhar:85} -\nocite{Dicrescenzo:85} -\nocite{Diver} -\nocite{Diver:86} -\nocite{Diver:88} -\nocite{Diver:88a} -\nocite{Diver:91} -\nocite{Dorfi:85} -\nocite{Dorizzi:86} -\nocite{dosSantos:85} -\nocite{dosSantos:87} -\nocite{dosSantos:87a} -\nocite{dosSantos:88a} -\nocite{dosSantos:90} -\nocite{Dresse:93} -\nocite{Drska:90} -\nocite{Dubowsky:75} -\nocite{Dudley:89} -\nocite{Dufner:69} -\nocite{Dulyan:87} -\nocite{Duncan:86} -\nocite{Duval:87} -\nocite{Dyer:94} -\nocite{Earles:70} -\nocite{Eastwood:87} -\nocite{Eastwood:87a} -\nocite{Eastwood:91} -\nocite{Edelen:81} -\nocite{Edelen:82} -\nocite{Edneral:89} -\nocite{Eisenberger:90} -\nocite{Eissfeller:86} -\nocite{Eitelbach:73} -\nocite{Eleuterio:82} -\nocite{Eliseev:85} -\nocite{Elishakoff:87} -\nocite{Elishakoff:87a} -\nocite{Esteban:90} -\nocite{Falck:89} -\nocite{Fazio:84} -\nocite{Fedorova:87} -\nocite{Fedorova:87a} -\nocite{Feldmar:86} -\nocite{Feuillebois:84} -\nocite{Fitch:73} -\nocite{Fitch:81} -\nocite{Fitch:83} -\nocite{Fitch:85} -\nocite{Fitch:85a} -\nocite{Fitch:87} -\nocite{Fitch:87a} -\nocite{Fitch:89} -\nocite{Fitch:89a} -\nocite{Fitch90} -\nocite{Fitch:90a} -\nocite{Fitch:93} -\nocite{Flatau:86} -\nocite{Flath:86} -\nocite{Fleischer:71} -\nocite{Fleischer:73} -\nocite{Fleischer:75} -\nocite{Fogelholm:82} -\nocite{Foster:89} -\nocite{Fox:71} -\nocite{Fox:74} -\nocite{Franceschetti:85} -\nocite{Freire:88} -\nocite{Freire:89} -\nocite{Frick:82} -\nocite{Fujimoto:84} -\nocite{Fuzio:85} -\nocite{Gaemers} -\nocite{Gaemers:78} -\nocite{Ganzha:89} -\nocite{Ganzha90} -\nocite{Ganzha90a} -\nocite{Ganzha:91} -\nocite{Ganzha:94} -\nocite{Garavaglia} -\nocite{Garavaglia:80} -\nocite{Garavaglia:84} -\nocite{Garcia:86} -\nocite{Garrad:86} -\nocite{Gastmans:79} -\nocite{Gatermann:90} -\nocite{Gatermann90a} -\nocite{Gatermann:91} -\nocite{Gatermann:91a} -\nocite{Gatermann:91b} -\nocite{Gatermann:92} -\nocite{Gatermann:93} -\nocite{Gatermann:93a} -\nocite{Gatermann:94} -\nocite{Gatermann:95} -\nocite{Gates:85} -\nocite{Gates:85a} -\nocite{Gates:85b} -\nocite{Gates:85c} -\nocite{Gates:86} -\nocite{Gebauer:85} -\nocite{Gebauer:88} -\nocite{Generalis:84} -\nocite{George:68} -\nocite{Gerdt:80} -\nocite{Gerdt:80a} -\nocite{Gerdt:80b} -\nocite{Gerdt:85} -\nocite{Gerdt:85a} -\nocite{Gerdt:85b} -\nocite{Gerdt:85c} -\nocite{Gerdt:86} -\nocite{Gerdt:87} -\nocite{Gerdt:87a} -\nocite{Gerdt:89} -\nocite{Gerdt:89a} -\nocite{Gerdt:89b} -\nocite{Gerdt90} -\nocite{Gerdt90a} -\nocite{Gerdt:90b} -\nocite{Gerdt:90c} -\nocite{Gerdt:91} -\nocite{Gerdt:91a} -\nocite{Gerdt:91b} -\nocite{Gerdt:93} -\nocite{Gervois:74} -\nocite{Gladd:82} -\nocite{Gladkih:83} -\nocite{Gladkih:84} -\nocite{Goldman:89} -\nocite{Golley} -\nocite{Good:75} -\nocite{Goto:77} -\nocite{Goto:78} -\nocite{Gould:84} -\nocite{Graebe:93} -\nocite{Gragert:81} -\nocite{Grammaticos} -\nocite{Grammaticos:78} -\nocite{Grammaticos:85} -\nocite{Gray:90} -\nocite{Greenland:84} -\nocite{Grimm} -\nocite{Griss:74} -\nocite{Griss:74a} -\nocite{Griss:75} -\nocite{Griss:76} -\nocite{Griss:76a} -\nocite{Griss:77} -\nocite{Griss:77a} -\nocite{Griss:78} -\nocite{Griss:78a} -\nocite{Griss:79} -\nocite{Griss:79a} -\nocite{Grozin:83} -\nocite{Grozin:88} -\nocite{Grozin:88a} -\nocite{Grozin:88b} -\nocite{Grozin:90} -\nocite{Grozin:90a} -\nocite{Grozin:90b} -\nocite{Grozin:91} -\nocite{Grozin:91a} -\nocite{Gunion:72} -\nocite{Gunion:73} -\nocite{Gunion:85} -\nocite{Hadinger:87} -\nocite{Handy:87} -\nocite{Harper:87} -\nocite{Harper:89} -\nocite{Harper:89a} -\nocite{Harrington:77} -\nocite{Harrington:77a} -\nocite{Harrington:79} -\nocite{Harrington:79a} -\nocite{Hartley:91} -\nocite{Hasenfratz:80} -\nocite{Hearn:68} -\nocite{Hearn:69} -\nocite{Hearn:69a} -\nocite{Hearn:71} -\nocite{Hearn:71a} -\nocite{Hearn:71b} -\nocite{Hearn:71c} -\nocite{Hearn:72} -\nocite{Hearn:72a} -\nocite{Hearn:72b} -\nocite{Hearn:73} -\nocite{Hearn:73a} -\nocite{Hearn:74} -\nocite{Hearn:74a} -\nocite{Hearn:76} -\nocite{Hearn:76a} -\nocite{Hearn:76b} -\nocite{Hearn:77} -\nocite{Hearn:78} -\nocite{Hearn:79} -\nocite{Hearn:79a} -\nocite{Hearn:80} -\nocite{Hearn:81} -\nocite{Hearn:81a} -\nocite{Hearn:82} -\nocite{Hearn:82a} -\nocite{Hearn:85} -\nocite{Hearn:86} -\nocite{Hearn:91} -\nocite{Hearn:93} -\nocite{Hearn:95} -\nocite{Hehl:92} -\nocite{Hehl:92a} -\nocite{Hermann:83} -\nocite{Hess:84} -\nocite{Hettich:77} -\nocite{Hietarinta:83} -\nocite{Hietarinta:83a} -\nocite{Hietarinta:84} -\nocite{Hietarinta:84a} -\nocite{Hietarinta:84b} -\nocite{Hietarinta:85} -\nocite{Hietarinta:87} -\nocite{Hietarinta:87a} -\nocite{Hietarinta:87b} -\nocite{Hietarinta:87c} -\nocite{Hietarinta:88} -\nocite{Hietarinta:89} -\nocite{Hietarinta:91} -\nocite{Hietarinta:92} -\nocite{Hietarinta:92a} -\nocite{Hirota:89} -\nocite{Horowitz:75} -\nocite{Horwitz:83} -\nocite{Hughes:90} -\nocite{Hulshof:84} -\nocite{Hulshof:85} -\nocite{Hulshof:81} -\nocite{Hulshof:83} -\nocite{Hunt:91} -\nocite{Husberg:81} -\nocite{Idesawa:77} -\nocite{Ilyin:87} -\nocite{Ilyin:89} -\nocite{Ilyin:91} -\nocite{Ilyin:91a} -\nocite{Inada:80} -\nocite{Ioakimidis:90} -\nocite{Ioakimidis:90a} -\nocite{Ito:85} -\nocite{Ito:85a} -\nocite{Ito:88} -\nocite{Ito:90} -\nocite{Ito:90a} -\nocite{Ito:94} -\nocite{Jansen:86} -\nocite{Janssen:87} -\nocite{Jeffrey:84} -\nocite{Kadlecsik:88} -\nocite{Kadlecsik:92} -\nocite{Kagan:85} -\nocite{Kagan:88} -\nocite{Kahn:69} -\nocite{Kamal:81} -\nocite{Kamel:69} -\nocite{Kamel:69a} -\nocite{Kamel:78} -\nocite{Kanada:81} -\nocite{Kanada:75} -\nocite{Kaneko:89} -\nocite{Kaps:85} -\nocite{Karr:85} -\nocite{Katsura:85} -\nocite{Kauffman:73} -\nocite{Kazasov:87} -\nocite{Keady:85} -\nocite{Keener:83} -\nocite{Keener:85} -\nocite{Keener:89} -\nocite{Keener:90} -\nocite{Kendall:88} -\nocite{Kendall:89} -\nocite{Kendall:89a} -\nocite{Kendall:90} -\nocite{Kendall:91} -\nocite{Kendall:91a} -\nocite{Kendall:93a} -\nocite{Kerner:75} -\nocite{Kersten:83} -\nocite{Kersten:84} -\nocite{Kersten:86} -\nocite{Kersten:86a} -\nocite{Kersten:86b} -\nocite{Killalea:80} -\nocite{Kinoshita:72} -\nocite{Kinoshita:73} -\nocite{Kitatani:86} -\nocite{Klimov:93} -\nocite{Kobayashi:84} -\nocite{Kobayashi:88} -\nocite{Kodaira:85} -\nocite{Koh:82} -\nocite{Koelbig:81} -\nocite{Koelbig:81b} -\nocite{Koelbig:82} -\nocite{Koelbig:82a} -\nocite{Koelbig:83} -\nocite{Koelbig:83a} -\nocite{Koelbig:84} -\nocite{Koelbig:84a} -\nocite{Koelbig:84b} -\nocite{Koelbig:85} -\nocite{Koelbig:85a} -\nocite{Koelbig:86} -\nocite{Koepf:94} -\nocite{Koepf:94a} -\nocite{Koepf:94b} -\nocite{Koepf:95} -\nocite{Koepf:95a} -\nocite{Koike:92} -\nocite{Kolar:90} -\nocite{Kornyak:87} -\nocite{Kotorynski:86} -\nocite{Krack:82} -\nocite{Kraus:73} -\nocite{Kredel:88} -\nocite{Kruse:83} -\nocite{Kryukov} -\nocite{Kryukov:84} -\nocite{Kryukov:85} -\nocite{Kryukov:85a} -\nocite{Kryukov:87} -\nocite{Kryukov:87a} -\nocite{Kryukov:88} -\nocite{Kryukov:88a} -\nocite{Kryukov:88b} -\nocite{Kryukov:91} -\nocite{Kuppers:71} -\nocite{Lambin:84} -\nocite{Lang:79} -\nocite{Laursen:79} -\nocite{Laursen:80} -\nocite{Laursen:81} -\nocite{Lecourtier:85} -\nocite{Lee:85} -\nocite{Leler:85} -\nocite{Lepage:83} -\nocite{Levi:70} -\nocite{Levi:71} -\nocite{Liebermann:75} -\nocite{Liska:84} -\nocite{Liska:87} -\nocite{Liska90} -\nocite{Liska:91} -\nocite{Lloyd:90} -\nocite{Loe:85} -\nocite{London:74} -\nocite{Loos:72} -\nocite{Lottati} -\nocite{Louw:86} -\nocite{Luegger:73} -\nocite{Luegger:91} -\nocite{Lukacs} -\nocite{Lukaszuk:87} -\nocite{Lux:75} -\nocite{MacCallum:86} -\nocite{MacCallum:86a} -\nocite{MacCallum:87} -\nocite{MacCallum:88} -\nocite{MacCallum:89} -\nocite{MacCallum:91} -\nocite{MacCallum:92} -\nocite{MacDonald:94} -\nocite{Mack:73} -\nocite{Mack:73a} -\nocite{Maclaren:89} -\nocite{Maguire:81} -\nocite{Malm:82} -\nocite{Man:93} -\nocite{Man:93a} -\nocite{Man:94} -\nocite{Marti:78} -\nocite{Marti:79} -\nocite{Marti:80} -\nocite{Marti:83} -\nocite{Marti:85} -\nocite{Marti:85a} -\nocite{Marti:88} -\nocite{Marti:93a} -\nocite{Marzinkewitsch:91} -\nocite{Matveev:87} -\nocite{Maurer:86} -\nocite{Mazepa:85} -\nocite{Mazzarella:85} -\nocite{McCrea:81} -\nocite{McCrea:82} -\nocite{McCrea:83} -\nocite{McCrea:84} -\nocite{McCrea:84a} -\nocite{McCrea:87} -\nocite{McCrea:87a} -\nocite{McCrea:88} -\nocite{McIsaac:85} -\nocite{Melenk:88} -\nocite{Melenk:89} -\nocite{Melenk:89a} -\nocite{Melenk:89b} -\nocite{Melenk:90} -\nocite{Melenk:91} -\nocite{Melenk:93} -\nocite{Melenk:93a} -\nocite{Melenk:94} -\nocite{melfo:92} -\nocite{Mirie:84} -\nocite{Molenkamp:91} -\nocite{Moller:89} -\nocite{Moller:92} -\nocite{Moritsugu:85} -\nocite{Moritsugu:88} -\nocite{Moritsugu:89} -\nocite{Moritsugu:89a} -\nocite{Muroa:91} -\nocite{Mueller:81} -\nocite{Mueller-Hoissen:93} -\nocite{Murzin:85} -\nocite{Nagata:82} -\nocite{Nagata:85} -\nocite{Nakamura:89} -\nocite{Nakashima:84} -\nocite{Nakashima:84a} -\nocite{Namba:86} -\nocite{Nemeth:82} -\nocite{Nemeth:87} -\nocite{Neun:89} -\nocite{Neutsch:85} -\nocite{Neutsch:86} -\nocite{Ng:89} -\nocite{Niki:84} -\nocite{Nikityuk:87} -\nocite{Noor:79} -\nocite{Norman:77} -\nocite{Norman:78} -\nocite{Norman:79} -\nocite{Norman:83} -\nocite{Norman90} -\nocite{Norman:93} -\nocite{Norman:95} -\nocite{Norton:80} -\nocite{Nucci:90} -\nocite{Ochiai:90} -\nocite{Ogilvie:82} -\nocite{Ogilvie:89} -\nocite{Ono:1979} -\nocite{Ozieblo} -\nocite{Padget90} -\nocite{Pankau:73} -\nocite{Pankau:73a} -\nocite{Parsons:68} -\nocite{Parsons:71} -\nocite{Pasini:91} -\nocite{Pattnaik:83} -\nocite{Pearce:81} -\nocite{Pearce:83} -\nocite{Perjes:84} -\nocite{Perjes:84a} -\nocite{Perjes:84b} -\nocite{Perjes:84c} -\nocite{Perjes:86} -\nocite{Perjes:86a} -\nocite{Perjes:88} -\nocite{Perlt:90} -\nocite{Perrottet:78} -\nocite{Pesic:73} -\nocite{Pictiaw:69} -\nocite{Piessens:84} -\nocite{Piessens:86} -\nocite{Pignataro:85} -\nocite{Podgorzak:84} -\nocite{Price:84} -\nocite{Quarton} -\nocite{Quarton:84} -\nocite{Rao:85} -\nocite{Rayna:87} -\nocite{Renner:91} -\nocite{Renner:92} -\nocite{Reusch:86} -\nocite{Rink:71} -\nocite{Rizzi:85} -\nocite{Rodionov:84} -\nocite{Rodionov:87} -\nocite{Rodionov:87a} -\nocite{Rodionov:88} -\nocite{Roelofs:91} -\nocite{Rogers:89} -\nocite{Roque:88} -\nocite{Roque:91} -\nocite{Ronveaux:88} -\nocite{Ronveaux:89} -\nocite{Rudenko:91} -\nocite{Saez:83} -\nocite{Sage:88} -\nocite{Sarlet:92} -\nocite{Sasaki:79} -\nocite{Savage:90} -\nocite{Sayers:87} -\nocite{Sayers:87a} -\nocite{Schlegel:91} -\nocite{Schmuck:77} -\nocite{Schoebel:92} -\nocite{Schoepf:91} -\nocite{Schruefer:81} -\nocite{Schruefer:82} -\nocite{Schruefer:87} -\nocite{Schruefer:88} -\nocite{Schwarz:80} -\nocite{Schwarz:82} -\nocite{Schwarz:82a} -\nocite{Schwarz:83} -\nocite{Schwarz:83a} -\nocite{Schwarz:84} -\nocite{Schwarz:84a} -\nocite{Schwarz:85} -\nocite{Schwarz:85a} -\nocite{Schwarz:86} -\nocite{Schwarz:87} -\nocite{Schwarz:88} -\nocite{Schwarz:94} -\nocite{Seiler:91} -\nocite{Shablygin:87} -\nocite{Shmueli:83} -\nocite{Shmueli:83a} -\nocite{Shtokhamer:75} -\nocite{Shtokhamer:77} -\nocite{Smit:79} -\nocite{Smit:81} -\nocite{Smit:82} -\nocite{Smit:87} -\nocite{Soderstrand:72} -\nocite{Soderstrand:72a} -\nocite{Soderstrand:74} -\nocite{Soma:77} -\nocite{Soma:85} -\nocite{Spiridonova:87} -\nocite{Squire} -\nocite{Steeb:92b} -\nocite{Steeb:92c} -\nocite{Steeb:92d} -\nocite{Steeb:93} -\nocite{Steeb:93a} -\nocite{Steeb:94} -\nocite{Steeb:94a} -\nocite{Steeb:94b} -\nocite{Steeb:94c} -\nocite{Steeb:95} -\nocite{Steinberg:82} -\nocite{Steinberg:93} -\nocite{Steuerwald} -\nocite{Stoutemyer:74} -\nocite{Stoutemyer:75} -\nocite{Stoutemyer:77} -\nocite{Stroscio:74} -\nocite{Stuart:88} -\nocite{Stuart:90} -\nocite{Suppes:89} -\nocite{Surguladze:89} -\nocite{Surguladze:91} -\nocite{Tallents:84} -\nocite{Tao90} -\nocite{Tasso:76} -\nocite{Thas:89} -\nocite{Thas:89a} -\nocite{Todd:88} -\nocite{Toth:86} -\nocite{Tournier:79} -\nocite{Tournier:87} -\nocite{Trenkov:91} -\nocite{Trotter:89} -\nocite{Tsai:65} -\nocite{Tsai:74} -\nocite{Ucoluk:82} -\nocite{Ueberberg:92} -\nocite{Umeno:89} -\nocite{Urintsev:91} -\nocite{vandenHeuvel:86} -\nocite{vandenHeuvel:86a} -\nocite{vandenHeuvel:87} -\nocite{vandenHeuvel:87a} -\nocite{vanHeerwaarden} -\nocite{vanHulzen:80} -\nocite{vanHulzen:81} -\nocite{vanHulzen:82} -\nocite{vanHulzen:82a} -\nocite{vanHulzen:83} -\nocite{vanHulzen:83a} -\nocite{vanHulzen:87} -\nocite{vanHulzen:88} -\nocite{vanHulzen:89} -\nocite{vanHulzen:89a} -\nocite{VanProeyan:76} -\nocite{VanProeyan:79} -\nocite{Vega:91} -\nocite{Vinitsky:87} -\nocite{Viry:93} -\nocite{Voros:77} -\nocite{Wanas} -\nocite{Wanas:85} -\nocite{Wang:84} -\nocite{Wang:93} -\nocite{Wassam:87} -\nocite{Wassam:87a} -\nocite{Watanabe:85} -\nocite{Watanabe:76} -\nocite{Watanabe:79} -\nocite{Weber:79} -\nocite{Wehner:86} -\nocite{Weispfenning:94} -\nocite{Winkelmann:89} -\nocite{Winkler:88} -\nocite{Witham:77} -\nocite{Wolf:95} -\nocite{Wood:89} -\nocite{Wright:84} -\nocite{Wulkow:90} -\nocite{Yamamoto:87} -\nocite{Yamartino:91} -\nocite{Yannouleas:88} -\nocite{Yannouleas:89} -\nocite{Zacrep:75} -\nocite{Zahalak:87} -\nocite{Zeng:84} -\nocite{Zharkov:93} -\nocite{Zharkov:93a} -\nocite{Zhidkova:78} - -\bibliography{bibl} -\bibliographystyle{plain} - -\end{document} - - +% The following UNIX script will create a hard copy version of the +% REDUCE bibliography from this file and the bibliography files +% bibl-*.bib. It creates the files tmp.* in the process. +% +% # Make REDUCE bibliography +% rm tmp.* +% cat bibl.tex > tmp.tex +% cat bibl*.bib > tmp.bib +% bib2tex tmp | sed 1,5d >> tmp.tex +% latex tmp +% bibtex tmp > tmp.blog +% latex tmp +% latex tmp +% +\documentstyle [11pt]{article} +\def\thebibliography#1{\section*{}\list + {[\arabic{enumi}]}{\settowidth\labelwidth{[#1]}\leftmargin\labelwidth + \advance\leftmargin\labelsep + \usecounter{enumi}} + \def\newblock{\hskip .11em plus .33em minus .07em} + \sloppy\clubpenalty4000\widowpenalty4000 + \sfcode`\.=1000\relax} +\textwidth 6.6in\textheight 9in\columnwidth\textwidth +\hoffset-2cm +\begin{document} +\setcounter{page}{0} +\title{REDUCE Bibliography} +\author{Anthony C. Hearn\\ +RAND \\ +Santa Monica CA 90407-2138 \vspace {.5cm} \\ +July 1995} +\date{} +\maketitle +\vspace{1cm} +This document contains a list of all known references to REDUCE. It no doubt +contains errors and omissions. Please report these by regular mail +(preferably in BibTeX format) to the REDUCE Secretary, RAND, P.O. Box 2138, +Santa Monica CA 90407-2318, or by electronic mail to reduce@rand.org. An +electronic copy of the bibliography in BibTeX format is also available from +the latter address. +\begin{center} +\vspace{9.0cm} +RAND Publication CP162 (Rev. 7/95) \vspace*{.5cm} \\ +Copyright \copyright 1995 RAND. All rights reserved. +\end{center} +\newpage +\voffset-2.5cm + +\nocite{Abbott:85} +\nocite{Abbott:86} +\nocite{Abbott:87} +\nocite{Abbott:87a} +\nocite{Abbott:88} +\nocite{Abbott:88a} +\nocite{Abbott:89} +\nocite{Abbott:89a} +\nocite{Abdali:88} +\nocite{Abiezzi:83} +\nocite{Abramov:91} +\nocite{Abramov:91a} +\nocite{Adamchik90} +\nocite{Adams:83} +\nocite{Adkins:83} +\nocite{Adkins:83a} +\nocite{Adkins:85} +\nocite{Aguilera-Navarro:87} +\nocite{Akselrod:90} +\nocite{Aldins:69} +\nocite{Alekseev:86} +\nocite{Alekseev:87} +\nocite{Alekseev:87a} +\nocite{Alfeld:82} +\nocite{Amirkhanov:87} +\nocite{Amirkhanov:91} +\nocite{Antweiler:89} +\nocite{Appelquist:70} +\nocite{Arbuzov:86} +\nocite{Kendall:93} +\nocite{Aso:81} +\nocite{Atherton:73} +\nocite{Aurenche:84} +\nocite{Aurenche:84a} +\nocite{Autin:89} +\nocite{Baekler:84} +\nocite{Baekler:84a} +\nocite{Baekler:86} +\nocite{Baekler:87} +\nocite{Baekler:87a} +\nocite{Baekler:87b} +\nocite{Baekler:88} +\nocite{Baekler:88a} +\nocite{Baekler:88b} +\nocite{Bahrdt:90} +\nocite{Baier:81} +\nocite{Baier:85} +\nocite{Baier:90} +\nocite{Bajla:78} +\nocite{Balian:78} +\nocite{Baker:81} +\nocite{Barbier:92} +\nocite{Barfoot:86} +\nocite{Barfoot:87} +\nocite{Barfoot:88} +\nocite{Bark:78} +\nocite{Barthes-Biesel:73} +\nocite{Barton:72} +\nocite{Bateman:86} +\nocite{Belkov:91} +\nocite{Bennett:88} +\nocite{Bennett:93} +\nocite{Berends:81} +\nocite{Berkovich:89} +\nocite{Berkovich:90} +\nocite{Berman:63} +\nocite{Berndt:91} +\nocite{Bessis:85} +\nocite{Bilge:92} +\nocite{Billoire:78} +\nocite{Biro:86} +\nocite{Biro:87} +\nocite{Birrell:77} +\nocite{Biswas:75} +\nocite{Bittencourt:90} +\nocite{Blum:93} +\nocite{Bocko:92} +\nocite{Boege:86} +\nocite{Bogdanova:88} +\nocite{Bordoni:81} +\nocite{Borst:94} +\nocite{Bowyer:87} +\nocite{Boyd:78} +\nocite{Boyd:93} +\nocite{Brackx:87} +\nocite{Brackx:87a} +\nocite{Brackx:89} +\nocite{Brackx:92} +\nocite{Bradford:86} +\nocite{Bradford:88} +\nocite{Bradford90} +\nocite{Broadhurst:83} +\nocite{Broadhurst:84} +\nocite{Broadhurst:85} +\nocite{Broadhurst:85a} +\nocite{Broadhurst:86} +\nocite{Broadhurst:87} +\nocite{Broadhurst:90} +\nocite{Broadhurst:91} +\nocite{Broadhurst:91a} +\nocite{Broadhurst:91b} +\nocite{Broadhurst:92} +\nocite{Broadhurst:92a} +\nocite{Broadhurst:93} +\nocite{Broadhurst:93a} +\nocite{Broadhurst:94} +\nocite{Brodsky:62} +\nocite{Brodsky:67} +\nocite{Brodsky:69} +\nocite{Brodsky:70} +\nocite{Brodsky:71} +\nocite{Brodsky:72} +\nocite{Brodsky:72a} +\nocite{Brodsky:72b} +\nocite{Brodsky:73} +\nocite{Broughan:82} +\nocite{Broughan:91} +\nocite{Brown:79} +\nocite{Bryan-Jones:87} +\nocite{Burnel} +\nocite{Burnel:94} +\nocite{Burnel:94a} +\nocite{Calmet:72} +\nocite{Calmet:72a} +\nocite{Calmet:74} +\nocite{Calmet:83} +\nocite{Campbell:67} +\nocite{Campbell:68} +\nocite{Campbell:70} +\nocite{Campbell:70a} +\nocite{Campbell:74} +\nocite{Campbell:87} +\nocite{Caprasse:84} +\nocite{Caprasse:85} +\nocite{Caprasse:86} +\nocite{Caprasse:86a} +\nocite{Caprasse:88} +\nocite{Caprasse:89a} +\nocite{Caprasse:90} +\nocite{Caprasse:91} +\nocite{Carlson:80} +\nocite{Carroll:73} +\nocite{Carroll:75} +\nocite{Cejchan} +\nocite{Chaffy:88} +\nocite{Chinnick:86} +\nocite{Cline:90} +\nocite{Cohen:76} +\nocite{Cohen:76a} +\nocite{Cohen:77} +\nocite{Cohen:79} +\nocite{Cohen:84} +\nocite{Cohen:89} +\nocite{Connor:84} +\nocite{Connor:84a} +\nocite{Conwell:84} +\nocite{Cowan:79} +\nocite{Cox:92} +\nocite{Cung:75} +\nocite{Darbaidze:86} +\nocite{Darbaidze:86a} +\nocite{Darbaidze:88} +\nocite{Darbaidze:89} +\nocite{Dautcourt:79} +\nocite{Dautcourt:80} +\nocite{Dautcourt:81} +\nocite{Dautcourt:83} +\nocite{Davenport:81} +\nocite{Davenport:82} +\nocite{Davenport:82a} +\nocite{Davenport:85} +\nocite{Davenport:88} +\nocite{Davenport:88a} +\nocite{Davenport:88b} +\nocite{Davenport:88c} +\nocite{Della-Dora:81} +\nocite{Della-Dora:84} +\nocite{Della-Dora:85} +\nocite{Demaret:89} +\nocite{DeMenna:87} +\nocite{Demichev:85} +\nocite{Demichev:86} +\nocite{deRop:88} +\nocite{DeVos:89} +\nocite{DeVos:93} +\nocite{Dewar:89} +\nocite{Dhar:85} +\nocite{Dicrescenzo:85} +\nocite{Diver} +\nocite{Diver:86} +\nocite{Diver:88} +\nocite{Diver:88a} +\nocite{Diver:91} +\nocite{Dorfi:85} +\nocite{Dorizzi:86} +\nocite{dosSantos:85} +\nocite{dosSantos:87} +\nocite{dosSantos:87a} +\nocite{dosSantos:88a} +\nocite{dosSantos:90} +\nocite{Dresse:93} +\nocite{Drska:90} +\nocite{Dubowsky:75} +\nocite{Dudley:89} +\nocite{Dufner:69} +\nocite{Dulyan:87} +\nocite{Duncan:86} +\nocite{Duval:87} +\nocite{Dyer:94} +\nocite{Earles:70} +\nocite{Eastwood:87} +\nocite{Eastwood:87a} +\nocite{Eastwood:91} +\nocite{Edelen:81} +\nocite{Edelen:82} +\nocite{Edneral:89} +\nocite{Eisenberger:90} +\nocite{Eissfeller:86} +\nocite{Eitelbach:73} +\nocite{Eleuterio:82} +\nocite{Eliseev:85} +\nocite{Elishakoff:87} +\nocite{Elishakoff:87a} +\nocite{Esteban:90} +\nocite{Falck:89} +\nocite{Fazio:84} +\nocite{Fedorova:87} +\nocite{Fedorova:87a} +\nocite{Feldmar:86} +\nocite{Feuillebois:84} +\nocite{Fitch:73} +\nocite{Fitch:81} +\nocite{Fitch:83} +\nocite{Fitch:85} +\nocite{Fitch:85a} +\nocite{Fitch:87} +\nocite{Fitch:87a} +\nocite{Fitch:89} +\nocite{Fitch:89a} +\nocite{Fitch90} +\nocite{Fitch:90a} +\nocite{Fitch:93} +\nocite{Flatau:86} +\nocite{Flath:86} +\nocite{Fleischer:71} +\nocite{Fleischer:73} +\nocite{Fleischer:75} +\nocite{Fogelholm:82} +\nocite{Foster:89} +\nocite{Fox:71} +\nocite{Fox:74} +\nocite{Franceschetti:85} +\nocite{Freire:88} +\nocite{Freire:89} +\nocite{Frick:82} +\nocite{Fujimoto:84} +\nocite{Fuzio:85} +\nocite{Gaemers} +\nocite{Gaemers:78} +\nocite{Ganzha:89} +\nocite{Ganzha90} +\nocite{Ganzha90a} +\nocite{Ganzha:91} +\nocite{Ganzha:94} +\nocite{Garavaglia} +\nocite{Garavaglia:80} +\nocite{Garavaglia:84} +\nocite{Garcia:86} +\nocite{Garrad:86} +\nocite{Gastmans:79} +\nocite{Gatermann:90} +\nocite{Gatermann90a} +\nocite{Gatermann:91} +\nocite{Gatermann:91a} +\nocite{Gatermann:91b} +\nocite{Gatermann:92} +\nocite{Gatermann:93} +\nocite{Gatermann:93a} +\nocite{Gatermann:94} +\nocite{Gatermann:95} +\nocite{Gates:85} +\nocite{Gates:85a} +\nocite{Gates:85b} +\nocite{Gates:85c} +\nocite{Gates:86} +\nocite{Gebauer:85} +\nocite{Gebauer:88} +\nocite{Generalis:84} +\nocite{George:68} +\nocite{Gerdt:80} +\nocite{Gerdt:80a} +\nocite{Gerdt:80b} +\nocite{Gerdt:85} +\nocite{Gerdt:85a} +\nocite{Gerdt:85b} +\nocite{Gerdt:85c} +\nocite{Gerdt:86} +\nocite{Gerdt:87} +\nocite{Gerdt:87a} +\nocite{Gerdt:89} +\nocite{Gerdt:89a} +\nocite{Gerdt:89b} +\nocite{Gerdt90} +\nocite{Gerdt90a} +\nocite{Gerdt:90b} +\nocite{Gerdt:90c} +\nocite{Gerdt:91} +\nocite{Gerdt:91a} +\nocite{Gerdt:91b} +\nocite{Gerdt:93} +\nocite{Gervois:74} +\nocite{Gladd:82} +\nocite{Gladkih:83} +\nocite{Gladkih:84} +\nocite{Goldman:89} +\nocite{Golley} +\nocite{Good:75} +\nocite{Goto:77} +\nocite{Goto:78} +\nocite{Gould:84} +\nocite{Graebe:93} +\nocite{Gragert:81} +\nocite{Grammaticos} +\nocite{Grammaticos:78} +\nocite{Grammaticos:85} +\nocite{Gray:90} +\nocite{Greenland:84} +\nocite{Grimm} +\nocite{Griss:74} +\nocite{Griss:74a} +\nocite{Griss:75} +\nocite{Griss:76} +\nocite{Griss:76a} +\nocite{Griss:77} +\nocite{Griss:77a} +\nocite{Griss:78} +\nocite{Griss:78a} +\nocite{Griss:79} +\nocite{Griss:79a} +\nocite{Grozin:83} +\nocite{Grozin:88} +\nocite{Grozin:88a} +\nocite{Grozin:88b} +\nocite{Grozin:90} +\nocite{Grozin:90a} +\nocite{Grozin:90b} +\nocite{Grozin:91} +\nocite{Grozin:91a} +\nocite{Gunion:72} +\nocite{Gunion:73} +\nocite{Gunion:85} +\nocite{Hadinger:87} +\nocite{Handy:87} +\nocite{Harper:87} +\nocite{Harper:89} +\nocite{Harper:89a} +\nocite{Harrington:77} +\nocite{Harrington:77a} +\nocite{Harrington:79} +\nocite{Harrington:79a} +\nocite{Hartley:91} +\nocite{Hasenfratz:80} +\nocite{Hearn:68} +\nocite{Hearn:69} +\nocite{Hearn:69a} +\nocite{Hearn:71} +\nocite{Hearn:71a} +\nocite{Hearn:71b} +\nocite{Hearn:71c} +\nocite{Hearn:72} +\nocite{Hearn:72a} +\nocite{Hearn:72b} +\nocite{Hearn:73} +\nocite{Hearn:73a} +\nocite{Hearn:74} +\nocite{Hearn:74a} +\nocite{Hearn:76} +\nocite{Hearn:76a} +\nocite{Hearn:76b} +\nocite{Hearn:77} +\nocite{Hearn:78} +\nocite{Hearn:79} +\nocite{Hearn:79a} +\nocite{Hearn:80} +\nocite{Hearn:81} +\nocite{Hearn:81a} +\nocite{Hearn:82} +\nocite{Hearn:82a} +\nocite{Hearn:85} +\nocite{Hearn:86} +\nocite{Hearn:91} +\nocite{Hearn:93} +\nocite{Hearn:95} +\nocite{Hehl:92} +\nocite{Hehl:92a} +\nocite{Hermann:83} +\nocite{Hess:84} +\nocite{Hettich:77} +\nocite{Hietarinta:83} +\nocite{Hietarinta:83a} +\nocite{Hietarinta:84} +\nocite{Hietarinta:84a} +\nocite{Hietarinta:84b} +\nocite{Hietarinta:85} +\nocite{Hietarinta:87} +\nocite{Hietarinta:87a} +\nocite{Hietarinta:87b} +\nocite{Hietarinta:87c} +\nocite{Hietarinta:88} +\nocite{Hietarinta:89} +\nocite{Hietarinta:91} +\nocite{Hietarinta:92} +\nocite{Hietarinta:92a} +\nocite{Hirota:89} +\nocite{Horowitz:75} +\nocite{Horwitz:83} +\nocite{Hughes:90} +\nocite{Hulshof:84} +\nocite{Hulshof:85} +\nocite{Hulshof:81} +\nocite{Hulshof:83} +\nocite{Hunt:91} +\nocite{Husberg:81} +\nocite{Idesawa:77} +\nocite{Ilyin:87} +\nocite{Ilyin:89} +\nocite{Ilyin:91} +\nocite{Ilyin:91a} +\nocite{Inada:80} +\nocite{Ioakimidis:90} +\nocite{Ioakimidis:90a} +\nocite{Ito:85} +\nocite{Ito:85a} +\nocite{Ito:88} +\nocite{Ito:90} +\nocite{Ito:90a} +\nocite{Ito:94} +\nocite{Jansen:86} +\nocite{Janssen:87} +\nocite{Jeffrey:84} +\nocite{Kadlecsik:88} +\nocite{Kadlecsik:92} +\nocite{Kagan:85} +\nocite{Kagan:88} +\nocite{Kahn:69} +\nocite{Kamal:81} +\nocite{Kamel:69} +\nocite{Kamel:69a} +\nocite{Kamel:78} +\nocite{Kanada:81} +\nocite{Kanada:75} +\nocite{Kaneko:89} +\nocite{Kaps:85} +\nocite{Karr:85} +\nocite{Katsura:85} +\nocite{Kauffman:73} +\nocite{Kazasov:87} +\nocite{Keady:85} +\nocite{Keener:83} +\nocite{Keener:85} +\nocite{Keener:89} +\nocite{Keener:90} +\nocite{Kendall:88} +\nocite{Kendall:89} +\nocite{Kendall:89a} +\nocite{Kendall:90} +\nocite{Kendall:91} +\nocite{Kendall:91a} +\nocite{Kendall:93a} +\nocite{Kerner:75} +\nocite{Kersten:83} +\nocite{Kersten:84} +\nocite{Kersten:86} +\nocite{Kersten:86a} +\nocite{Kersten:86b} +\nocite{Killalea:80} +\nocite{Kinoshita:72} +\nocite{Kinoshita:73} +\nocite{Kitatani:86} +\nocite{Klimov:93} +\nocite{Kobayashi:84} +\nocite{Kobayashi:88} +\nocite{Kodaira:85} +\nocite{Koh:82} +\nocite{Koelbig:81} +\nocite{Koelbig:81b} +\nocite{Koelbig:82} +\nocite{Koelbig:82a} +\nocite{Koelbig:83} +\nocite{Koelbig:83a} +\nocite{Koelbig:84} +\nocite{Koelbig:84a} +\nocite{Koelbig:84b} +\nocite{Koelbig:85} +\nocite{Koelbig:85a} +\nocite{Koelbig:86} +\nocite{Koepf:94} +\nocite{Koepf:94a} +\nocite{Koepf:94b} +\nocite{Koepf:95} +\nocite{Koepf:95a} +\nocite{Koike:92} +\nocite{Kolar:90} +\nocite{Kornyak:87} +\nocite{Kotorynski:86} +\nocite{Krack:82} +\nocite{Kraus:73} +\nocite{Kredel:88} +\nocite{Kruse:83} +\nocite{Kryukov} +\nocite{Kryukov:84} +\nocite{Kryukov:85} +\nocite{Kryukov:85a} +\nocite{Kryukov:87} +\nocite{Kryukov:87a} +\nocite{Kryukov:88} +\nocite{Kryukov:88a} +\nocite{Kryukov:88b} +\nocite{Kryukov:91} +\nocite{Kuppers:71} +\nocite{Lambin:84} +\nocite{Lang:79} +\nocite{Laursen:79} +\nocite{Laursen:80} +\nocite{Laursen:81} +\nocite{Lecourtier:85} +\nocite{Lee:85} +\nocite{Leler:85} +\nocite{Lepage:83} +\nocite{Levi:70} +\nocite{Levi:71} +\nocite{Liebermann:75} +\nocite{Liska:84} +\nocite{Liska:87} +\nocite{Liska90} +\nocite{Liska:91} +\nocite{Lloyd:90} +\nocite{Loe:85} +\nocite{London:74} +\nocite{Loos:72} +\nocite{Lottati} +\nocite{Louw:86} +\nocite{Luegger:73} +\nocite{Luegger:91} +\nocite{Lukacs} +\nocite{Lukaszuk:87} +\nocite{Lux:75} +\nocite{MacCallum:86} +\nocite{MacCallum:86a} +\nocite{MacCallum:87} +\nocite{MacCallum:88} +\nocite{MacCallum:89} +\nocite{MacCallum:91} +\nocite{MacCallum:92} +\nocite{MacDonald:94} +\nocite{Mack:73} +\nocite{Mack:73a} +\nocite{Maclaren:89} +\nocite{Maguire:81} +\nocite{Malm:82} +\nocite{Man:93} +\nocite{Man:93a} +\nocite{Man:94} +\nocite{Marti:78} +\nocite{Marti:79} +\nocite{Marti:80} +\nocite{Marti:83} +\nocite{Marti:85} +\nocite{Marti:85a} +\nocite{Marti:88} +\nocite{Marti:93a} +\nocite{Marzinkewitsch:91} +\nocite{Matveev:87} +\nocite{Maurer:86} +\nocite{Mazepa:85} +\nocite{Mazzarella:85} +\nocite{McCrea:81} +\nocite{McCrea:82} +\nocite{McCrea:83} +\nocite{McCrea:84} +\nocite{McCrea:84a} +\nocite{McCrea:87} +\nocite{McCrea:87a} +\nocite{McCrea:88} +\nocite{McIsaac:85} +\nocite{Melenk:88} +\nocite{Melenk:89} +\nocite{Melenk:89a} +\nocite{Melenk:89b} +\nocite{Melenk:90} +\nocite{Melenk:91} +\nocite{Melenk:93} +\nocite{Melenk:93a} +\nocite{Melenk:94} +\nocite{melfo:92} +\nocite{Mirie:84} +\nocite{Molenkamp:91} +\nocite{Moller:89} +\nocite{Moller:92} +\nocite{Moritsugu:85} +\nocite{Moritsugu:88} +\nocite{Moritsugu:89} +\nocite{Moritsugu:89a} +\nocite{Muroa:91} +\nocite{Mueller:81} +\nocite{Mueller-Hoissen:93} +\nocite{Murzin:85} +\nocite{Nagata:82} +\nocite{Nagata:85} +\nocite{Nakamura:89} +\nocite{Nakashima:84} +\nocite{Nakashima:84a} +\nocite{Namba:86} +\nocite{Nemeth:82} +\nocite{Nemeth:87} +\nocite{Neun:89} +\nocite{Neutsch:85} +\nocite{Neutsch:86} +\nocite{Ng:89} +\nocite{Niki:84} +\nocite{Nikityuk:87} +\nocite{Noor:79} +\nocite{Norman:77} +\nocite{Norman:78} +\nocite{Norman:79} +\nocite{Norman:83} +\nocite{Norman90} +\nocite{Norman:93} +\nocite{Norman:95} +\nocite{Norton:80} +\nocite{Nucci:90} +\nocite{Ochiai:90} +\nocite{Ogilvie:82} +\nocite{Ogilvie:89} +\nocite{Ono:1979} +\nocite{Ozieblo} +\nocite{Padget90} +\nocite{Pankau:73} +\nocite{Pankau:73a} +\nocite{Parsons:68} +\nocite{Parsons:71} +\nocite{Pasini:91} +\nocite{Pattnaik:83} +\nocite{Pearce:81} +\nocite{Pearce:83} +\nocite{Perjes:84} +\nocite{Perjes:84a} +\nocite{Perjes:84b} +\nocite{Perjes:84c} +\nocite{Perjes:86} +\nocite{Perjes:86a} +\nocite{Perjes:88} +\nocite{Perlt:90} +\nocite{Perrottet:78} +\nocite{Pesic:73} +\nocite{Pictiaw:69} +\nocite{Piessens:84} +\nocite{Piessens:86} +\nocite{Pignataro:85} +\nocite{Podgorzak:84} +\nocite{Price:84} +\nocite{Quarton} +\nocite{Quarton:84} +\nocite{Rao:85} +\nocite{Rayna:87} +\nocite{Renner:91} +\nocite{Renner:92} +\nocite{Reusch:86} +\nocite{Rink:71} +\nocite{Rizzi:85} +\nocite{Rodionov:84} +\nocite{Rodionov:87} +\nocite{Rodionov:87a} +\nocite{Rodionov:88} +\nocite{Roelofs:91} +\nocite{Rogers:89} +\nocite{Roque:88} +\nocite{Roque:91} +\nocite{Ronveaux:88} +\nocite{Ronveaux:89} +\nocite{Rudenko:91} +\nocite{Saez:83} +\nocite{Sage:88} +\nocite{Sarlet:92} +\nocite{Sasaki:79} +\nocite{Savage:90} +\nocite{Sayers:87} +\nocite{Sayers:87a} +\nocite{Schlegel:91} +\nocite{Schmuck:77} +\nocite{Schoebel:92} +\nocite{Schoepf:91} +\nocite{Schruefer:81} +\nocite{Schruefer:82} +\nocite{Schruefer:87} +\nocite{Schruefer:88} +\nocite{Schwarz:80} +\nocite{Schwarz:82} +\nocite{Schwarz:82a} +\nocite{Schwarz:83} +\nocite{Schwarz:83a} +\nocite{Schwarz:84} +\nocite{Schwarz:84a} +\nocite{Schwarz:85} +\nocite{Schwarz:85a} +\nocite{Schwarz:86} +\nocite{Schwarz:87} +\nocite{Schwarz:88} +\nocite{Schwarz:94} +\nocite{Seiler:91} +\nocite{Shablygin:87} +\nocite{Shmueli:83} +\nocite{Shmueli:83a} +\nocite{Shtokhamer:75} +\nocite{Shtokhamer:77} +\nocite{Smit:79} +\nocite{Smit:81} +\nocite{Smit:82} +\nocite{Smit:87} +\nocite{Soderstrand:72} +\nocite{Soderstrand:72a} +\nocite{Soderstrand:74} +\nocite{Soma:77} +\nocite{Soma:85} +\nocite{Spiridonova:87} +\nocite{Squire} +\nocite{Steeb:92b} +\nocite{Steeb:92c} +\nocite{Steeb:92d} +\nocite{Steeb:93} +\nocite{Steeb:93a} +\nocite{Steeb:94} +\nocite{Steeb:94a} +\nocite{Steeb:94b} +\nocite{Steeb:94c} +\nocite{Steeb:95} +\nocite{Steinberg:82} +\nocite{Steinberg:93} +\nocite{Steuerwald} +\nocite{Stoutemyer:74} +\nocite{Stoutemyer:75} +\nocite{Stoutemyer:77} +\nocite{Stroscio:74} +\nocite{Stuart:88} +\nocite{Stuart:90} +\nocite{Suppes:89} +\nocite{Surguladze:89} +\nocite{Surguladze:91} +\nocite{Tallents:84} +\nocite{Tao90} +\nocite{Tasso:76} +\nocite{Thas:89} +\nocite{Thas:89a} +\nocite{Todd:88} +\nocite{Toth:86} +\nocite{Tournier:79} +\nocite{Tournier:87} +\nocite{Trenkov:91} +\nocite{Trotter:89} +\nocite{Tsai:65} +\nocite{Tsai:74} +\nocite{Ucoluk:82} +\nocite{Ueberberg:92} +\nocite{Umeno:89} +\nocite{Urintsev:91} +\nocite{vandenHeuvel:86} +\nocite{vandenHeuvel:86a} +\nocite{vandenHeuvel:87} +\nocite{vandenHeuvel:87a} +\nocite{vanHeerwaarden} +\nocite{vanHulzen:80} +\nocite{vanHulzen:81} +\nocite{vanHulzen:82} +\nocite{vanHulzen:82a} +\nocite{vanHulzen:83} +\nocite{vanHulzen:83a} +\nocite{vanHulzen:87} +\nocite{vanHulzen:88} +\nocite{vanHulzen:89} +\nocite{vanHulzen:89a} +\nocite{VanProeyan:76} +\nocite{VanProeyan:79} +\nocite{Vega:91} +\nocite{Vinitsky:87} +\nocite{Viry:93} +\nocite{Voros:77} +\nocite{Wanas} +\nocite{Wanas:85} +\nocite{Wang:84} +\nocite{Wang:93} +\nocite{Wassam:87} +\nocite{Wassam:87a} +\nocite{Watanabe:85} +\nocite{Watanabe:76} +\nocite{Watanabe:79} +\nocite{Weber:79} +\nocite{Wehner:86} +\nocite{Weispfenning:94} +\nocite{Winkelmann:89} +\nocite{Winkler:88} +\nocite{Witham:77} +\nocite{Wolf:95} +\nocite{Wood:89} +\nocite{Wright:84} +\nocite{Wulkow:90} +\nocite{Yamamoto:87} +\nocite{Yamartino:91} +\nocite{Yannouleas:88} +\nocite{Yannouleas:89} +\nocite{Zacrep:75} +\nocite{Zahalak:87} +\nocite{Zeng:84} +\nocite{Zharkov:93} +\nocite{Zharkov:93a} +\nocite{Zhidkova:78} + +\bibliography{bibl} +\bibliographystyle{plain} + +\end{document} + + Index: r36/doc/BOOLEAN.TEX ================================================================== --- r36/doc/BOOLEAN.TEX +++ r36/doc/BOOLEAN.TEX @@ -1,169 +1,169 @@ -\documentstyle[11pt,reduce]{article} -\title{BOOLEAN: Computing with boolean expressions} -\date{} -\author{ -H. Melenk\\[0.05in] -Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ -Heilbronner Strasse 10 \\ -D--10711 Berlin -- Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -E--mail: melenk@sc.zib--berlin.de \\[0.05in] -} - -\begin{document} -\maketitle - -\section{Introduction} - -The package {\bf Boolean} supports the computation with -boolean expressions in the propositional calculus. -The data objects are composed from algebraic expressions (``atomic parts'', ``leafs'') -connected by the infix boolean operators {\bf and}, {\bf or}, -{\bf implies}, {\bf equiv}, and the unary prefix operator -{\bf not}. {\bf Boolean} allows you to simplify expressions -built from these operators, and to test properties like -equivalence, subset property etc. Also the reduction of -a boolean expression by a partial evaluation and combination -of its atomic parts is supported. - -\section{Entering boolean expressions} - -In order to distinguish boolean data expressions from -boolean expressions in the \REDUCE programming -language (e.g. in an {\bf if} statement), each expression -must be tagged explicitly by an operator {\bf boolean}. -Otherwise the boolean operators are not accepted in the -\REDUCE algebraic mode input. -The first argument of {\bf boolean} can be any boolean expression, -which may contain references to other boolean values. -\begin{verbatim} - boolean (a and b or c); - q := boolean(a and b implies c); - boolean(q or not c); -\end{verbatim} -Brackets are used to override the operator precedence as usual. -The leafs or atoms of a boolean expression are those parts which -do not contain a leading boolean operator. These are -considered as constants during the boolean evaluation. There -are two pre-defined values: -\begin{itemize} -\item {\bf true}, {\bf t} or {\bf 1} -\item {\bf false}, {\bf nil} or {\bf 0} -\end{itemize} -These represent the boolean constants. In a result -form they are used only as {\bf 1} and {\bf 0}. - -By default, a {\bf boolean} expression is converted to a -disjunctive normal form, that is a form where terms are connected -by {\bf or} on the top level and each term is set of leaf -expressions, eventually preceded by {\bf not} and connected -by {\bf and}. An operators {\bf or} or {\bf and} is omitted -if it would have only one single operand. The result of -the transformation is again an expression with leading -operator {\bf boolean} such that the boolean expressions -remain separated from other algebraic data. Only the boolean -constants {\bf 0} and {\bf 1} are returned untagged. - -On output, the -operators {\bf and} and {\bf or} are represented as -\verb+/\+ and \verb+\/+, respectively. -\begin{verbatim} -boolean(true and false); -> 0 -boolean(a or not(b and c)); -> boolean(not(b) \/ not(c) \/ a) -boolean(a equiv not c); -> boolean(not(a)/\c \/ a/\not(c)) -\end{verbatim} - -\section{Normal forms} - -The {\bf disjunctive} normal form is used by default. It -represents the ``natural'' view and allows us to represent -any form free or parentheses. -Alternatively a {\bf conjunctive} normal form can be -selected as simplification target, which is a form with -leading operator {\bf and}. To produce that form add the keyword {\bf and} -as an additional argument to a call of {\bf boolean}. -\begin{verbatim} -boolean (a or b implies c); - -> - boolean(not(a)/\not(b) \/ c) - -boolean (a or b implies c, and); - -> - boolean((not(a) \/ c)/\(not(b) \/ c)) -\end{verbatim} - -Usually the result is a fully reduced disjunctive or conjuntive normal -form, where all redundant elements have been eliminated following the -rules - -$ a \wedge b \vee \neg a \wedge b \longleftrightarrow b$ - -$ a \vee b \wedge \neg a \vee b \longleftrightarrow b$ - - -Internally the full normal forms are computed -as intermediate result; in these forms each term contains -all leaf expressions, each one exactly once. This unreduced form is returned -when you set the additional keyword {\bf full}: -\begin{verbatim} -boolean (a or b implies c, full); - -> -boolean(a/\b/\c \/ a/\not(b)/\c \/ not(a)/\b/\c \/ not(a)/\not(b)/\c - - \/ not(a)/\not(b)/\not(c)) -\end{verbatim} - -The keywords {\bf full} and {\bf and} may be combined. - -\section{Evaluation of a boolean expression} - -If the leafs of the boolean expression are algebraic expressions -which may evaluate to logical values because the environment -has changed (e.g. variables have been bound), you can re--investigate -the expression using the operator {\tt testbool} with the boolean -expression as argument. This operator tries to evaluate all -leaf expressions in \REDUCE boolean style. As many -terms as possible are replaced by their boolean values; the others -remain unchanged. The resulting expression is contracted to a -minimal form. The result {\bf 1} (= true) or {\bf 0} (=false) -signals that the complete expression could be evaluated. - -In the following example the leafs are built as numeric greater test. -For using ${\bf >}$ in the expressions the greater sign must -be declared operator first. The error messages are meaningless. -\begin{verbatim} -operator >; -fm:=boolean(x>v or not (u>v)); - -> - fm := boolean(not(u>v) \/ x>v) - -v:=10$ - -testbool fm; - - ***** u - 10 invalid as number - ***** x - 10 invalid as number - - -> - boolean(not(u>10) \/ x>10) - -x:=3$ -testbool fm; - - ***** u - 10 invalid as number - - -> - boolean(not(u>10)) - -x:=17$ - -testbool fm; - - ***** u - 10 invalid as number - - -> - 1 - -\end{verbatim} -\end{document} - +\documentstyle[11pt,reduce]{article} +\title{BOOLEAN: Computing with boolean expressions} +\date{} +\author{ +H. Melenk\\[0.05in] +Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ +Heilbronner Strasse 10 \\ +D--10711 Berlin -- Wilmersdorf \\ +Federal Republic of Germany \\[0.05in] +E--mail: melenk@sc.zib--berlin.de \\[0.05in] +} + +\begin{document} +\maketitle + +\section{Introduction} + +The package {\bf Boolean} supports the computation with +boolean expressions in the propositional calculus. +The data objects are composed from algebraic expressions (``atomic parts'', ``leafs'') +connected by the infix boolean operators {\bf and}, {\bf or}, +{\bf implies}, {\bf equiv}, and the unary prefix operator +{\bf not}. {\bf Boolean} allows you to simplify expressions +built from these operators, and to test properties like +equivalence, subset property etc. Also the reduction of +a boolean expression by a partial evaluation and combination +of its atomic parts is supported. + +\section{Entering boolean expressions} + +In order to distinguish boolean data expressions from +boolean expressions in the \REDUCE programming +language (e.g. in an {\bf if} statement), each expression +must be tagged explicitly by an operator {\bf boolean}. +Otherwise the boolean operators are not accepted in the +\REDUCE algebraic mode input. +The first argument of {\bf boolean} can be any boolean expression, +which may contain references to other boolean values. +\begin{verbatim} + boolean (a and b or c); + q := boolean(a and b implies c); + boolean(q or not c); +\end{verbatim} +Brackets are used to override the operator precedence as usual. +The leafs or atoms of a boolean expression are those parts which +do not contain a leading boolean operator. These are +considered as constants during the boolean evaluation. There +are two pre-defined values: +\begin{itemize} +\item {\bf true}, {\bf t} or {\bf 1} +\item {\bf false}, {\bf nil} or {\bf 0} +\end{itemize} +These represent the boolean constants. In a result +form they are used only as {\bf 1} and {\bf 0}. + +By default, a {\bf boolean} expression is converted to a +disjunctive normal form, that is a form where terms are connected +by {\bf or} on the top level and each term is set of leaf +expressions, eventually preceded by {\bf not} and connected +by {\bf and}. An operators {\bf or} or {\bf and} is omitted +if it would have only one single operand. The result of +the transformation is again an expression with leading +operator {\bf boolean} such that the boolean expressions +remain separated from other algebraic data. Only the boolean +constants {\bf 0} and {\bf 1} are returned untagged. + +On output, the +operators {\bf and} and {\bf or} are represented as +\verb+/\+ and \verb+\/+, respectively. +\begin{verbatim} +boolean(true and false); -> 0 +boolean(a or not(b and c)); -> boolean(not(b) \/ not(c) \/ a) +boolean(a equiv not c); -> boolean(not(a)/\c \/ a/\not(c)) +\end{verbatim} + +\section{Normal forms} + +The {\bf disjunctive} normal form is used by default. It +represents the ``natural'' view and allows us to represent +any form free or parentheses. +Alternatively a {\bf conjunctive} normal form can be +selected as simplification target, which is a form with +leading operator {\bf and}. To produce that form add the keyword {\bf and} +as an additional argument to a call of {\bf boolean}. +\begin{verbatim} +boolean (a or b implies c); + -> + boolean(not(a)/\not(b) \/ c) + +boolean (a or b implies c, and); + -> + boolean((not(a) \/ c)/\(not(b) \/ c)) +\end{verbatim} + +Usually the result is a fully reduced disjunctive or conjuntive normal +form, where all redundant elements have been eliminated following the +rules + +$ a \wedge b \vee \neg a \wedge b \longleftrightarrow b$ + +$ a \vee b \wedge \neg a \vee b \longleftrightarrow b$ + + +Internally the full normal forms are computed +as intermediate result; in these forms each term contains +all leaf expressions, each one exactly once. This unreduced form is returned +when you set the additional keyword {\bf full}: +\begin{verbatim} +boolean (a or b implies c, full); + -> +boolean(a/\b/\c \/ a/\not(b)/\c \/ not(a)/\b/\c \/ not(a)/\not(b)/\c + + \/ not(a)/\not(b)/\not(c)) +\end{verbatim} + +The keywords {\bf full} and {\bf and} may be combined. + +\section{Evaluation of a boolean expression} + +If the leafs of the boolean expression are algebraic expressions +which may evaluate to logical values because the environment +has changed (e.g. variables have been bound), you can re--investigate +the expression using the operator {\tt testbool} with the boolean +expression as argument. This operator tries to evaluate all +leaf expressions in \REDUCE boolean style. As many +terms as possible are replaced by their boolean values; the others +remain unchanged. The resulting expression is contracted to a +minimal form. The result {\bf 1} (= true) or {\bf 0} (=false) +signals that the complete expression could be evaluated. + +In the following example the leafs are built as numeric greater test. +For using ${\bf >}$ in the expressions the greater sign must +be declared operator first. The error messages are meaningless. +\begin{verbatim} +operator >; +fm:=boolean(x>v or not (u>v)); + -> + fm := boolean(not(u>v) \/ x>v) + +v:=10$ + +testbool fm; + + ***** u - 10 invalid as number + ***** x - 10 invalid as number + + -> + boolean(not(u>10) \/ x>10) + +x:=3$ +testbool fm; + + ***** u - 10 invalid as number + + -> + boolean(not(u>10)) + +x:=17$ + +testbool fm; + + ***** u - 10 invalid as number + + -> + 1 + +\end{verbatim} +\end{document} + Index: r36/doc/CALI.TEX ================================================================== --- r36/doc/CALI.TEX +++ r36/doc/CALI.TEX @@ -1,3168 +1,3168 @@ -% CALI user documentation -% H.-G. Graebe | Univ. Leipzig | Version 2.2.1 - -\documentstyle[11pt]{article} -\date{June 28, 1995} - -\textheight 21cm -\textwidth 15cm -\voffset -60pt -\hoffset -45pt - -\newcommand{\gr}{Gr\"obner } -\newcommand{\x}{{\bf x}} -\newcommand{\ind}[1]{{\em #1}\index{#1}} -\newcommand{\pbx}[1]{\mbox{}\hfill \parbox[t]{12cm}{#1} \pagebreak[3]} -\newcommand{\nl}{\newline \hspace*{5mm}} - -\makeindex - -\title{CALI\\[20pt] A REDUCE Package for \\ - Commutative Algebra \\Version 2.2.1} - -\author{ -Hans-Gert Gr\"abe \\[15pt] -Universit\"at Leipzig\\ -Institut f\"ur Informatik \\ -Augustusplatz 10 -- 11\\ -04109 Leipzig / Germany\\[20pt] -email: graebe@informatik.uni-leipzig.de} - -\begin{document} - -\maketitle - -\vfill -Key words: -affine and projective monomial curves, -affine and projective sets of points, -analytic spread, -associated graded ring, -blowup, -border bases, -constructive commutative algebra, -dual bases, -elimination, -equidimensional part, -extended \gr factorizer, -free resolution, -\gr algorithms for ideals and module, -\gr factorizer, -ideal and module operations, -independent sets, -intersections, -lazy standard bases, -local free resolutions, -local standard bases, -minimal generators, -minors, -normal forms, -pfaffians, -polynomial maps, -primary decomposition, -quotients, -symbolic powers, -symmetric algebra, -triangular systems, -weighted Hilbert series, -primality test, -radical, -unmixed radical. - -\pagebreak - -\tableofcontents - -\pagebreak - -\section{Introduction} - -This package contains algorithms for computations in commutative -algebra closely related to the \gr algorithm for ideals and modules. -Its heart is a new implementation of the \gr algorithm\footnote{The -data representation even for polynomials is different from that given -in the {\tt groebner} package distributed with REDUCE (and rests on ideas -used in the {\tt dipoly} package).} that allows the computation of -syzygies, too. This implementation is also applicable to submodules of -free modules with generators represented as rows of a matrix. - -Moreover CALI contains facilities for local computations, using a -modern implementation of Mora's standard basis algorithm, see -\cite{MPT} and \cite{tcah}, that works for arbitrary term orders. -The full analogy between modules over the local ring \linebreak[1] -$k[x_v:v\in H]_{\bf m}$ and homogeneous (in fact H-local) modules -over $k[x_v:v\in H]$ is reflected through the switch -\ind{Noetherian}. Turn it on (\gr basis, the default) or off (local -standard basis) to choose appropriate algorithms -automatically. In v.\ 2.2 we present an unified approach to both -cases, using reduction with bounded ecart for non Noetherian term -orders, see \cite{ala} for details. This allows to have a common -driver for the \gr algorithm in both cases. - -CALI extends also the restricted term order facilities of the {\tt -groebner} package, defining term orders by degree vector lists, and -the rigid implementation of the sugar idea, by a more flexible -\ind{ecart} vector, in particular useful for local computations, see -\cite{tcah}. -\medskip - -The package was designed mainly as a symbolic mode programming -environment extending the build-in facilities of REDUCE for the -computational approach to problems arising naturally in commutative -algebra. An algebraic mode interface accesses (in a more rigid frame) -all important features implemented symbolically and thus -should be favored for short sample computations. - -On the other hand, tedious computations are strongly recommended to -be done symbolically since this allows considerably more flexibility -and avoids unnecessary translations of intermediate results from -CALI's internal data representation to the algebraic mode and vice -versa. Moreover, one can easily extend the package with new symbolic -mode scripts, or do more difficult interactive computations. For all -these purposes the symbolic mode interface offers substantially more -facilities than the algebraic one. -\medskip - -For a detailed description of special symbolic mode procedures one -should consult the source code and the comments therein. In this -manual we can give only a brief description of the main ideas -incorporated into the package CALI. We concentrate on the data -structure design and the description of the more advanced algorithms. -For sample computations from several fields of commutative algebra -the reader may consult also the {\em cali.tst} file. -\medskip - -As main topics CALI contains facilities for -\begin{itemize} -\item defining rings, ideals and modules, - -\item computing \gr bases and local standard bases, - -\item computing syzygies, resolutions and (graded) Betti numbers, - -\item computing (now also weighted) Hilbert series, multiplicities, -independent sets, and dimensions, - -\item computing normal forms and representations, - -\item computing sums, products, intersections, quotients, stable -quotients, elimination ideals etc., - -\item primality tests, computation of radicals, unmixed radicals, -equidimensional parts, primary decompositions etc. of ideals and -modules, - -\item advanced applications of \gr bases (blowup, associated graded -ring, analytic spread, symmetric algebra, monomial curves etc.), - -\item applications of linear algebra techniques to zero dimensional - ideals, as e.g.\ the FGLM change of term orders, border bases - and affine and projective ideals of sets of points, - -\item splitting polynomial systems of equations mixing factorization and -the \gr algorithm, triangular systems, and different versions of the -extended \gr factorizer. - -\end{itemize} - -Below we will use freely without further explanation the notions -common for text books and papers about constructive commutative -algebra, assuming the reader to be familiar with the corresponding -ideas and concepts. For further references see e.g.\ the text books -\cite{BKW}, \cite{CLO} and \cite{Mishra} or the survey papers -\cite{B1}, \cite{B2} and \cite{Ro}. - -\subsection{Description of the Documents Distributed with CALI} - -The CALI package contains the following files: -\begin{quote} -cali.chg - -\pbx{a detailed report of changes from v.\ 2.1 to v.\ 2.2. and 2.2.1} - -cali.log - -\pbx{the output file, that cali.tst should produce with -\begin{quote} \tt -load\_package cali; - -out "logfile"\$ - -in "cali.tst"; - -shut "logfile"\$ -\end{quote}} - -cali.red - -\pbx{the CALI source file.} - -cali.tex - -\pbx{this manual.} - -cali.tst - -\pbx{a test file with various examples and applications of CALI.} - -\end{quote} - -CALI should be precompiled as usual, i.e.\ either using the {\em -makefasl} utility of REDUCE or ``by hand'' via -\begin{verbatim} - faslout "cali"$ - in "cali.red"$ - faslend$ -\end{verbatim} -and then loaded via -\begin{verbatim} - load_package cali; -\end{verbatim} -Upon successful loading CALI responds with a message containing the -version number and the last update of the distribution. - -\begin{center} -\fbox{\parbox{12cm}{Feel free to contact me by email if You have -problems to get CALI started. Also comments, hints, bug reports etc. -are welcome.}} -\end{center} - -\subsection{CALI's Language Concept} - -From a certain point of view one of the major disadvantage of the -current RLISP (and the underlying PSL) language is the fact -that it supports modularity and data encapsulation only in a -rudimentary way. Since all parts of code loaded into a session are -visible all the time, name conflicts between different packages may -occur, will occur (even not issuing a warning message), and are hard -to prevent, since packages are developed (and are still developing) -by different research groups at different places and different time. - -A (yet rudimentary) concept of REDUCE packages and modules indicates the -direction into what the REDUCE designers are looking for a solution -for this general problem. -\medskip - -CALI (2.0 and higher) follows a name concept for internal procedures -to mimick data encapsulation at a semantical level. We hope this way -on the one hand to resolve the conflicts described above at least for -the internal part of CALI and on the other hand to anticipate a -desirable future and already foregoing development of REDUCE towards -a true modularity. - -The package CALI is divided into several modules, each of them -introducing either a single new data type together with basic -facilities, constructors, and selectors or a collection of algorithms -subject to a common problem. Each module contains \ind{internal -procedures}, conceptually hidden by this module, \ind{local -procedures}, designed for a CALI wide use, and \ind{global -procedures}, exported by CALI into the general (algebraic or -symbolic) environment of REDUCE. A header \ind{module cali} contains -all (fluid) global variables and switches defined by the pacakge -CALI. - -Along these lines the CALI procedures available in symbolic mode are -divided into three types with the following naming convention: -\begin{quote} -\verb|module!=procedure| - -\pbx{internal to the given module.} - -\verb|module_procedure| - -\pbx{exported by the given module into the local CALI environment.} - -\verb|procedure!*| - -\pbx{a global procedure usually having a semantically equivalent -procedure (possibly with another parameter list) without trailing -asterisk in algebraic mode.} -\end{quote} -There are also symbolic mode equivalents without trailing asterisk, if -the algebraic procedure is not a {\em psopfn}, but a {\em symbolic -operator}. They transfer data to CALI's internal structure and call -the corresponding procedure with trailing asterisk. CALI 2.2 -distinguishes between algebraic and symbolic calls of such a -procedure. In symbolic mode such a procedure calls the corresponding -procedure with trailing asterisk directly without data transfer. -\medskip - -CALI 2.2 follows also a more concise concept for global -variables. There are three types of them: -\begin{quote} -True {\em fluid} global variables, - -\pbx{that are part of the current data structure, as e.g.\ the current -base ring and the degree vector. They are often locally rebound to be -restored after interrupts.} - -Global variables, stored on the property list of the package name {\tt -cali}, - -\pbx{that reflect the state of the computational model as e.g.\ the -trace level, the output print level or the chosen version of the \gr -basis algorithm. There are several such parameters in the module -\ind{dualbases} to serve the common dual basis driver with -information for different applications.} - -{\em Switches,} - -\pbx{that allow to choose different branches of algorithms. Note that -this concept interferes with the second one. Different {\em versions} -of algorithms, that apply different functions in a common driver, are -{\em not} implemented through switches.} -\end{quote} - -\subsection{New and Improved Facilities in v.\ 2.1} - -The major changes in v.\ 2.1 reflect the experience we've got from the -use of CALI 2.0. The following changes are worth mentioning -explicitely: -\begin{enumerate} -\item The algebraic rule concept was adapted to CALI. It allows to -supply rule based coefficient domains. This is a more efficient way -to deal with (easy) algebraic numbers than through the {\em arnum -package}. - -\item \ind{listtest} and \ind{listminimize} provide an unified -concept for different list operations previously scattered in the -source text. - -\item There are several new quotient algorithms at the symbolic level -(both the general element and the intersection approaches are -available) and new features for the computation of equidimensional -hull and equidimensional radical. - -\item A new \ind{module scripts} offers advanced applications of \gr -bases. - -\item Several advanced procedures initialize a \gr basis computation -over a certain intermediate base ring or term order as e.g.\ -\ind{eliminate}, \ind{resolve}, \ind{matintersect} or all -\ind{primary decomposition} procedures. Interrupting a computation in -v.\ 2.1 now restores the original values of CALI's global variables, -since all intermediate procedures work with local copies of -the global variables.\footnote{Note that recovering the base -ring this way may cause some trouble since the intermediate ring, -installed with \ind{setring}, changed possibly the internal variable -order set by {\em setkorder}.} This doesn't apply to advanced -procedures that change the current base ring as e.g.\ \ind{blowup}, -\ind{preimage}, \ind{sym} etc. - -\end{enumerate} - -\subsection{New and Improved Facilities in v.\ 2.2} - -Version 2.2 (beside bug fixes) incorporates several new facilities of -constructive non linear algebra that we investigated the last two -years, as e.g.\ dual bases, the \gr factorizer, triangular systems, and -local standard bases. Essential changes concern the following topics: -\begin{enumerate} -\item The CALI modules \ind{red} and \ind{groeb} were rewritten and -the \ind{module mora} was removed. This is -due to new theoretical insight into standard bases theory as -e.g.\ described in \cite{tcah} or \cite{ala}. The \gr basis algorithm -is reorganized as a \gr driver with simplifier and base lists, that -involves different versions of polynomial reduction according to the -setting via \ind{gbtestversion}. It applies now to -both noetherian and non noetherian term orders in a unified way. - -The switches \ind{binomial} and \ind{lazy} were removed. - -\item The \gr factorizer was thoroughly revised, extended along the -lines explained in \cite{fgb}, and collected into a separate -\ind{module groebf}. It now allows a list of constraints also in -algebraic mode. Two versions of an \ind{extended \gr factorizer} -produce \ind{triangular systems}, -i.e.\ a decomposition into quasi prime components, see \cite{efgb}, -that are well suited for further (numerical) evaluation. There is also -a version of the \gr factorizer that allows a list of problems as -input. This is especially useful, if a system is splitted with respect -to a ``cheap'' (e.g. degrevlex) term order and the pieces are -recomputed with respect to a ``hard'' (e.g. pure lex) term order. - -The extended \gr factorizer involves, after change to dimension zero, -the computation of \ind{triangular systems}. The corresponding module -\ind{triang} extends the facilities for zero dimensional ideals and -modules in the \ind{module odim}. - -\item A new \ind{module lf} implements the \ind{dual bases} approach -as described in \cite{MMM}. On this basis there are new -implementations of \ind{affine\_points} and \ind{proj\_points}, that -are significantly faster than the old ones. The linear algebra -\ind{change of term orders} \cite{FGLM} is available, too. There are -two versions, one with precomputed \ind{border basis}, the other with -conventional normal forms. - -\item \ind{dpmat}s now have a \ind{gb-tag} that indicates, whether the -given ideal or module basis is already a \gr basis. This avoids -certain \gr basis recomputations especially during advanced algorithms -as e.g.\ prime decomposition. In the algebraic interface \gr bases are -computed automatically when needed rather than to issue an error -message as in v.\ 2.1. So one can call \ind{modequalp} or \ind{dim} -etc. not having computed \gr bases in advance. Note that such -automatic computation can be avoided with \ind{setgbasis}. - -\item Hilbert series are now \ind{weighted Hilbert series}, since -e.g.\ for blow up rings the generating ideal is multigraded. Usual -Hilbert series are computed as in v.\ 2.1 with respect to the -\ind{ecart vector}. Weighted Hilbert series accept a list of (integer) -weight lists as second parameter. - -\item There are some name and conceptual changes to existing -procedures and variables to have a more concise semantic concept. This -concerns -\begin{quote} -\ind{tracing} (the trace parameter is now stored on the property list -of {\tt cali} and should be set with \ind{setcalitrace}), - -choosing different versions of the \gr algorithm (through -\ind{gbtestversion}) and the Hilbert series computation (through -\ind{hftestversion}), - -some names (\ind{mat2list} replaced \ind{flatten}, \ind{HilbertSeries} -replaced {\em hilbseries}) and - -parameter lists of some local and internal procedures (consult {\em -cali.chg} for details). -\end{quote} - -\item The \ind{revlex term order} is now the reverse lexicographic -term order on the {\bf reversely} ordered variables. This is consistent -with other computer algebra systems (e.g.\ SINGULAR or -AXIOM)\footnote{But different to the currently distibuted {\tt -groebner} package in REDUCE. Note that the computations in -\cite{fgb} were done {\em before} these changes.} and implies the same -order on the variables for deglex and degrevlex term orders (this was -the main reason to change the definition). - -\item Ideals of minors, pfaffians and related stuff are now -implemented as extension of the internal {\tt matrix} package and -collected into a separate \ind{module calimat}. Thus they allow more -general expressions, especially with variable exponents, as general -REDUCE matrices do. So one can define generic ideals as e.g.\ ideals -of minors or pfaffians of matrices, containing generic expressions as -elements. They must be specified for further use in CALI substituting -general exponents by integers. - -\end{enumerate} - -\subsection{New and Improved Facilities in v.\ 2.2.1\label{221}} - -The main change concerns the primary decomposition algorithm, where I -fixed a serious bug for deciding, which embedded primes are really -embedded\footnote{That there must be a bug was pointed out to me by -Shimoyama Takeshi who compared different p.d.\ implementations. The -bug is due to an incorrect test for embedded primes: A (superfluous) -primary component may contain none of the isolated primary components, -but their intersection! Note that neither \cite{GTZ} nor \cite{BKW} -comment on that. Details of the implementation will appear in -\cite{primary}.}. During that remake I incorporated also the \gr -factorizer to compute isolated primes. Since REDUCE has no -multivariate {\em modular} factorizer, the switch \ind{factorprimes} -may be turned off to switch to the former algorithm. - - - -Some minor bugs are fixed, too, e.g.\ the bug that made \ind{radical} -crashing. - - - - -\section{The Computational Model} - -This section gives a short introduction into the data type design of -CALI at different levels. First (\S 1 and 2) we describe CALI's way -of algorithmic translation of the abstract algebraic objects {\em -ring of polynomials, ideal} and (finitely generated) {\em module}. -Then (\S 3 and 4) we describe the algebraic mode interface of CALI -and the switches and global variables to drive a session. In the next -chapter we give a more detailed overview of the basic (symbolic mode) data -structures involved with CALI. We refer to the appendix for a short -summary of the commands available in algebraic mode. - -\subsection{The Base Ring} - -A polynomial ring consists in CALI of the following data: -\begin{quote} -a list of variable names - -\pbx{All variables not occuring in the list of ring names are treated -as parameters. Computations are executed denominatorfree, but the -results are valid only over the corresponding parameter {\em field} -extension.} - -a term order and a term order tag - -\pbx{They describe the way in which the terms in each polynomial (and -polynomial vector) are ordered.} - -an ecart vector - -\pbx{A list of positive integers corresponding to the variable -names.} -\end{quote} - -A \ind{base ring} may be defined (in algebraic mode) through the -command -\begin{verbatim} - setring -\end{verbatim} -with $$ ::= \{\, vars,\,tord,\,tag\,[,\,ecart\,]\,\} resp. -\begin{verbatim} - setring(vars, tord, tag [,ecart]) -\end{verbatim} -\index{setring} -This sets the global (symbolic) variable \ind{cali!=basering}. Here -{\tt vars} is the list of variable names, {\tt tord} a (possibly -empty) list of weight lists, the \ind{degree vectors}, and {\tt tag} -the tag LEX or REVLEX. Optionally one can supply {\tt ecart}, a list -of positive integers of the same length as {\tt vars}, to set an ecart -vector different from the default one (see below). - -The degree vectors must have the same length as {\tt vars}. If $(w_1\ -\ldots\ w_k)$ is the list of degree vectors then -\[x^aj\ :\ a_i=b_i\quad\mbox{and}\quad a_j>b_j\ -\mbox{(revlex.)}\] - -Every term order can be represented in such a way, see \cite{MR88}. - -During the ring setting the term order will be checked to be -Noetherian (i.e.\ to fulfill the descending chain condition) provided -the \ind{switch Noetherian} is on (the default). The same applies -turning {\em noetherian on}: If the term order of the underlying -base ring isn't Noetherian the switch can't be turned over. Hence, -starting from a non Noetherian term order, one should define {\em -first} a new ring and {\em then} turn the switch on. - -Useful term orders can be defined by the procedures -\begin{quote} -\verb|degreeorder vars|, \index{degreeorder} - -\pbx{that returns $tord=\{\{1,\ldots ,1\}\}$.} - -\verb|localorder vars|, \index{localorder} - -\pbx{that returns $tord=\{\{-1,\ldots ,-1\}\}$ (a non Noetherian term -order for computations in local rings).} - -\verb|eliminationorder(vars,elimvars)|, \index{eliminationorder} - -\pbx{that returns a term order for elimination of the variables in -{\tt elimvars}, a subset of all {\tt vars}. It's recommended to -combine it with the tag REVLEX.} - -\verb|blockorder(vars,integerlist)|, \index{blockorder} - -\pbx{that returns the list of degree vectors for the block order with -block lengths given in the {\tt integerlist}. Note that these numbers -should sum up to the length of the variable list supplied as the first -argument.} -\end{quote} - -\noindent Examples: -\begin{verbatim} -vars:={x,y,z}; -tord:=degreeorder vars; % Returns {{1,1,1}}. -setring(vars,tord,lex); % GRADLEX in the groebner package. - -% or - -setring({a,b,c,d},{},lex); % LEX in the groebner package. - -% or - -vars:={a,b,c,x,y,z}; -tord:=eliminationorder(vars,{x,y,z}); -tord:=reverse blockorder(vars,{3,3}); - % Return both {{0,0,0,1,1,1},{1,1,1,0,0,0}}. -setring(vars,tord,revlex); -\end{verbatim} -\pagebreak[2] - -The base ring is initialized with \\[10pt] -\verb|{{t,x,y,z},{{1,1,1,1}},revlex,{1,1,1,1}}|,\\[10pt] -i.e.\ $S=k[t,x,y,z]$ supplied with the degree wise reverse -lexicographic term order. -\begin{quote} -\verb|getring m|\index{getring} - -\pbx{returns the ring attached to the object with the identifier -$m$. E.g.\ } - -\verb|setring getring m| - -\pbx{(re)sets the base ring to the base ring of the formerly defined -object (ideal or module) $m$.} - -\verb|getring()| - -\pbx{returns the currently active base ring.} -\end{quote} - -CALI defines also an \ind{ecart vector}, attaching to each variable a -positive weight with respect to that homogenizations and related -algorithms are executed. It may be set optionally by the user during -the \ind{setring} command. (Default: If the term order is a -(positive) degree order then the ecart is the first degree vector, -otherwise each ecart equals 1). - -The ecart vector is used in several places for efficiency reason (\gr -basis computation with the sugar strategy) or for termination (local -standard bases). If the input is homogeneous the ecart vector should -reflect this homogeneity rather than the first degree vector to -obtain the best possible performance. For a discussion of local -computations with encoupled ecart vector see \cite{tcah}. In general -the ecart vector is recommended to be chosen in such a way that the -input examples become close to be homogeneous. {\em Homogenizations} -and \ind{Hilbert series} are computed with respect to this ecart -vector. -\medskip - -\noindent \verb|getecart()|\index{getecart} returns the ecart vector -currently set. - - -\subsection{Ideals and Modules} - -If $S=k[x_v,\ v \in H]$ is a polynomial ring, a matrix $M$ of size -$r\times c$ defines a map -\[f\ :\ S^r \longrightarrow S^c\] -by the following rule -\[ f(v):=v\cdot M \qquad \mbox{ for } v \in S^r.\] -There are two modules, connected with such a map, $im\ f$, the -submodule of $S^c$ generated by the rows of $M$, and $coker\ f\ -(=S^c/im\ f)$. Conceptually we will identify $M$ with $im\ f$ for the -basic algebra, and with $coker\ f$ for more advanced topics of -commutative algebra (Hilbert series, dimension, resolution etc.) -following widely accepted conventions. - -With respect to a fixed basis $\{e_1,\ldots ,e_c\}$ one can define -module term orders on $S^c$, \gr bases of submodules of $S^c$ etc. -They generalize the corresponding notions for ideal bases. See -\cite{E} or \cite{MM} for a detailed introduction to this area of -computational commutative algebra. This allows to define joint -facilities for both ideals and submodules of free modules. Moreover -computing syzygies the latter come in in a natural way. - -CALI handles ideal and module bases in a unique way representing them -as rows of a \ind{dpmat} ({\bf d}istributive {\bf p}olynomial {\bf -mat}rix). It attaches to each unit vector $e_i$ a monomial $x^{a_i}$, -the $i$-th \ind{column degree} and represents the rows of a dpmat $M$ -as lists of module terms $x^ae_i$, sorted with respect to a -\ind{module term order}, that may be roughly\footnote{The correct -definition is even more difficult.} described as -\bigskip - -\begin{tabular}{cccp{6cm}} -$x^ae_ij$ (revlex.)\\} -\end{tabular} - -Every dpmat $M$ has its own column degrees (no default !). They are -managed through a global (symbolic) variable \ind{cali!=degrees}. -\begin{quote} -\verb|getdegrees m| \index{getdegrees} - -\pbx{returns the column degrees of the object with identifier m.} - -\verb|getdegrees()| - -\pbx{returns the current setting of {\em cali!=degrees}.} - -\verb|setdegrees | \index{setdegrees} - -\pbx{sets {\em cali!=degrees} correspondingly. Use this command -before executing {\em setmodule} to give a dpmat prescribed column -degrees since cali!=degrees has no default value and changes during -computations. A good guess is to supply the empty list (i.e.\ all -column degrees are equal to $\x^0$). Be careful defining modules -without prescribed column degrees.} -\end{quote} - -To distinguish between \ind{ideals} and \ind{modules} the former are -represented as a \ind{dpmat} with $c=0$ (and hence without column -degrees). If $I \subset S$ is such an ideal one has to distinguish -between the ideal $I$ (with $c=0$, allowing special ideal operations -as e.g.\ ideal multiplication) and the submodule $I$ of the free -one dimensional module $S^1$ (with $c=1$, allowing matrix operations -as e.g.\ transposition, matrix multiplication etc.). \ind{ideal2mat} -converts an (algebraic) list of polynomials into an (algebraic) -matrix column whereas \ind{mat2list} collects all matrix entries into -a list. - -\subsection{The Algebraic Mode Interface} - -Corresponding to CALI's general philosophy explained in the -introduction the algebraic mode interface translates algebraic input -into CALI's internal data representation, calls the corresponding -symbolic functions, and retranslates the result back into algebraic -mode. Since \gr basis computations may be very tedious even on small -examples, one should find a well balance between the storage of -results computed earlier and the unavoidable time overhead and memory -request associated with the management of these results. - -Therefore CALI distinguishes between {\em free} and {\em bounded} -\index{free identifier}\index{bounded identifier} identifiers. Free -identifiers stand only for their value whereas to bounded identifiers -several internal information is attached to their property list for -later use. -\medskip - -After the initialization of the {\em base ring} bounded identifiers -for ideals or modules should be declared via -\begin{verbatim} -setmodule(name,matrix value) -\end{verbatim} -resp. -\begin{verbatim} -setideal(name,list of polynomials) -\end{verbatim} -\index{setmodule}\index{setideal} -This way the corresponding internal representation (as \ind{dpmat}) -is attached to {\tt name} as the property \ind{basis}, the prefix -form as its value and the current base ring as the property -\ind{ring}. - -Performing any algebraic operation on objects defined this way their -ring will be compared with the current base ring (including the term -order). If they are different an error message occurs. If {\tt m} is -a valid name, after resetting the base ring -\begin{verbatim} -setmodule(m1,m) -\end{verbatim} -reevaluates {\tt m} with respect to the new base ring (since the -{\em value} of {\tt m} is its prefix form) and assigns the reordered -dpmat to {\tt m1} clearing all information previously computed for -{\tt m1} ({\tt m1} and {\tt m} may coincide). - -All computations are performed with respect to the ring $S=k[x_v\in -{\tt vars}]$ over the field $k$. Nevertheless by efficiency reasons -\ind{base coefficients} are represented in a denominator free way as -standard forms. Hence the computational properties of the base -coefficient domain depend on the \ind{dmode} and also on auxiliary -variables, contained in the expressions, but not in the variable -list. They are assumed to be parameters. - -Best performance will be obtained with integer or modular domain -modes, but one can also try \ind{algebraic numbers} as coefficients -as e.g.\ generated by {\tt sqrt} or the {\tt arnum} package. To avoid -an unnecessary slow-down connected with the management of simplified -algebraic expressions there is a \ind{switch hardzerotest} (default: -off) that may be turned on to force an additional simplification of -algebraic coefficients during each zero test. It should be turned on -only for domain modes without canonical representations as e.g.\ -mixtures of arnums and square roots. We remind the general zero -decision problem for such domains. - -Alternatively, CALI offers the possibility to define a set of -algebraic substitution rules that will affect CALI's base coefficient -arithmetic only. -\begin{quote} -\verb|setrules |\index{setrules} - -\pbx{transfers the (algebraic) rule list into the internal -representation stored at the {\tt cali} value {\tt rules}. - -In particular, {\tt setrules \{\}} clears the rules previously set.} - -\verb|getrules()|\index{getrules} - -\pbx{returns the internal CALI rules list in algebraic form.} -\end{quote} - -We recommend to use \ind{setrules} for computations with algebraic -numbers since they are better adapted to the data structure of CALI -than the algebraic numbers provided by the {\tt arnum} package. -Note, that due to the zero decision problem -complicated {\em setrules} based computations may produce wrong -results if base coefficient's pseudo division is involved (as e.g.\ -with \ind{dp\_pseudodivmod}). In this case we recommend to enlarge -the variable set and add the defining equations of the algebraic -numbers to the equations of the problem\footnote{A {\em qring} -facility for the computation over quotient rings will be incorporated -into future versions.}. -\medskip - -The standard domain (Integer) doesn't allow denominators for input. -\ind{setideal} clears automatically the common denominator of each -input expression whereas a polynomial matrix with true rational -coefficients will be rejected by \ind{setmodule}. -\medskip - -One can save/initialize ideal and module bases together with their -accompanying data (base ring, degrees) to/from a file: -\begin{verbatim} -savemat(m,name) -\end{verbatim} -resp. -\begin{verbatim} -initmat name -\end{verbatim} execute the file transfer from/to disk files with the -specified file {\tt name}. e.g.\ -\begin{verbatim} -savemat(m,"myfile"); -\end{verbatim} -saves the base ring and the ideal basis of $m$ to the file ``myfile'' -whereas -\begin{verbatim} -setideal(m,initmat "myfile"); -\end{verbatim} -sets the current base ring (via a call to \ind{setring}) to the base -ring of $m$ saved at ``myfile'' and then recovers the basis of $m$ -from the same file. - -\subsection{Switches and Global Variables} - -There are several switches, (fluid) global variables, a trace -facility, and global parameters on the property list of the package -name {\tt cali} to control CALI's computations. -\medskip - -\subsubsection*{Switches} - -\begin{quote} -\ind{bcsimp} - -\pbx{on: Cancel out gcd's of base coefficients. (Default: on)} - -\ind{detectunits} - -\pbx{on: replace polynomials of the form \newline -$\langle monomial\rangle * -\langle polynomial\ unit\rangle $ by $\langle monomial\rangle$ -during interreductions and standard basis computations. - -Affects only local computations. (Default: off)} - -\ind{factorprimes} - -\pbx{on: Invoke the \gr factorizer during computation of isolated -primes. (Default: on). Note that REDUCE lacks a modular multivariate -factorizer, hence for modular prime decomposition computations this -switch has to be turned off.} - -\ind{factorunits} - -\pbx{on: factor polynomials and remove polynomial unit factors -during interreductions and standard basis computations. - -Affects only local computations. (Default: off)} - -\ind{hardzerotest} - -\pbx{on: try an additional algebraic simplification of base -coefficients at each base coefficient's zero test. Useful only for -advanced base coefficient domains without canonical REDUCE -representation. May slow down the computation drastically. -(Default: off)} - -\ind{lexefgb} - -\pbx{on: Use the pure lexicographic term order and \ind{zerosolve} -during reduction to dimension zero in the \ind{extended \gr -factorizer}. This is a single, but possibly hard task compared to the -degrevlex invocation of \ind{zerosolve1}. See \cite{efgb} for a -discussion of different zero dimensional solver strategies. -(Default: off)} - -\ind{Noetherian} - -\pbx{on: choose algorithms for Noetherian term orders. - -off: choose algorithms for local term orders. - -(Default: on)} - -\ind{red\_total} - -\pbx{on: compute total normal forms, i.e. apply reduction (Noetherian -term orders) or reduction with bounded ecart (non Noetherian term -orders to tail terms of polynomials, too. - -off: Do only top reduction. - -(Default: on)} - -\end{quote} - -\subsubsection*{Tracing} - -Different to v.\ 2.1 now intermediate output during the computations -is controlled by the value of the {\tt trace} and {\tt printterms} -entries on the property list of the package name {\tt cali}. The -former value controls the intensity of the intermediate output -(Default: 0, no tracing), the latter the number of terms printed in -such intermediate polynomials (Default: all). -\begin{quote} -\verb|setcalitrace |\index{setcalitrace} - -\pbx{changes the trace intensity. Set $n=2$ for a sparse tracing (a -dot for each reduction step). -Other good suggestions are the values 30 or 40 for tracing the \gr -algorithm or $n>70$ for tracing the normal form algorithm. The higher -$n$ the more intermediate information will be given.} - -\verb|setcaliprintterms |\index{setcaliprintterms} - -\pbx{sets the number of terms that are printed in intermediate -polynomials. Note that this does not affect the output of whole {\em -dpmats}. The output of polynomials with more than $n$ terms ($n>0$) -breaks off and continues with ellipses.} - -\verb|clearcaliprintterms()|\index{clearcaliprintterms} - -\pbx{clears the {\tt printterms} value forcing full intermediate -output (according to the current trace level).} -\end{quote} - -\subsubsection*{Global Variables} - -\begin{quote} -\ind{cali!=basering} - -\pbx{The currently active base ring initialized e.g.\ by -\ind{setring}.} - -\ind{cali!=degrees} - -\pbx{The currently active module component degrees initialized e.g.\ -by \ind{setdegrees}.} - -\ind{cali!=monset} - -\pbx{A list of variable names considered as non zero divisors during -\gr basis computations initialized e.g.\ by \ind{setmonset}. Useful -e.g.\ for binomial ideals defining monomial varieties or other prime -ideals.} - -\end{quote} - -\subsubsection*{Entries on the Property List of {\tt cali}} - -This approach is new for v.\ 2.2. Information concerning the state of -the computational model as e.g.\ trace intensity, base coefficient -rules, or algorithm versions are stored as values on the property list -of the package name \ind{cali}. This concerns -\begin{quote} -\ind{trace} and \ind{printterms} - -\pbx{see above.} - -\ind{efgb} - -\pbx{Changed by the \ind{switch lexefgb}.} - -\ind{groeb!=rf} - -\pbx{Reduction function invoked during the \gr algorithm. It can be -changed with \ind{gbtestversion}\ $$ ($n=1,2,3$, default is 1).} - -\ind{hf!=hf} - -\pbx{Variant for the computation of the Hilbert series numerator. It -can be changed with \ind{hftestversion}\ $$ ($n=1,2$, default is 1).} - -\ind{rules} - -\pbx{Algebraic ``replaceby'' rules introduced to CALI with the -\ind{setrules} command.} - -\ind{evlf}, \ind{varlessp}, \ind{sublist}, \ind{varnames}, -\ind{oldborderbasis}, \ind{oldring}, \ind{oldbasis} - -\pbx{see \ind{module lf}, implementing the dual bases approach.} -\end{quote} - - -\section{Basic Data Structures} - -In the following we describe the data structure layers underlying the -dpmat representation in CALI and some important (symbolic) procedures -to handle them. We refer to the source code and the comments therein for -a more complete survey about the procedures available for different -data types. - -\subsection{The Coefficient Domain} - -Base coefficients as implemented in the \ind{module bcsf} are standard -forms in the variables outside the variable list of the current -ring. All computations are executed "denominator free" over the -corresponding quotient field, i.e.\ gcd's are canceled out without -request. To avoid this set the \ind{switch bcsimp} off.\footnote{This -induces a rapid base coefficient's growth and doesn't yield {\bf -Z}-\gr bases in the sense of \cite{GTZ} since the S-pair criteria are -different.} In the given implementation we use the s.f. procedure {\em -qremf} for effective divisibility test. We had some trouble with it -under {\em on factor}. - -Additionally it is possible to supply the -parameters occuring as base coefficients with a (global) set of -algebraic rules.\footnote{This is different from the LET rule -mechanism since they must be present in symbolic mode. Hence for a -simultaneous application of the same rules in algebraic mode outside -CALI they must additionally be declared in the usual way.} -\begin{quote} -\verb|setrules!* r|\index{setrules} - -\pbx{converts an algebraic mode rules list $r$ as e.g.\ used in -WHERE statements into the internal CALI format.} -\end{quote} - -\subsection{The Base Ring} - -The \ind{base ring} is defined by its {\tt name list}, the {\tt -degree matrix} (a list of lists of integers), the {\tt ring tag} (LEX -or REVLEX), and the {\tt ecart}. The name list contains a phantom -name {\tt cali!=mk} for the module component at place 0. -\medskip - -The \ind{module ring} exports among others the selectors -\ind{ring\_names}, \ind{ring\_degrees}, \ind{ring\_tag}, -\ind{ring\_ecart}, the test function \ind{ring\_isnoetherian} and the -transfer procedures from/to an (appropriate, printable by -\ind{mathprint}) algebraic prefix form \ind{ring\_from\_a} (including -extensive tests of the supplied parameters for consistency) and -\ind{ring\_2a}. - -The following procedures allow to define a base ring: -\begin{quote} -\verb|ring_define(name list, degree matrix, ring tag, ecart)| -\index{ring\_define} - -\pbx{combines the given parameters to a ring.} - -\verb|setring!* |\index{setring} - -\pbx{sets {\em cali!=basering} and checks for consistency with the -\ind{switch Noetherian}. It also sets through -\ind{setkorder} the current variable list as main variables. It is -strongly recommended to use {\em setring!* \ldots} instead of {\em -cali!=basering:=\ldots}.} -\end{quote} -\verb|degreeorder!*| , \verb|localorder!*|, \verb|eliminationorder!*|, and -\verb|blockorder!*| -\index{degreeorder} -\index{localorder} -\index{eliminationorder} -\index{blockorder} -define term order matrices in full analogy to algebraic mode. -\medskip - -There are three ring constructors for special purposes: -\begin{quote} -\verb|ring_sum(a,b)|\index{ring\_sum} - -\pbx{returns a ring, that is constructed in the following way: Its -variable list is the union of the (disjoint) lists of the variables -of the rings $a$ and $b$ (in this order) whereas the degree list is -the union of the (appropriately shifted) degree lists of $b$ and $a$ -(in this order). The ring tag is that of $a$. Hence it returns -(essentially) the ring $b\bigoplus a$ if $b$ has a degree part (e.g.\ -useful for elimination problems, introducing ``big'' new variables) -and the ring $a\bigoplus b$ if $b$ has no degree part (introducing -``small'' new variables).} - -\verb|ring_rlp(r,u)|\index{ring\_rlp} - -\pbx{$u$ is a subset of the names of the ring $r$. Returns the ring -$r$, but with a term order ``first degrevlex on $u$, then the order on -r''.} - -\verb|ring_lp(r,u)|\index{ring\_lp} - -\pbx{As $rlp$, but with a term order ``first lex on $u$, then the -order on r''.} -\end{quote} - -\noindent Example: -\begin{verbatim} -vars:='(x y z) -setring!* ring_define(vars,degreeorder!* vars,'lex,'(1 1 1)); - % GRADLEX in the groebner package. -\end{verbatim} - -\subsection{Monomials} - -The current version uses a place-driven exponent representation -closely related to a vector model. This model handles term orders on $S$ -and module term orders on $S^c$ in a unique way. The zero component of the -exponent list of a monomial contains its module component ($>0$) or 0 -(ring element). All computations are executed with respect to a -{\em current ring} (\ind{cali!=basering}) and {\em current (monomial) -weights} of the free generators $e_i, i=1,\ldots,c$, of $S^c$ -(\ind{cali!=degrees}). For efficiency reasons every monomial has a -precomputed degree part that should be reevaluated if {\tt -cali!=basering} (i.e.\ the term order) or {\tt cali!=degrees} were -changed. {\tt cali!=degrees} contains the list of column degrees of -the current module as an assoc. list and will be set automatically by -(almost) all dpmat procedure calls. Since monomial operations use the -degree list that was precomputed with respect to fixed column degrees -(and base ring) -\begin{quote}\bf -watch carefully for {\tt cali!=degrees} programming at the monomial -or dpoly level ! -\end{quote} - -As procedures there are selectors for the module component, the exponent and -the degree parts, comparison procedures, procedures for the management of -the module component and the degree vector, monomial arithmetic, transfer -from/to prefix form, and more special tools. - -\subsection{Polynomials and Polynomial Vectors} - -CALI uses a distributive representation as a list of terms for both -polynomials and polynomial vectors, where a \ind{term} is a dotted -pair -\[(\ .\ ).\] -The \ind{ecart} of a polynomial (vector) $f=\sum{t_i}$ with (module) -terms $t_i$ is defined as \[max(ec(t_i))-ec(lt(t_i)),\] see -\cite{tcah}. Here $ec(t_i)$ denotes the ecart of the term $t_i$, i.e.\ -the scalar product of the exponent vector of $t_i$ (including the -monomial weight of the module generator) with the ecart vector of the -current base ring. - -As procedures there are selectors, dpoly arithmetic including the management -of the module component, procedures for reordering (and reevaluating) -polynomials wrt.\ new term order degrees, for extracting common base -coefficient or monomial factors, for transfer from/to prefix form and for -homogenization and dehomogenization (wrt.\ the current ecart vector). - -Two advanced procedures use ideal theory ingredients: -\begin{quote} -\verb|dp_pseudodivmod(g,f)|\index{dp\_pseudodivmod} - -\pbx{returns a dpoly list $\{q,r,z\}$ such that $z\cdot g = q\cdot f + -r$ and $z$ is a dpoly unit (i.e.\ a scalar for Noetherian term -orders). For non Noetherian term orders the necessary modifications -are described in \cite{ala}. - -$g, f$ and $r$ belong to the same free module or ideal. -} - -\verb|dpgcd(a,b)| \index{dpgcd} - -\pbx{computes the gcd of two dpolys $a$ and $b$ by the syzygy method: -The syzygy module of $\{a,b\}$ is generated by a single element -$[-b_0\ \ a_0]$ with $a=ga_0, b=gb_0$, where $g$ is the gcd of $a$ -and $b$. Since it uses dpoly pseudodivision it may work not properly -with \ind{setrules}.} -\end{quote} - - -\subsection{Base Lists} - -Ideal bases are one of the main ingredients for dpmats. They are -represented as lists of \ind{base elements} and contain together with -each dpoly entry the following information: -\begin{itemize} -\item a number (the row number of the polynomial vector in the -corresponding dpmat). - -\item the dpoly, its ecart (as the main sort criterion), and length. - -\item a representation part, that may contain a representation of the -given dpoly in terms of a certain fixed basis (default: empty). -\end{itemize} - -The representation part is managed during normal form computations -and other row arithmetic of dpmats appropriately with the following -procedures: -\begin{quote} -\verb|bas_setrelations b|\index{bas\_setrelations} - -\pbx{sets the relation part of the base element $i$ in the base list -$b$ to $e_i$.} - -\verb|bas_removerelations b|\index{bas\_removerelations} - -\pbx{removes all relations, i.e.\ replaces them with the zero -polynomial vector.} - -\verb|bas_getrelations b|\index{bas\_getrelations} - -\pbx{gets the relation part of $b$ as a separate base list.} -\end{quote} - -Further there are procedures for selection and construction of base -elements and for the manipulation of lists of base elements as e.g.\ -sorting, renumbering, reordering, simplification, deleting zero base -elements, transfer from/to prefix form, homogenization and dehomogenization. - -\subsection{Dpoly Matrices} - -Ideals and matrices, represented as \ind{dpmat}s, are the central -data type of the CALI package, as already explained above. Every -dpmat $m$ combines the following information: -\begin{itemize} -\item its size (\ind{dpmat\_rows} m,\ind{dpmat\_cols} m), - -\item its base list (\ind{dpmat\_list} m) and - -\item its column degrees as an assoc. list of monomials -(\ind{dpmat\_coldegs} m). If this list is empty, all degrees are -assumed to be equal to $x^0$. - -\item New in v.\ 2.2 there is a \ind{gb-tag} (\ind{dpmat\_gbtag} m), -indicating that the given base list is already a \gr basis (under the -given term order). -\end{itemize} - -The \ind{module dpmat} contains selectors, constructors, and the -algorithms for the basic management of this data structure as e.g.\ -file transfer, transfer from/to algebraic prefix forms, reordering, -simplification, extracting row degrees and leading terms, dpmat matrix -arithmetic, homogenization and dehomogenization. - -The modules {\em matop} and {\em quot} collect more advanced procedures -for the algebraic management of dpmats. - -\subsection{Extending the REDUCE Matrix Package} - -In v.\ 2.2 minors, Jacobian matrix, and Pfaffians are available for -general REDUCE matrices. They are collected in the \ind{module -calimat} and allow to define procedures in more generality, especially -allowing variable exponents in polynomial expressions. Such a -generalization is especially useful for the investigation of whole -classes of examples that may be obtained from a generic one by -specialization. In the following $m$ is a matrix given in algebraic -prefix form. -\begin{quote} -\verb|matjac(m,l)|\index{matjac} - -\pbx{returns the Jacobian matrix of the ideal $m$ (given as an -algebraic mode list) with respect to the variable list $l$.} - -\verb|minors(m,k)|\index{minors} - -\pbx{returns the matrix of $k$-minors of the matrix $m$.} - -\verb|ideal_of_minors(m,k)|\index{ideal\_of\_minors} - -\pbx{returns the ideal of the $k$-minors of the matrix $m$.} - -\verb|pfaffian m|\index{pfaffian} - -\pbx{returns the pfaffian of a skewsymmetric matrix $m$.} - -\verb|ideal_of_pfaffians(m,k)|\index{ideal\_of\_pfaffians} - -\pbx{returns the ideal of the $2k$-pfaffians of the skewsymmetric -matrix $m$.} - -\verb|random_linear_form(vars,bound)|\index{random\_linear\_form} - -\pbx{returns a random linear form in algebraic prefix form in the -supplied variables $vars$ with integer coefficients bounded by the -supplied $bound$.} - -\verb|singular_locus!*(m,c)|\index{singular\_locus} - -\pbx{returns the singular locus of $m$ (as dpmat). $m$ must be an -ideal of codimension $c$ given as a list of polynomials in prefix -form. {\tt Singular\_locus} computes the ideal generated by the -corresponding Jacobian and $m$ itself.} -\end{quote} - -\section{About the Algorithms Implemented in CALI} - -Below we give a short explanation of the main algorithmic ideas of -CALI and the way they are implemented and may be accessed -(symbolically). - -\subsection{Normal Form Algorithms} - -For v.\ 2.2 we completely revised the implementation of normal form -algorithms due to the insight obtained from our investigations of -normal form procedures for local term orders in \cite{ala} and -\cite{tcah}. It allows a common handling of Noetherian and non -Noetherian term orders already on this level thus making superfluous -the former duplication of reduction procedures in the modules {\em -red} and {\em mora} as in v.\ 2.1. -\medskip - -Normal form algorithms reduce polynomials (or polynomial vectors) -with respect to a given finite set of generators of an ideal or -module. The result is not unique except for a total normal form with -respect to a \gr basis. Furthermore different reduction strategies -may yield significant differences in computing time. - -CALI reduces by first matching, usually keeping base lists sorted -with respect to the sort predicate \ind{red\_better}. In v.\ 2.2 we -sort solely by the dpoly length, since the introduction of -\ind{red\_TopRedBE}, i.e.\ reduction with bounded ecart, guarantees -termination also for non Noetherian term orders. Overload red\_better -for other reduction strategies. -\medskip - -Reduction procedures produce for a given ideal basis $B\subset S$ and -a polynomial $f\in S$ a (pseudo) normal form $h\in S$ such that -$h\equiv u\cdot f\ mod\ B$ where $u\in S$ is a polynomial unit, i.e.\ -a (polynomially represented) non zero domain element in the Noetherian -case (pseudodivision of $f$ by $B$) or a polynomial with a scalar as -leading term in the non Noetherian case. Following up the reduction -steps one can even produce a presentation of $h-u\cdot f$ as a -polynomial combination of the base elements in $B$. - -More general, given for $f_i\in B$ and $f$ representations $f_i = -\sum{r_{ik}e_k} = R_i\cdot E^T$ and $f=R\cdot E^T$ as polynomial -combinations wrt.\ a fixed basis $E$ one can produce such a -presentation also for $h$. For this purpose the dpoly $f$ and its -representation are collected into a base element and reduced -simultaneously by the base list $B$, that collects the base elements -and their representations. -\medskip - -The main procedures of the newly designed reduction package are the -following: -\begin{quote} -\verb|red_TopRedBE(bas,model)|\index{red\_TopRedBE} - -\pbx{Top reduction with bounded ecart of the base element $model$ by -the base list $bas$, i.e.\ only reducing the top term and only with -base elements with ecart bounded by that of $model$.} - -\verb|red_TopRed(bas,model)|\index{red\_TopRed} - -\pbx{Top reduction of $model$, but without restrictions.} - -\verb|red_TailRed(bas,model)|\index{red\_TailRed} - -\pbx{Make tail reduction on $model$, i.e.\ top reduction on the tail -terms. For convergence this uses reduction with bounded ecart for non -Noetherian term orders and full reduction otherwise.} -\medskip - -There is a common \ind{red\_TailRedDriver} that takes a top reduction -function as parameter. It can be used for experiments with other top -reduction procedure combinations. - -\verb|red_TotalRed(bas,model)|\index{red\_TotalRed} - -\pbx{A terminating total reduction, i.e. for Noetherian term orders -the classical one and for local term orders using tail reduction with -bounded ecart.} - -\verb|red_Straight bas|\index{red\_Straight} - -\pbx{Reduce (with {\em red\_TailRed}) the tails of the polynomials in -the base list $bas$.} - -\verb|red_TopInterreduce bas|\index{red\_TopInterreduce} - -\pbx{Reduces the base list $bas$ with $red\_TopRed$ until it -has pairwise incomparable leading terms, computes correct -representation parts, but does no tail reduction.} - -\verb|red_Interreduce bas|\index{red\_Interreduce} - -\pbx{Does top and, if {\tt on red\_total}, also tail interreduction on -the base list $bas$.} -\end{quote} - -Usually, e.g.\ for ideal generation problems, there is no need to care -about the multiplier $u$. If nevertheless one needs its value, the -base element $f$ may be prepared with \ind{red\_prepare} to collect -this information in the 0-slot of its representation part. Extract -this information with \ind{red\_extract}. -\begin{quote} -\verb|red_redpol(bas,model)|\index{red\_redpol} - -\pbx{combines this tool with a total reduction of the base element -$model$ and returns a dotted pair - -\centerline{$( . )$.}} -\end{quote} - -Advanced applications call the interfacing procedures -\begin{quote} -\verb|interreduce!* m|\index{interreduce} - -\pbx{that returns an interreduced basis of the dpmat $m$.} - -\verb|mod!*(f,m)|\index{mod} - -\pbx{that returns the dotted pair $(h.u)$ where $h$ is the pseudo -normal form of the dpoly $f$ modulo the dpmat $m$ and $u$ the -corresponding polynomial unit multiplier.} - -\verb|normalform!*(a,b)|\index{normalform} - -\pbx{that returns $\{a_1,r,z\}$ with $a_1=z*a-r*b$ where the rows of -the dpmat $a_1$ are the normalforms of the rows of the dpmat $a$ with -respect to the dpmat $b$.} -\end{quote} - -For local standard bases the ideal generated by the basic polynomials -may have components not passing through the origin. Although they do -not contribute to the ideal in $Loc(S)=S_{\bf m}$ they usually heavily -increase the necessary computational effort. Hence for local term -orders one should try to remove polynomial units as soon as they -are detected. To remove them from base elements in an early stage of -the computation one can either try the (cheap) test, whether $f\in S$ -is of the form $\langle monomial\rangle *\langle polynomial\ -unit\rangle$ or factor $f$ completely and remove polynomial unit -factors. For base elements this may be done with -\ind{bas\_detectunits} or \ind{bas\_factorunits}. - -Moreover there are two switches \ind{detectunits} and -\ind{factorunits}, both off by default, that force such automatic -simplifications during more advanced computations. - -The procedure \ind{deleteunits!*} tries explicitely to factor the -basis polynomials of a dpmat and to remove polynomial units occuring -as one of the factors. - -\subsection{The \gr and Standard Basis Algorithms} - -There is now a unique \ind{module groeb} that contains the \gr -resp. standard basis algorithms with syzygy computation facility and -related topics. There are common procedures (working for both -Noetherian and non Noetherian term orders) -\begin{quote} -\verb|gbasis!* m|\index{gbasis} - -\pbx{that returns a minimal \gr or standard basis of the dpmat $m$,} - -\verb|syzygies!* m|\index{syzygies} - -\pbx{that returns an interreduced basis of the first syzygy module of -the dpmat $m$ and} - -\verb|syzygies1!* m|\index{syzygies1} - -\pbx{that returns a (not yet interreduced) basis of the syzygy module -of the dpmat $m$.} -\end{quote} - -These procedures start the outer \gr engine (now also common for both -Noetherian and non Noetherian term orders) -\begin{quote} -\verb|groeb_stbasis(m,mgb,ch,syz)|\index{groeb\_stbasis} -\end{quote} -that returns, applied to the dpmat $m$, three dpmats $g,c,s$ with -\begin{quote} -$g$ --- the minimal reduced \gr basis of $m$ if $mgb=t$, - -$c$ --- the transition matrix $g=c\cdot m$ if $ch=t$, and - -$s$ --- the (not yet interreduced) syzygy matrix of $m$ if $syz=t$. -\end{quote} - -The next layer manages the preparation of the representation parts -of the base elements to carry the syzygy information, calls the -{\em general internal driver}, and extracts the relevant information -from the result of that computation. The general internal driver -branches according to different reduction functions into several -versions. Upto now there are three different strategies for the -reduction procedures for the S-polynomial reduction (different -versions may be chosen via \ind{gbtestversion}): -\begin{enumerate} -\item Total reduction with local simplifier lists. For local term -orders this is (almost) Mora's first version for the tangent cone (the -default). - -\item Total reduction with global simplifier list. For local term -orders this is (almost) Mora's SimpStBasis, see \cite{MPT}. - -\item Total reduction with bounded ecart. -\end{enumerate} -The first two versions (almost) coincide for Noetherian term -orders. The third version reduces only with bounded ecart, thus -forcing more pairs to be treated than necessary, but usually less -expensive to be reduced. It is not yet well understood, whether this -idea is of practical importance. - -\ind{groeb\_lazystbasis} calls the lazy standard basis driver instead, -that implements Mora's lazy algorithm, see \cite{MPT}. As -\ind{groeb\_homstbasis}, the computation of \gr and standard bases via -homogenization (Lazard's approach), it is not fully integrated into -the algebraic interface. Use -\begin{quote} -\verb|homstbasis!* m|\index{homstbasis} - -\pbx{for the invocation of the homogenization approach to compute a -standard basis of the dpmat $m$ and} - -\verb|lazystbasis!* m|\index{lazystbasis} - -\pbx{for the lazy algorithm.} -\end{quote} -Experts commonly agree that the classical approach is better for -``computable'' examples, but computations done by the author -on large examples indicate, that both approaches are in fact -independent. -\medskip - -The pair list management uses the sugar strategy, see \cite{GMNRT}, -with respect to the current ecart vector. If the input is homogeneous -and the ecart vector reflects this homogeneity then pairs are sorted -by ascending degree. Hence no superfluous base -elements will be computed in this case. In general the sugar strategy -performs best if the ecart vector is chosen to make the input close -to be homogeneous. - -There is another global variable \ind{cali!=monset} that may contain -a list of variable names (a subset of the variable names of the -current base ring). During the ``pure'' \gr algorithm (without syzygy -and representation computations) common monomial factors containing -only these variables will be canceled out. This shortcut is useful if -some of the variables are known to be non zero divisors as e.g.\ in -most implicitation problems. -\begin{quote} -\verb|setmonset!* vars|\index{setmonset} - -\pbx{initializes {\em cali!=monset} with a given list of variables -$vars$.} -\end{quote} - -The \gr tools as e.g.\ pair criteria, pair list update, pair -management and S-polynomial construction are available. -\begin{quote} -\verb|groeb_mingb m|\index{groeb\_mingb} - -\pbx{extracts a minimal \gr basis from the dpmat $m$, removing base -elements with leading terms, divisible by other leading terms.} - -\verb|groeb_minimize(bas,syz)|\index{groeb\_minimize} - -\pbx{minimizes the dpmat pair $(bas,syz)$ deleting superfluous base -elements from $bas$ using syzygies from $syz$ containing unit -entries.} -\end{quote} - -\subsection{The \gr Factorizer} - -If $\bar{k}$ is the algebraic closure of $k$, -$B:=\{f_1,\ldots,f_m\}\subset S$ a finite system of polynomials, and -$C:=\{g_1,\ldots,g_k\}$ a set of side conditions define the {\em -relative set of zeroes} -\[Z(B,C):=\{a\in \bar{k}^n : \forall\ f\in B\ f(a)=0\mbox{ and } -\forall g\in C\ g(a)\neq 0\}.\] -Its Zariski closure is the zero set of $I(B):<\prod C>$. - -The \gr factorizer solves the following problem: -\begin{quote} -\it Find a collection $(B_\alpha,C_\alpha)$ of \gr bases $B_\alpha$ -and side conditions $C_\alpha$ such that -\[Z(B,C) = \bigcup_\alpha Z(B_\alpha,C_\alpha).\] -\end{quote} -The \ind{module groebf} and the \ind{module triang} contain algorithms -related to that problem, triangular systems, and their generalizations -as described in \cite{fgb} and \cite{efgb}. V. 2.2 thus heavily -extends the algorithmic possibilities that were implemented in former -releases of CALI. - -Note that, different to v.\ 2.1, we work with constraint {\em lists}. -\begin{quote} -\verb|groebfactor!*(bas,con)|\index{groebfactor} - -\pbx{returns for the dpmat ideal $bas$ and the constraint list $con$ -(of dpolys) a minimal list of $(dpmat, constraint\ list)$ pairs with -the desired property.} -\end{quote} -During a preprocessing it splits the submitted basis $bas$ by a -recursive factorization of polynomials and interreduction of bases -into a (reduced) list of smaller subproblems consisting of a partly -computed \gr basis, a constraint list, and a list of pairs not yet -processed. The main procedure forces the next subproblem to be -processed until another factorization is possible. Then the -subproblem splits into subsubproblems, and the subproblem list will -be updated. Subproblems are kept sorted with respect to their -expected dimension \ind{easydim} forcing this way a {\em depth first} -recursion. Returned and not yet interreduced \gr bases are, after -interreduction, subject to another call of the preprocessor since -interreduced polynomials may factor anew. -\begin{quote} -\verb|listgroebfactor!* l|\index{listgroebfactor} - -\pbx{proceeds a whole list of dpmats (without constraints) at once and -strips off constraints at the end.} -\end{quote} -\medskip - -Using the (ordinary) \gr factorizer even components of different -dimension may keep gluing together. The \ind{extended \gr factorizer} -involves a postprocessing, that guarantees a decomposition into -puredimensional components, given by triangular systems instead of \gr -bases. Triangular systems in positive dimension must not be \gr bases -of the underlying ideal. They should be preferred, since they are more -simple but contain all information about the (quasi) prime component -that they represent. The complete \gr basis of the corresponding -component can be obtained by an easy stable quotient computation, see -\cite{efgb}. We refer to the same paper for the definition of -\ind{triangular systems} in positive dimension, that is consistent -with our approach. -\begin{quote} -\verb|extendedgroebfactor!*(bas,c)| and -\verb|extendedgroebfactor1!*(bas,c)| -\index{extendedgroebfactor} \index{extendedgroebfactor1} - -\pbx{return a list of results $\{b_i,c_i,v_i\}$ in algebraic prefix -form such that $b_i$ is a triangular set wrt.\ the variables $v_i$ and -$c_i$ is a list of constraints, such that $b_i:<\prod c_i>$ is the -(puredimensional) recontraction of the zerodimensional ideal -$b_i\bigotimes_k k(v_i)$. For the first version the recontraction is -not computed, hence the output may be not minimal. The second version -computes recontractions to decide superfluous components already -during the algorithm. Note that the stable quotient computation -involved for that purpose may drastically slow down the whole -attempt.} -\end{quote} -The postprocessing involves a change to dimension zero and invokes -(zero dimensional) triangular system computations from the -\ind{module triang}. In a first step \ind{groebf\_zeroprimes1} -incorporates the square free parts of certain univariate polynomials -into these systems and strips off the constraints (since relative sets -of zeroes in dimension zero are Zariski closed), using a splitting -approach analogous to the \gr factorizer. In a second step, according -to the \ind{switch lexefgb}, either \ind{zerosolve!*} or -\ind{zerosolve1!*} converts these intermediate results into lists of -triangular systems in prefix form. If \ind{lexefgb} is {\tt off} (the -default), the zero dimensional term order is degrevlex and -\ind{zerosolve1!*}, the ``slow turn to lex'' is involved, for {\tt on -lexefgb} the pure lexicographic term order and \ind{zerosolve!*}, -M\"ollers original approach, see \cite{Moeller}, are used. Note that -for this term order we need only a single \gr basis computation at -this level. - -A third version, \ind{zerosolve2!*}, mixes the first approach with the -FGLM change of term orders. It is not incorporated into the extended -\gr factorizer. - -\subsection{Basic Operations on Ideals and Modules} - -\gr and local standard bases are the heart of several basic -algorithms in ideal theory, see e.g.\ \cite[6.2.]{BKW}. CALI offers -the following facilities: -\begin{quote} -\verb|submodulep!*(m,n)|\index{submodulep} - -\pbx{tests the dpmat $m$ for being a submodule of the dpmat $n$ -reducing the basis elements of $m$ with respect to $n$. The result -will be correct provided $n$ is a \gr basis.} - -\verb|modequalp!*(m,n)|\index{modequalp} - -\pbx{ = submodulep!*(m,n) and submodulep!*(n,m).} - -\verb|eliminate!*(m,)| \index{eliminate} - -\pbx{computes the elimination ideal/module eliminating the variables -in the given variable list (a subset of the variables of the current -base ring). Changes temporarily the term order to degrevlex.} - -\verb|matintersect!* l|\index{matintersect} -\footnote{This can be done for ideals and -modules in an unique way. Hence {\em idealintersect!*} has been -removed in v.\ 2.1.} - -\pbx{computes the intersection of the dpmats in the dpmat list $l$ -along \cite[6.20]{BKW}.} -\end{quote} - -CALI offers several quotient algorithms. They rest on the computation -of quotients by a single element of the following kind: Assume -$M\subset S^c, v\in S^c, f\in S$. Then there are -\begin{quote} -the \ind{module quotient} $M : (v) = \{g\in S\ |\ gv\in M\}$, - -the \ind{ideal quotient} $M : (f) = \{w\in S^c\ |\ fw\in M\}$, and - -the \ind{stable quotient} $M : (f)^\infty = \{w\in S^c\ |\ \exists\, -n\, :\, f^nw\in M\}$. -\end{quote} -CALI uses the elimination approach \cite[4.4.]{CLO} and -\cite[6.38]{BKW} for their computation: -\begin{quote} -\verb|matquot!*(M,f)|\index{matquot} - -\pbx{returns the module or ideal quotient $M:(f)$ depending on $f$.} - -\verb|matqquot!*(M,f)|\index{matqquot} - -\pbx{returns the stable quotient $M:(f)^\infty$.} -\end{quote} -\ind{matquot!*} calls the pseudo division with remainder -\begin{quote} -\verb|dp_pseudodivmod(g,f)|\index{dp\_pseudodivmod} - -\pbx{that returns a dpoly list $\{q,r,z\}$ such that $z\cdot g = -q\cdot f + r$ with a dpoly unit $z$.\ ($g, f$ and $r$ must belong to -the same free module). This is done uniformly for noetherian and -local term orders with an extended normal form algorithm as described -in \cite{ala}.} -\end{quote} -\medskip - -In the same way one defines the quotient of a module by another -module (both embedded in a common free module $S^c$), the quotient of -a module by an ideal, and the stable quotient of a module by an -ideal. Algorithms for their computation can be obtained from the -corresponding algorithms for a single element as divisor either by -the generic element method \cite{E} or as an intersection -\cite[6.31]{BKW}. CALI offers both approaches (X=1 or 2 below) at -the symbolic level, but for true quotients only the latter one is -integrated into the algebraic mode interface. -\begin{quote} -\verb|idealquotientX!*(M,I)|\index{idealquotient} - -\pbx{returns the ideal quotient $M:I$ of the dpmat $M$ by the dpmat -ideal $I$.} - -\verb|modulequotientX!*(M,N)|\index{modulequotient} - -\pbx{returns the module quotient $M:N$ of the dpmat $M$ by the dpmat -$N$.} - -\verb|annihilatorX!* M|\index{annihilator} - -\pbx{returns the annihilator of $coker\ M$, i.e.\ the module quotient -$S^c:M$, if $M$ is a submodule of $S^c$.} - -\verb|matstabquot!*(M,I)|\index{matstabquot} - -\pbx{returns the stable quotient $M:I^\infty$ (only by the general element -method).} -\end{quote} - - -\subsection{Monomial Ideals} - -Monomial ideals occur as ideals of leading terms of (ideal's) \gr -bases and also as components of leading term modules of submodules of -free modules, see \cite{rois}, and reflect some properties of the -original ideal/module. Several parameters of the original ideal or -module may be read off from it as e.g.\ dimension and Hilbert series. - -The \ind{module moid} contains the corresponding algorithms on -monomial ideals. Monomial ideals are lists of monomials, kept sorted -by descending lexicographic order as proposed in \cite{BS}. - -\begin{quote} -\verb|moid_primes u| \index{moid\_primes} - -\pbx{returns the minimal primes (as a list of lists of variable -names) of the monomial ideal $u$ using an adaption of the algorithm, -proposed in \cite{BS} for the computation of the codimension.} - -\verb|indepvarsets!* m| \index{indepvarsets} - -\pbx{returns (based on {\em moid\_primes}) the list of strongly -independent sets of $m$, see \cite{KW} and \cite{rois} for -definitions.} - -\verb|dim!* m| \index{dim} - -\pbx{returns the dimension of $coker\ m$ as the size of the largest -independent set.} - -\verb|codim!* m| \index{codim} - -\pbx{returns the codimension of $coker\ m$.} - -\verb|easyindepset!* m| \index{easyindepset} - -\pbx{returns a maximal with respect to inclusion independent set of -$m$.} - -\verb|easydim!* m| \index{easydim} - -\pbx{is a fast dimension algorithm (based on {\em easyindepset}), that -will be correct if $m$ is (radically) unmixed. Since it is -significantly faster than the general dimension -algorithm\footnotemark, it should -be used, if all maximal independent sets are known to be of equal -cardinality (as e.g.\ for prime or unmixed ideals, see \cite{rois}).} -\footnotetext{This algorithm is of linear time as opposed to the -problem to determine the dimension of an arbitrary monomial ideal, -that is known to be NP-hard in the number of variables, see -\cite{BS}.} -\end{quote} - -\subsection{Hilbert Series} - -CALI v. 2.2 now offers also \ind{weighted Hilbert series}, i.e.\ -series that may reflect multihomogeneity of ideals and modules. For -this purpose -a weighted Hilbert series has a list of (integer) degree vectors -as second parameter, and the ideal(s) of leading terms are evaluated -wrt.\ these weights. For the output and polynomial arithmetic, -involved during the computation of the Hilbert series numerator, the -different weight levels are mapped onto the first variables of the -current ring. If $w$ is such a weight vector list and $I$ is a -monomial ideal in the polynomial ring $S=k[x_v\,:\,v\in V]$ we get -(using multi exponent notation) -\[H(S/I,t) := \sum_{\alpha}{|\{x^a\not\in I\,:\,w(a)=\alpha\}|\cdot -t^\alpha} = \frac{Q(t)}{\prod_{v\in V}{\left(1-t^{w(x_v)}\right)} }\] -for a certain polynomial Hilbert series numerator $Q(t)$. $H(R/I,t)$ -is known to be a rational function with pole order at $t=1$ equal to -$dim\ R/I$. Note that \ind{WeightedHilbertSeries} returns a {\em -reduced} rational function where the gcd of numerator and denominator -is canceled out. - -(Non weighted) Hilbert series call the weighted Hilbert series -procedure with a single weight vector, the ecart vector of the current -ring. - -The Hilbert series numerator $Q(t)$ is computed using (the obvious -generalizations to the weighted case of) the algorithms in \cite{BS} -and \cite{BCRT}. Experiments suggest that the former is better for few -generators of high degree whereas the latter has to be preferred for -many generators of low degree. Choose the version with -\ind{hftestversion} $n$, $n=1,\,2$. Bayer/Stillman's approach ($n=1$) -is the default. In the following $m$ is a dpmat and \gr basis. - -\begin{quote} -\verb|hf_whilb(m,w)| \index{hf\_whilb} - -\pbx{returns the weighted Hilbert series numerator $Q(t)$ of $m$ -according to the version chosen with \ind{hftestversion}.} - -\verb|WeightedHilbertSeries!*(m,w)| \index{WeightedHilbertSeries} - -\pbx{returns the weighted Hilbert series reduced rational function of -$m$ as s.q.} - -\verb|HilbertSeries!*(m,w)| \index{HilbertSeries} - -\pbx{returns the Hilbert series reduced rational function of $m$ wrt.\ -the ecart vector of the current ring as s.q.} - -\verb|hf_whilb3(u,w)| and \verb|hf_whs_from_resolution(u,w)| -\index{hf\_whilb3} -\index{hf\_whs\_from\_resolution} - -\pbx{compute the weighted Hilbert series numerator and the -corresponding reduced rational function from (the column degrees of) a -given resolution $u$.} - -\verb|degree!* m| \index{degree} - -\pbx{returns the value of the numerator of the reduced Hilbert series -of $m$ at $t=1$. i.e.\ the sum of its coefficients. For the standard -ecart this is the degree of $coker\ m$.} -\end{quote} - -\subsection{Resolutions} - -Resolutions of ideals and modules, represented as lists of dpmats, are -computed via repeated syzygy computation with minimization steps -between them to get minimal bases and generators of syzygy -modules. Note that the algorithms apply simultaneously to both -Noetherian and non Noetherian term orders. For compatibility reasons -with further releases v. 2.2 introduces a second parameter to -bound the number of syzygy modules to be computed, since Hilbert's -syzygy theorem applies only to regular rings. -\begin{quote} -\verb|Resolve!*(m,d)| \index{Resolve} - -\pbx{computes a minimal resolution of the dpmat $m$, i.e. a list of -dpmats $\{s_0, s_1, s_2,\ldots\}$, where $s_k$ is the $k$-th syzygy -module of $m$, upto part $s_d$.} - -\verb|BettiNumbers!* c| and \verb|GradedBettiNumbers!* c| -\index{BettiNumbers} -\index{GradedBettiNumbers} - -\pbx{returns the Betti numbers resp.\ the graded Betti numbers of the -resolution $c$, i.e.\ the list of the lengths resp.\ the degree lists -(according to the ecart) themselves of the dpmats in $c$.} -\end{quote} - -\subsection{Zero Dimensional Ideals and Modules} - -There are several algorithms that either force the reduction of a -given problem to dimension zero or work only for zero dimensional -ideals or modules. The \ind{module odim} offers such -algorithms. It contains, e.g.\ -\begin{quote} -\verb|dimzerop!* m| \index{dimzerop} - -\pbx{that tests a dpmat $m$ for being zero dimensional.} - -\verb|getkbase!* m| \index{getkbase} - -\pbx{that returns a (monomial) k-vector space basis of $Coker\ m$ -provided $m$ is a \gr basis.} - -\verb|odim_borderbasis m| \index{odim\_borderbasis} - -\pbx{that returns a border basis, see \cite{MMM}, of the -zero dimensional dpmat $m$ as a list of base elements.} - -\verb|odim_parameter m| \index{odim\_parameter} - -\pbx{that returns a parameter of the dpmat $m$, i.e.\ a variable $x -\in vars$ such that $k[x]\bigcap Ann\ S^c/m=(0)$, or {\em nil} if $m$ -is zero dimensional.} - -\verb|odim_up(a,m)| \index{odim\_up} - -\pbx{that returns an univariate polynomial (of smallest possible -degree if $m$ is a gbasis) in the variable $a$, that belongs to the -zero dimensional dpmat ideal $m$, using Buchberger's approach -\cite{B1}.} -\end{quote} - -\subsection{Primary Decomposition and Related Algorithms} - -The algorithms of the \ind{module prime} implement the ideas of -\cite{GTZ} with modifications along \cite{Kr} and their natural -generalizations to modules as e.g.\ explained in \cite{Ru}. Version -2.2.1 fixes a serious bug detecting superfluous embedded primary -components, see section \ref{221}, and contains now a second primary -decomposition algorithm, based on ideal separation, as standard. For a -discussion about embedded primes and the ideal separation approach, -see \cite{primary}. - - -CALI contains also algorithms for the computation of the unmixed part -of a given module and the unmixed radical of a given ideal (along the -same lines). We followed the stepwise recursion decreasing dimension -in each step by 1 as proposed in (the final version of) \cite{GTZ} -rather than the ``one step'' method described in \cite{BKW} since -handling leading coefficients, i.e.\ standard forms, depending on -several variables is a quite hard job for -REDUCE\footnote{\ind{prime!=decompose2} implements this strategy in -the symbolic mode layer.}. - -In the following procedures $m$ must be a \gr basis. -\begin{quote} -\verb|zeroradical!* m| \index{zeroradical} - -\pbx{returns the radical of the zero dimensional ideal $m$, using -squarefree decomposition of univariate polynomials.} - -\verb|zeroprimes!* m| \index{zeroprimes} - -\pbx{computes as in \cite{GTZ} the list of prime ideals of $Ann\ F/M$ -if $m$ is zero dimensional, using the (sparse) general position -argument from \cite{KW}.} - -\verb|zeroprimarydecomposition!* m| \index{zeroprimarydecomposition} - -\pbx{computes the primary components of the zero dimensional dpmat $m$ -using prime splitting with the prime ideals of $Ann\ F/M$. It returns -a list of pairs with first entry the primary component -and second entry the corresponding associated prime ideal.} - -\verb|isprime!* m| \index{isprime} - -\pbx{a (one step) primality test for ideals, extracted from -\cite{GTZ}.} - -\verb|isolatedprimes!* m| \index{isolatedprimes} - -\pbx{computes (only) the isolated prime ideals of $Ann\ F/M$.} - -\verb|radical!* m| \index{radical} - -\pbx{computes the radical of the dpmat ideal $m$, reducing as in -\cite{GTZ} to the zero dimensional case.} - -\verb|easyprimarydecomposition!* m| \index{easyprimarydecomposition} - -\pbx{computes the primary components of the dpmat $m$, if it has no -embedded components. The algorithm uses prime splitting with the -isolated prime ideals of $Ann\ F/M$. It returns a list of pairs as in -{\em zeroprimarydecomposition!*}.} - -\verb|primarydecomposition!* m| \index{primarydecomposition} - -\pbx{computes the primary components of the dpmat $m$ along the lines -of \cite{GTZ}. It returns a list of two-element lists as in {\em -zeroprimarydecomposition!*}.} - -\verb|unmixedradical!* m| \index{unmixedradical} - -\pbx{returns the unmixed radical, i.e.\ the intersection of the -isolated primes of top dimension, associated to the dpmat ideal $m$.} - -\verb|eqhull!* m| \index{eqhull} - -\pbx{returns the equidimensional hull, i.e.\ the intersection of the - top dimensional primary components of the dpmat $m$.} -\end{quote} - -\subsection{Advanced Algorithms} - -The \ind{module scripts} just under further development offers some -advanced topics of the \gr bases theory. It introduces the new data -structure of a \ind{map} between base rings: -\medskip - -A ring map -\[ \phi\ :\ R\longrightarrow S\] -for $R=k[r_i], S=k[s_j]$ is represented in symbolic mode as a list -\[ \{preimage\_ring\ R,\ image\_ring\ S, subst\_list\},\] -where {\tt subst\_list} is a substitution list $\{r_1=\phi_1(s), -r_2=\phi_2(s),\ldots \}$ in algebraic prefix form, i.e.\ looks like -{\tt (list (equal var image) \ldots )}. - -The central tool for several applications is the computation of the -preimage $\phi^{-1}(I)\subset R$ of an ideal $I\subset S$ either -under a polynomial map $\phi$ or its closure in $R$ under a rational -map $\phi$, see \cite[7.69 and 7.71]{BKW}. -\begin{quote} -\verb|preimage!*(m,map)| \index{preimage} - -\pbx{computes the preimage of the ideal $m$ in algebraic prefix form -under the given polynomial map and sets the current base ring to the -preimage ring. Returns the result also in algebraic prefix form.} - -\verb|ratpreimage!*(m,map)| \index{ratpreimage} - -\pbx{computes the closure of the preimage of the ideal $m$ in -algebraic prefix form under the given rational map and sets the -current base ring to the preimage ring. Returns the result also in -algebraic prefix form.} - -\end{quote} - -Derived applications are -\begin{quote} -\verb|affine_monomial_curve!*(l,vars)|\index{affine\_monomial\_curve} - -\pbx{$l$ is a list of integers, $vars$ a list of variable names of the -same length as $l$. The procedure sets the current base ring and -returns the defining ideal of the affine monomial curve with generic -point $(t^i\ :\ i\in l)$ computing the corresponding preimage.} - -\verb|analytic_spread!* M|\index{analytic\_spread} - -\pbx{Computes the analytic spread of $M$, i.e.\ the dimension of the -exceptional fiber ${\cal R}(M)/m{\cal R}(M)$ of the blowup along $M$ -over the irrelevant ideal $m$ of the current base ring.} - -\verb|assgrad!*(M,N,vars)|\index{assgrad} - -\pbx{Computes the associated graded ring \[gr_R(N):= -(R/N\oplus N/N^2\oplus\ldots)={\cal R}(N)/N{\cal R}(N)\] over the ring -$R=S/M$, where $M$ and -$N$ are dpmat ideals defined over the current base ring $S$. {\tt -vars} is a list of new variable names one for each generator of $N$. -They are used to create a second ring $T$ with degree order -corresponding to the ecart of the row degrees of $N$ and a ring map -\[\phi : S\oplus T\longrightarrow S.\] -It returns a dpmat ideal $J$ such that $(S\oplus T)/J$ is a -presentation of the -desired associated graded ring over the new current base ring -$S\oplus T$.} - -\verb|blowup!*(M,N,vars)|\index{blowup} - -\pbx{Computes the blow up ${\cal R}(N):=R[N\cdot t]$ of $N$ over -the ring $R=S/M$, where $M$ and $N$ are dpmat ideals defined over the -current base ring $S$. {\tt vars} is a list of new variable names one -for each generator of $N$. They are used to create a second ring $T$ -with degree order corresponding to the ecart of the row degrees of -$N$ and a ring map -\[\phi : S\oplus T\longrightarrow S.\] -It returns a dpmat ideal $J$ such that $(S\oplus T)/J$ is -a presentation of the -desired blowup ring over the new current base ring $S\oplus T$.} - -\verb|proj_monomial_curve!*(l,vars)|\index{proj\_monomial\_curve} - -\pbx{$l$ is a list of integers, $vars$ a list of variable names of the -same length as $l$. The procedure set the current base ring and -returns the defining ideal of the projective monomial curve with -generic point \mbox{$(s^{d-i}\cdot t^i\ :\ i\in l)$} in $R$, where -\mbox{$d=max\{ x\, :\, x\in l\}$}, computing the corresponding preimage.} - -\verb|sym!*(M,vars)|\index{sym} - -\pbx{Computes the symmetric algebra $Sym(M)$ where $M$ is a dpmat ideal -defined over the current base ring $S$. {\tt vars} is a list of new -variable names one for each generator of $M$. They are used to create -a second ring $R$ with degree order corresponding to the ecart of the -row degrees of $N$ and a ring map -\[\phi : S\oplus R\longrightarrow S.\] -It returns a dpmat ideal $J$ such that $(S\oplus R)/J$ is the -desired symmetric algebra over the new current base ring $S\oplus R$.} - -\end{quote} - - -There are several other applications: -\begin{quote} -\verb|minimal_generators!* m| \index{minimal\_generators} - -\pbx{returns a set of minimal generators of the dpmat $m$ inspecting -the first syzygy module.} - -\verb|nzdp!*(f,m)| \index{nzdp} - -\pbx{tests whether the dpoly $f$ is a non zero divisor on $coker\ -m$. $m$ must be a \gr basis.} - -\verb|symbolic_power!*(m,d)| \index{symbolic\_power} - -\pbx{returns the $d$\/th symbolic power of the prime dpmat ideal $m$ as -the equidimensional hull of the $d$\/th true power. (Hence applies also -to unmixed ideals.)} - -\verb|varopt!* m| \index{varopt} - -\pbx{finds a heuristically optimal variable order by the approach in -\cite{BGK} and returns the corresponding list of variables.} -\end{quote} - - -\subsection{Dual Bases} - - -For the general ideas underlying the dual bases approach see e.g.\ -\cite{MMM}. This paper explains, that constructive problems from very -different areas of commutative algebra can be formulated in a unified -way as the computation of a basis for the intersection of the kernels -of a finite number of linear functionals generating a dual -$S$-module. Our implementation honours -this point of view, presenting two general drivers \ind{dualbases} and -\ind{dualhbases} for the computation of such bases (even as submodules -of a free module $M=S^m$) with affine resp.\ projective dimension zero. - -Such a collection of $N$ linear functionals -\[L\,:\, M=S^m \longrightarrow k^N\] -should be given through values $\{[e_i,L(e_i)], i=1,\ldots,m\}$ on the -generators $e_i$ of $M$ and an evaluation function {\tt -evlf([p,L(p)],x)}, that evaluates $L(p\cdot x)$ from $L(p)$ for $p\in -M$ and the variable $x\in S$. - -\ind{dualbases} starts with a list of such generator/value constructs -generating $M$ and performs Gaussian reduction on expressions $[p\cdot -x,L(p\cdot x)]$, where $p$ was already processed, $L(p)\neq 0$, and -$x\in S$ is a variable. These elements are processed in ascending order -wrt.\ the term order on $M$. This guarantees both termination and that -the resulting basis of $ker\ L$ is a \gr basis. The $N$ values of $L$ -are attached to $N$ variables, that are ordered linearly. Gaussian -elimination is executed wrt.\ this variable order. - -To initialize the dual bases driver one has to supply the basic -generator/value list (through the parameter list; for ideals just the -one element list containing the generator $[1\in S,L(1)]$), the -evaluation function, and the linear algebra variable order. The latter -are supplied via the property list of {\tt cali} as properties {\tt -evlf} and {\tt varlessp}. Different applications need more entries -on the property list of {\tt cali} to manage the communication between -the driver and the calling routine. - -\ind{dualhbases} realizes the same idea for (homogeneous) ideals and -modules of (projective) dimension zero. It produces zerodimensional -``slices'' with ascending degree until it reaches a supremum supplied -by the user, see \cite{MMM} for details. -\medskip - -Applications concern affine and projective defining ideals of a finite -number of points\footnote{This substitutes the ``brute force'' method -computing the corresponding intersections directly as it was -implemented in v. 2.1. The new approach is significantly faster. The -old stuff is available as \ind{affine\_points1!*} and -\ind{proj\_points1!*}.} and two versions (with and without precomputed -border basis) of term order -changes for zerodimensional ideals and modules as first described in -\cite{FGLM}. -\begin{quote} -\verb|affine_points!* m| \index{affine\_points} - -\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) -with as many columns as the current base ring has ring variables. This -procedure returns the defining ideal of the collection of points in -affine space with coordinates given by the rows of $m$. Note that $m$ -may contain parameters. In this case $k$ is treated as rational -function field.} - -\verb|change_termorder!*(m,r)| and \verb|change_termorder1!*(m,r)| -\index{change\_termorder} -\index{change\_termorder1} - -\pbx{$m$ is a \gr basis of a zero dimensional ideal wrt.\ the current -base ring. These procedures change the current ring to $r$ and compute -the \gr basis of $m$ wrt.\ the new ring $r$. The former uses a -precomputed border basis.} - -\verb|proj_points!* m| \index{proj\_points} - -\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) -with as many columns as the current base ring has ring variables. This -procedure returns the defining ideal of the collection of points in -projective space with homogeneous coordinates given by the rows of -$m$. Note that $m$ may as for {\tt affine\_points} contain -parameters.} -\end{quote} - -\pagebreak - -\appendix -\section{A Short Description of Procedures Available in Algebraic -Mode} - -Here we give a short description, ordered alphabetically, of {\bf -algebraic} procedures offered by CALI in the algebraic mode -interface\footnote{It does {\bf not} contain switches, get\ldots\ -procedures, setting trace level and related stuff.}. - -If not stated explicitely procedures take (algebraic mode) polynomial -matrices ($c>0$) or polynomial lists ($c=0$) $m,m1,m2,\ldots\ $ as -input and return results of the same type. $gb$ stands for a bounded -identifier\footnote{Different to v. 2.1 a \gr basis will be computed -automatically, if necessary.}, $gbr$ for one with precomputed -resolution. For the mechanism of \ind{bounded identifier} see the -section ``Algebraic Mode Interface''. - -\begin{quote} -\verb|affine_monomial_curve(l,vars)|\index{affine\_monomial\_curve} - -\pbx{$l$ is a list of integers, $vars$ a list of variable names of the -same length as $l$. The procedure sets the current base ring and -returns the defining ideal of the affine monomial curve with generic -point $(t^i\ :\ i\in l)$.} - -\verb|affine_points m| \index{affine\_points} - -\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) -with as many columns as the current base ring has ring variables. This -procedure returns the defining ideal of the collection of points in -affine space with coordinates given by the rows of $m$. Note that $m$ -may contain parameters. In this case $k$ is treated as rational -function field.} - -\verb|analytic_spread m|\index{analytic\_spread} - -\pbx{Computes the analytic spread of $m$.} - -\verb|annihilator m| \index{annihilator} - -\pbx{returns the annihilator of the dpmat $m\subseteq S^c$, i.e.\ -$Ann\ S^c/M$.} - -\verb|assgrad(M,N,vars)|\index{assgrad} - -\pbx{Computes the associated graded ring $gr_R(N)$ over $R=S/M$, where -$S$ is the current -base ring. {\tt vars} is a list of new variable names, one for -each generator of $N$. They are used to create a second ring $T$ -to return an ideal $J$ such that $(S\oplus T)/J$ is the desired -associated graded ring over the new current base ring $S\oplus T$.} - -\verb|bettiNumbers gbr| \index{bettiNumbers} - -\pbx{extracts the list of Betti numbers from the resolution of $gbr$.} - -\verb|blowup(M,N,vars)|\index{blowup} - -\pbx{Computes the blow up ${\cal R}(N)$ of $N$ over the ring $R=S/M$, -where $S$ is the current base ring. {\tt vars} is a list of new -variable names, one for each generator of $N$. They are used to create -a second ring $T$ to return an ideal $J$ such that $(S\oplus T)/J$ is -the desired blowup ring over the new current base ring $S\oplus T$.} - -\verb|change_termorder(m,r)| and \verb|change_termorder1(m,r)| -\index{change\_termorder} -\index{change\_termorder1} - -\pbx{Change the current ring to $r$ and compute the \gr basis of $m$ -wrt.\ the new ring $r$ by the FGLM approach. The former uses -internally a precomputed border basis.} - -\verb|codim gb| \index{codim} - -\pbx{returns the codimension of $S^c/gb$.} - -\verb|degree gb| \index{degree} - -\pbx{returns the multiplicity of $gb$ as the sum of the coefficients -of the (classical) Hilbert series numerator.} - -\verb|degsfromresolution gbr| \index{degsfromresolution} - -\pbx{returns the list of column degrees from the minimal resolution -of $gbr$.} - -\verb|deleteunits m| \index{deleteunits} - -\pbx{factors each basis element of the dpmat ideal $m$ and removes -factors that are polynomial units. Applies only to non Noetherian -term orders.} - -\verb|dim gb| \index{dim} - -\pbx{returns the dimension of $S^c/gb$.} - -\verb|dimzerop gb| \index{dimzerop} - -\pbx{tests whether $S^c/gb$ is zerodimensional.} - -\verb|directsum(m1,m2,...)| \index{directsum} - -\pbx{returns the direct sum of the modules $m1,m2,\ldots$, embedded -into the direct sum of the corresponding free modules.} - -\verb|dpgcd(f,g)| \index{dpgcd} - -\pbx{returns the gcd of two polynomials $f$ and $g$, computed by the -syzygy method.} - -\verb|easydim m| and \verb|easyindepset m| -\index{easydim}\index{easyindepset} - -\pbx{ If the given ideal or module is unmixed (e.g.\ prime) then all -maximal strongly independent sets are of equal size and one can look -for a maximal with respect to inclusion rather than size strongly -independent set. These procedures don't test the input for being a -\gr basis or unmixed, but construct a maximal with respect to -inclusion independent set of the basic leading terms resp.\ detect -from this (an approximation for) the dimension.} - -\verb|easyprimarydecomposition m| \index{easyprimarydecomposition} - -\pbx{a short primary decomposition using ideal separation of isolated -primes of $m$, that yields true results only for modules without -embedded components. Returns a list of $\{component, associated\ -prime\}$ pairs.} - -\verb|eliminate(m,)| \index{eliminate} - -\pbx{computes the elimination ideal/module eliminating the variables -in the given variable list (a subset of the variables of the current -base ring). Changes temporarily the term order to degrevlex.} - -\verb|eqhull m| \index{eqhull} - -\pbx{returns the equidimensional hull of the dpmat $m$.} - -\verb|extendedgroebfactor(m,c)| and \verb|extendedgroebfactor1(m,c)| -\index{extendedgroebfactor} \index{extendedgroebfactor1} - -\pbx{return for a polynomial ideal $m$ and a list of (polynomial) -constraints $c$ a list of results $\{b_i,c_i,v_i\}$, where $b_i$ is a -triangular set wrt.\ the variables $v_i$ and $c_i$ is a list of -constraints, such that -$Z(m,c) = \bigcup Z(b_i,c_i)$. For the first version the output may be -not minimal. The second version decides superfluous components already -during the algorithm.} - -\verb|gbasis gb| \index{gbasis} - -\pbx{returns the \gr resp. local standard basis of $gb$.} - -\verb|getkbase gb| \index{getkbase} - -\pbx{returns a k-vector space basis of $S^c/gb$, consisting of module -terms, provided $gb$ is zerodimensional.} - -\verb|getleadterms gb| \index{getleadterms} - -\pbx{returns the dpmat of leading terms of a \gr resp. local standard -basis of $gb$.} - -\verb|GradedBettinumbers gbr| \index{GradedBettinumbers} - -\pbx{extracts the list of degree lists of the free summands in a -minimal resolution of $gbr$.} - -\verb|groebfactor(m[,c])|\index{groebfactor} - -\pbx{returns for the dpmat ideal $m$ and an optional constraint list -$c$ a (reduced) list of dpmats such that the union of their zeroes is -exactly $Z(m,c)$. Factors all polynomials involved in the \gr -algorithms of the partial results.} - -\verb|HilbertSeries gb| \index{HilbertSeries} - -\pbx{returns the Hilbert series of $gb$ with respect to the current -ecart vector.} - -\verb|homstbasis m| \index{homstbasis} - -\pbx{computes the standard basis of $m$ by Lazard's homogenization -approach.} - -\verb|ideal2mat m| \index{ideal2mat} - -\pbx{converts the ideal (=list of polynomials) $m$ into a column -vector.} - -\verb|ideal_of_minors(mat,k)| \index{ideal\_of\_minors} - -\pbx{computes the generators for the ideal of $k$-minors of the matrix -$mat$.} - -\verb|ideal_of_pfaffians(mat,k)| \index{ideal\_of\_pfaffians} - -\pbx{computes the generators for the ideal of the $2k$-pfaffians of -the skewsymmetric matrix $mat$.} - -\verb|idealpower(m,n)| \index{idealpower} - -\pbx{returns the interreduced basis of the ideal power $m^n$ with -respect to the integer $n\geq 0$.} - -\verb|idealprod(m1,m2,...)| \index{idealprod} - -\pbx{returns the interreduced basis of the ideal product -\mbox{$m1\cdot m2\cdot \ldots$} of the ideals $m1,m2,\ldots$.} - -\verb|idealquotient(m1,m2)| \index{idealquotient} - -\pbx{returns the ideal quotient $m1:m2$ of the module $m1\subseteq -S^c$ by the ideal $m2$.} - -\verb|idealsum(m1,m2,...)| \index{idealsum} - -\pbx{returns the interreduced basis of the ideal sum $m1+m2+\ldots$.} - -\verb|indepvarsets gb| \index{indepvarsets} - -\pbx{returns the list of strongly independent sets of $gb$ with -respect to the current term order, see \cite{KW} for a definition in -the case of ideals and \cite{rois} for submodules of free modules.} - -\verb|initmat(m,| \index{initmat} - -\pbx{initializes the dpmat $m$ together with its base ring, term order -and column degrees from a file.} - -\verb|interreduce m| \index{interreduce} - -\pbx{returns the interreduced module basis given by the rows of $m$, -i.e.\ a basis with pairwise indivisible leading terms.} - -\verb|isolatedprimes m| \index{isolatedprimes} - -\pbx{returns the list of isolated primes of the dpmat $m$, i.e.\ the -isolated primes of $Ann\ S^c/M$.} - -\verb|isprime gb| \index{isprime} - -\pbx{tests the ideal $gb$ to be prime.} - -\verb|iszeroradical gb| \index{iszeroradical} - -\pbx{tests the zerodimensional ideal $gb$ to be radical.} - -\verb|lazystbasis m| \index{lazystbasis} - -\pbx{computes the standard basis of $m$ by the lazy algorithm, see -e.g.\ \cite{MPT}.} - -\verb|listgroebfactor in| \index{listgroebfactor} - -\pbx{computes for the list $in$ of ideal bases a list $out$ of \gr -bases by the \gr factorization method, such that -$\bigcup_{m\in in}Z(m) = \bigcup_{m\in out}Z(m)$.} - -\verb|mat2list m| \index{mat2list} - -\pbx{converts the matrix $m$ into a list of its entries.} - -\verb|matappend(m1,m2,...)| \index{matappend} - -\pbx{collects the rows of the dpmats $m1,m2,\ldots $ to a common -matrix. $m1,m2,\ldots$ must be submodules of the same free module, -i.e.\ have equal column degrees (and size).} - -\verb|mathomogenize(m,var)| \index{mathomogenize} -\footnote{Dehomogenize with {\tt sub(z=1,m)} if $z$ is the -homogenizing variable.} - -\pbx{returns the result obtained by homogenization of the rows of m -with respect to the variable {\tt var} and the current \ind{ecart -vector}.} - -\verb|matintersect(m1,m2,...)| \index{matintersect} - -\pbx{returns the interreduced basis of the intersection $m1\bigcap -m2\bigcap \ldots$.} - -\verb|matjac(m,)| \index{matjac} - -\pbx{returns the Jacobian matrix of the ideal m with respect to the -supplied variable list} - -\verb|matqquot(m,f)| \index{matqquot} - -\pbx{returns the stable quotient $m:(f)^\infty$ of the dpmat $m$ by -the polynomial $f\in S$.} - -\verb|matquot(m,f)| \index{matquot} - -\pbx{returns the quotient $m:(f)$ of the dpmat $m$ by the polynomial -$f\in S$.} - -\verb|matstabquot(m1,id)| \index{matstabquot} - -\pbx{returns the stable quotient $m1:id^\infty$ of the dpmat $m1$ by -the ideal $id$.} - -\verb|matsum(m1,m2,...)| \index{matsum} - -\pbx{returns the interreduced basis of the module sum $m1+m2+\ldots$ -in a common free module.} - -\verb|minimal_generators m| \index{minimal\_generators} - -\pbx{returns a set of minimal generators of the dpmat $m$.} - -\verb|minors(m,b)| \index{minors} - -\pbx{returns the matrix of minors of size $b\times b$ of the matrix -$m$.} - -\verb|a mod m| \index{mod} - -\pbx{computes the (true) normal form(s), i.e.\ a standard quotient -representation, of $a$ modulo the dpmat $m$. $a$ may be either a -polynomial or a polynomial list ($c=0$) or a matrix ($c>0$) of the -correct number of columns.} - -\verb|modequalp(gb1,gb2)| \index{modequalp} - -\pbx{tests, whether $gb1$ and $gb2$ are equal (returns YES or NO).} - -\verb|modulequotient(m1,m2)| \index{modulequotient} - -\pbx{returns the module quotient $m1:m2$ of two dpmats $m1,m2$ in a -common free module.} - -\verb|normalform(m1,m2)| \index{normalform} - -\pbx{returns a list of three dpmats $\{m3,r,z\}$, where $m3$ is the -normalform of $m1$ modulo $m2$, $z$ a scalar matrix of polynomial -units (i.e.\ polynomials of degree 0 in the noetherian case and -polynomials with leading term of degree 0 in the tangent cone case), -and $r$ the relation matrix, such that \[m3=z*m1+r*m2.\]} - -\verb|nzdp(f,m)| \index{nzdp} - -\pbx{tests whether the dpoly $f$ is a non zero divisor on $coker\ -m$.} - -\verb|pfaffian mat| \index{pfaffian} - -\pbx{returns the pfaffian of a skewsymmetric matrix $mat$.} - -\verb|preimage(m,map)| \index{preimage} - -\pbx{computes the preimage of the ideal $m$ under the given -polynomial map and sets the current base ring to the preimage ring.} - -\verb|primarydecomposition m| -\index{primarydecomposition} - -\pbx{returns the primary decomposition of the dpmat $m$ as a list of -$\{component, associated\ prime\}$ pairs.} - -\verb|proj_monomial_curve(l,vars)|\index{proj\_monomial\_curve} - -\pbx{$l$ is a list of integers, $vars$ a list of variable names of the -same length as $l$. The procedure sets the current base ring and -returns the defining ideal of the projective monomial curve with -generic point \mbox{$(s^{d-i}\cdot t^i\ :\ i\in l)$} in $R$ where $d=max\{ -x\, :\, x\in l\}$.} - -\verb|proj_points m| \index{proj\_points} - -\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) -with as many columns as the current base ring has ring variables. This -procedure returns the defining ideal of the collection of points in -projective space with homogeneous coordinates given by the rows of -$m$. Note that $m$ may as for {\tt affine\_points} contain -parameters.} - -\verb|radical m| \index{radical} - -\pbx{returns the radical of the dpmat ideal $m$.} - -\verb|random_linear_form(vars,bound)| \index{random\_linear\_form} - -\pbx{returns a random linear form in the variables {\tt vars} with integer -coefficients less than the supplied {\tt bound}.} - -\verb|ratpreimage(m,map)| \index{ratpreimage} - -\pbx{computes the closure of the preimage of the ideal $m$ under the -given rational map and sets the current base ring to the preimage -ring.} - -\verb|resolve(m[,d])| \index{resolve} - -\pbx{returns the first $d$ members of the minimal resolution of the -bounded identifier $m$ as a list of matrices. If the resolution has -less than $d$ non zero members, only those are collected. (Default: -$d=100$)} - -\verb|savemat(m,)| \index{savemat} - -\pbx{save the dpmat $m$ together with the settings of it base ring, -term order and column degrees to a file.} - -\verb|setgbasis m| \index{setgbasis} - -\pbx{declares the rows of the bounded identifier $m$ to be already a -\gr resp. local standard basis thus avoiding a possibly time -consuming \gr or standard basis computation.} - -\verb|sieve(m,)| \index{sieve} - -\pbx{sieves out all base elements with leading terms having a factor -contained in the specified variable list (a subset of the variables -of the current base ring). Useful for elimination problems solved -``by hand''.} - -\verb|singular_locus(M,c)| \index{singular\_locus} - -\pbx{returns the defining ideal of the singular locus of $Spec\ S/M$ -where $M$ is an ideal of codimension $c$, adding to $M$ the generators -of the ideal of the $c$-minors of the Jacobian of $M$.} - -\verb|submodulep(m,gb)| \index{submodulep} - -\pbx{tests, whether $m$ is a submodule of $gb$ (returns YES or NO).} - -\verb|sym(M,vars)|\index{sym} - -\pbx{Computes the symmetric algebra $Sym(M)$ where $M$ is an ideal -defined over the current base ring $S$. {\tt vars} is a list of new -variable names, one for each generator of $M$. They are used to create -a second ring $R$ to return an ideal $J$ such that $(S\oplus R)/J$ is -the desired symmetric algebra over the new current base ring $S\oplus -R$.} - -\verb|symbolic_power(m,d)| \index{symbolic\_power} - -\pbx{returns the $d$th symbolic power of the prime dpmat ideal $m$.} - -\verb|syzygies m| \index{syzygies} - -\pbx{returns the first syzygy module of the bounded identifier $m$.} - -\verb|tangentcone gb| \index{tangentcone} - -\pbx{returns the tangent cone part, i.e.\ the homogeneous part of -highest degree with respect to the first degree vector of the term -order from the \gr basis elements of the dpmat $gb$. The term order -must be a degree order.} - -\verb|unmixedradical m| \index{unmixedradical} - -\pbx{returns the unmixed radical of the dpmat ideal $m$.} - -\verb|varopt m| \index{varopt} - -\pbx{finds a heuristically optimal variable order, see \cite{BGK}. -\[\tt vars:=varopt\ m;\ setring(vars,\{\},lex);\ setideal(m,m);\] -changes to the lexicographic term order with heuristically best -performance for a lexicographic \gr basis computation.} - -\verb|WeightedHilbertSeries(m,w)| \index{WeightedHilbertSeries} - -\pbx{returns the weighted Hilbert series of the dpmat $m$. Note that -$m$ is not a bounded identifier and hence not checked to be a \gr -basis. $w$ is a list of integer weight vectors.} - -\verb|zeroprimarydecomposition m| \index{zeroprimarydecomposition} - -\pbx{returns the primary decomposition of the zerodimensional dpmat -$m$ as a list of $\{component, associated\ prime\}$ pairs.} - -\verb|zeroprimes m| \index{zeroprimes} - -\pbx{returns the list of primes of the zerodimensional dpmat $m$.} - -\verb|zeroradical gb| \index{zeroradical} - -\pbx{returns the radical of the zerodimensional ideal $gb$.} - -\verb|zerosolve m|, \verb|zerosolve1 m| and \verb|zerosolve2 m| -\index{zerosolve}\index{zerosolve1}\index{zerosolve2} - -\pbx{Returns for a zerodimensional ideal a list of triangular systems -that cover $Z(m)$. {\tt Zerosolve} needs a pure lex.\ term order for -the ``fast'' turn to lex.\ as described in \cite{Moeller}, {\tt -Zerosolve1} is the ``slow'' turn to lex.\ as described in \cite{efgb}, -and {\tt Zerosolve2} incorporated the FGLM term order change into {\tt -Zerosolve1}.} -\end{quote} -\pagebreak - - -\section{The CALI Module Structure} -\vfill - -\begin{tabular}{|p{1.5cm}||p{5.5cm}|p{2cm}|p{4cm}|} -\hline -\sloppy - -name & subject & data type & representation \\ -\hline - -cali & Header module, contains \linebreak -global variables, switches etc. & --- & ---\\ - -bcsf & Base coefficient arithmetic & base coeff. & standard forms \\ - -ring & Base ring setting, definition of the term order & base ring & -special type RING\\ - -mo & monomial arithmetic & monomials & (exp. list . degree list)\\ - -dpoly & Polynomial and vector arith\-metic & dpolys & list of terms\\ - -bas & Operations on base lists & base list & list of base elements \\ - -dpmat & Operations on polynomial matrices, the central data type of -CALI & dpmat & special type DPMAT\\ - -red & Normal form algorithms & --- & ---\\ - -groeb & \gr basis algorithm and related ones & --- & ---\\ - -groebf & the \gr factorizer and its extensions & --- & ---\\ - -matop & Operations on (lists of) \linebreak dpmats that correspond to -ideal/module operations & --- & ---\\ - -quot & Different quotient algorithms & --- & --- \\ - -moid & Monomial ideal algorithms & monomial ideal & list of monomials \\ - -hf & weighted Hilbert series & -- & -- \\ - -res & Resolutions of dpmats & resolution & list of dpmats \\ - -intf & Interface to algebraic mode & --- & ---\\ - -odim & Algorithms for zerodimensional ideals and modules & --- & ---\\ - -prime & Primary decomposition and related questions & --- & ---\\ - -scripts & Advanced applications & --- & ---\\ - -calimat & Extension of the matrix package & --- & ---\\ - -lf & The dual bases approach & --- & ---\\ - -triang & (Zero dimensional) triangular systems & --- & ---\\ -\hline -\end{tabular} -\vfill -\pagebreak - -\begin{theindex} - - \item affine\_monomial\_curve, 33, 36 - \item affine\_points, 7, 35, 36 - \item affine\_points1!*, 35 - \item algebraic numbers, 13 - \item analytic\_spread, 33, 36 - \item annihilator, 28, 36 - \item assgrad, 33, 36 - - \indexspace - - \item bas\_detectunits, 23 - \item bas\_factorunits, 23 - \item bas\_getrelations, 20 - \item bas\_removerelations, 20 - \item bas\_setrelations, 20 - \item base coefficients, 13 - \item base elements, 19 - \item base ring, 9, 17 - \item basis, 13 - \item bcsimp, 14 - \item BettiNumbers, 30, 36 - \item binomial, 7 - \item blockorder, 10, 18 - \item blowup, 7, 33, 36 - \item border basis, 8 - \item bounded identifier, 13, 36 - - \indexspace - - \item cali, 16 - \item cali!=basering, 9, 16, 18 - \item cali!=degrees, 12, 16, 18 - \item cali!=monset, 16, 25 - \item change of term orders, 7 - \item change\_termorder, 35, 37 - \item change\_termorder1, 35, 37 - \item clearcaliprintterms, 16 - \item codim, 29, 37 - \item column degree, 12 - - \indexspace - - \item degree, 30, 37 - \item degree vectors, 9 - \item degreeorder, 10, 18 - \item degsfromresolution, 37 - \item deleteunits, 23, 37 - \item detectunits, 14, 23 - \item dim, 8, 29, 37 - \item dimzerop, 31, 37 - \item directsum, 37 - \item dmode, 13 - \item dp\_pseudodivmod, 14, 19, 28 - \item dpgcd, 19, 37 - \item dpmat, 8, 12, 13, 20 - \item dpmat\_coldegs, 20 - \item dpmat\_cols, 20 - \item dpmat\_gbtag, 20 - \item dpmat\_list, 20 - \item dpmat\_rows, 20 - \item dual bases, 6, 7, 34, 35 - - \indexspace - - \item easydim, 26, 29, 37 - \item easyindepset, 29, 37 - \item easyprimarydecomposition, 32, 37 - \item ecart, 3, 19 - \item ecart vector, 8, 11, 40 - \item efgb, 16 - \item eliminate, 7, 27, 38 - \item eliminationorder, 10, 18 - \item eqhull, 32, 38 - \item evlf, 17 - \item extended \gr factorizer, 7, 15, 26 - \item extendedgroebfactor, 26, 38 - \item extendedgroebfactor1, 26, 38 - - \indexspace - - \item factorunits, 15, 23 - \item flatten, 8 - \item free identifier, 13 - - \indexspace - - \item gb-tag, 8, 20 - \item gbasis, 24, 38 - \item gbtestversion, 7, 8, 16, 24 - \item getdegrees, 12 - \item getecart, 11 - \item getkbase, 31, 38 - \item getleadterms, 38 - \item getring, 11 - \item getrules, 13 - \item global procedures, 5 - \item GradedBettiNumbers, 30 - \item gradedbettinumbers, 38 - \item groeb, 7 - \item groeb!=rf, 16 - \item groeb\_homstbasis, 24 - \item groeb\_lazystbasis, 24 - \item groeb\_mingb, 25 - \item groeb\_minimize, 25 - \item groeb\_stbasis, 24 - \item groebf\_zeroprimes1, 27 - \item groebfactor, 26, 38 - - \indexspace - - \item hardzerotest, 15 - \item hf!=hf, 16 - \item hf\_whilb, 30 - \item hf\_whilb3, 30 - \item hf\_whs\_from\_resolution, 30 - \item hftestversion, 8, 16, 30 - \item HilbertSeries, 8, 11, 30, 38 - \item homstbasis, 25, 38 - - \indexspace - - \item ideal2mat, 12, 38 - \item ideal\_of\_minors, 21, 38 - \item ideal\_of\_pfaffians, 21, 39 - \item idealpower, 39 - \item idealprod, 39 - \item idealquotient, 27, 28, 39 - \item ideals, 12 - \item idealsum, 39 - \item indepvarsets, 29, 39 - \item initmat, 39 - \item internal procedures, 5 - \item interreduce, 23, 39 - \item isolatedprimes, 32, 39 - \item isprime, 32, 39 - \item iszeroradical, 39 - - \indexspace - - \item lazy, 7 - \item lazystbasis, 25, 39 - \item lexefgb, 15, 27 - \item lexicographic, 9 - \item listgroebfactor, 26, 39 - \item listminimize, 6 - \item listtest, 6 - \item local procedures, 5 - \item localorder, 10, 18 - - \indexspace - - \item map, 32 - \item mat2list, 8, 12, 39 - \item matappend, 40 - \item mathomogenize, 40 - \item mathprint, 17 - \item matintersect, 7, 27, 40 - \item matjac, 21, 40 - \item matqquot, 28, 40 - \item matquot, 28, 40 - \item matstabquot, 28, 40 - \item matsum, 40 - \item minimal\_generators, 34, 40 - \item minors, 21, 40 - \item mod, 23, 40 - \item modequalp, 8, 27, 40 - \item module - \subitem bcsf, 17 - \subitem cali, 5 - \subitem calimat, 8, 21 - \subitem dpmat, 20 - \subitem groeb, 24 - \subitem groebf, 7, 26 - \subitem lf, 7, 17 - \subitem moid, 28 - \subitem mora, 7 - \subitem odim, 7, 31 - \subitem prime, 31 - \subitem ring, 17 - \subitem scripts, 7, 32 - \subitem triang, 26, 27 - \item module quotient, 27 - \item module term order, 12 - \item modulequotient, 28, 40 - \item modules, 12 - \item moid\_primes, 29 - - \indexspace - - \item Noetherian, 3, 15 - \item normalform, 23, 41 - \item nzdp, 34, 41 - - \indexspace - - \item odim\_borderbasis, 31 - \item odim\_parameter, 31 - \item odim\_up, 31 - \item oldbasis, 17 - \item oldborderbasis, 17 - \item oldring, 17 - - \indexspace - - \item pfaffian, 21, 41 - \item preimage, 7, 32, 41 - \item primarydecomposition, 7, 41 - \item printterms, 16 - \item proj\_monomial\_curve, 33, 41 - \item proj\_points, 7, 35, 41 - \item proj\_points1!*, 35 - - \indexspace - - \item radical, 32, 41 - \item random\_linear\_form, 21, 41 - \item ratpreimage, 33, 41 - \item red, 7 - \item red\_better, 22 - \item red\_extract, 23 - \item red\_Interreduce, 23 - \item red\_prepare, 23 - \item red\_redpol, 23 - \item red\_Straight, 22 - \item red\_TailRed, 22 - \item red\_TailRedDriver, 22 - \item red\_TopInterreduce, 23 - \item red\_TopRed, 22 - \item red\_TopRedBE, 22 - \item red\_total, 15 - \item red\_TotalRed, 22 - \item Resolve, 7, 30, 42 - \item reverse lexicographic, 8, 9 - \item ring, 13 - \item ring\_2a, 17 - \item ring\_define, 17 - \item ring\_degrees, 17 - \item ring\_ecart, 17 - \item ring\_from\_a, 17 - \item ring\_isnoetherian, 17 - \item ring\_lp, 18 - \item ring\_names, 17 - \item ring\_rlp, 18 - \item ring\_sum, 18 - \item ring\_tag, 17 - \item rules, 16 - - \indexspace - - \item savemat, 42 - \item setcaliprintterms, 16 - \item setcalitrace, 8, 15 - \item setdegrees, 12, 16 - \item setgbasis, 8, 42 - \item setideal, 13, 14 - \item setkorder, 18 - \item setmodule, 13, 14 - \item setmonset, 16, 25 - \item setring, 7, 9, 11, 14, 16, 18 - \item setrules, 13, 14, 16, 17, 19 - \item sieve, 42 - \item singular\_locus, 21, 42 - \item stable quotient, 27 - \item sublist, 17 - \item submodulep, 27, 42 - \item switch - \subitem bcsimp, 17 - \subitem hardzerotest, 13 - \subitem lexefgb, 16, 27 - \subitem Noetherian, 10, 18 - \item sym, 7, 34, 42 - \item symbolic\_power, 34, 42 - \item syzygies, 24, 42 - \item syzygies1, 24 - - \indexspace - - \item tangentcone, 42 - \item term, 19 - \item trace, 16 - \item tracing, 8 - \item triang, 7 - \item triangular systems, 7, 26 - - \indexspace - - \item unmixedradical, 32, 42 - - \indexspace - - \item varlessp, 17 - \item varnames, 17 - \item varopt, 34, 43 - - \indexspace - - \item WeightedHilbertSeries, 8, 29, 30, 43 - - \indexspace - - \item zeroprimarydecomposition, 31, 32, 43 - \item zeroprimes, 31, 43 - \item zeroradical, 31, 43 - \item zerosolve, 15, 27, 43 - \item zerosolve1, 15, 27, 43 - \item zerosolve2, 27, 43 - -\end{theindex} - -\pagebreak - -\begin{thebibliography}{xxx} -\bibitem{BS} D. Bayer, M. Stillman: Computation of Hilbert -functions. {\it J. Symb. Comp. \bf 14} (1992), 31 - 50. -\bibitem{BKW} T. Becker, H. Kredel, V. Weispfenning: \gr bases. A -computational approach to commutative algebra. Grad. Texts in Math. -141, Springer, New York 1993. -\bibitem{BCRT} A. M. Bigatti, P. Conti, L. Robbiano, C. Traverso: A -``divide and conquer'' algorithm for Hilbert-Poincare series, -multiplicity and dimension of monomial ideals. In: Proc. AAECC-10, -LNCS 673 (1993), 76 - 88. -\bibitem{BGK} W. Boege, R. Gebauer, H. Kredel: Some examples for -solving systems of algebraic equations by calculating \gr bases. {\it -J. Symb. Comp. \bf 2} (1986), 83 - 98. -\bibitem{B1} B. Buchberger: \gr bases: An algorithmic method in -polynomial ideal theory. In: Recent trends in multidimensional -system theory (N.~K.~Bose ed), Reidel, Dortrecht 1985, 184 - 232. -\bibitem{B2} B. Buchberger: Applications of \gr bases in non-linear -computational geometry. LNCS 296 (1988), 52 - 80. -\bibitem{CLO} D. Cox, J. Little, D. O'Shea: Ideals, varieties, and -algorithms. Undergraduate Texts in Math., Springer, New York 1992. -\bibitem{E} D. Eisenbud: Commutative algebra with a view toward -algebraic geometry. Springer, 1995. -\bibitem{FGLM} Faugere, Gianni, Lazard, Mora: Efficient computations -of zerodimensional \gr bases by change of ordering. {\it -J. Symb. Comp. \bf 16} (1993), 329 - 344. -\bibitem{GTZ} P. Gianni, B. Trager, G. Zacharias: \gr bases and -primary decomposition of polynomial ideals. {\it J. Symb. Comp. \bf -6} (1988), 149 - 167. -\bibitem{GMNRT} A. Giovini, T. Mora, G. Niesi, L. Robbiano, C. -Traverso: "One sugar cube, please" or Selection strategies in the -Buchberger algorithm. In: Proceedings of the ISSAC'91, ACM Press -1991, 49 - 54. -\bibitem{rois} H.-G. Gr\"abe: Two remarks on independent sets. -{\it J. Alg. Comb. \bf 2} (1993), 137 - 145. -\bibitem{tcah} H.-G. Gr\"abe: The tangent cone algorithm and -homogenization. {\it J. Pure Applied Alg.\bf 97} (1994), 303 - 312. - -\bibitem{ala} H.-G. Gr\"abe: Algorithms in local algebra. To appear - -\bibitem{fgb} H.-G. Gr\"abe: On factorized \gr bases. Report Nr. 6 -(1994), Inst. f. Informatik, Univ. Leipzig. - -To appear in: Proc. ``Computer Algebra in Science and Engineering'', -Bielefeld 1994. - -\bibitem{efgb} H.-G. Gr\"abe: Triangular systems and factorized \gr -bases. Report Nr. 7 (1995), Inst. f. Informatik, Univ. Leipzig. - -\bibitem{primary} H.-G. Gr\"abe: Factorized \gr bases and primary -decomposition. To appear. - -\bibitem{Kr} H. Kredel: Primary ideal decomposition. In: Proc. -EUROCAL'87, Lecture Notes in Comp. Sci. 378 (1986), 270 - 281. -\bibitem{KW} H. Kredel, V. Weispfenning: Computing dimension and -independent sets for polynomial ideals. {\it J. Symb. Comp. \bf 6} -(1988), 231 - 247. -\bibitem{MMM} M. Marinari, H.-M. M\"oller, T. Mora: \gr bases of -ideals given by dual bases. In: Proc. ISSAC'91, ACM Press 1991, 55 - -63. -\bibitem{Mishra} B. Mishra: Algorithmic Algebra. Springer, New York -1993. -\bibitem{MM} H.-M. M\"oller, F. Mora: New constructive methods in -classical ideal theory. {\it J. Alg. \bf 100} (1986), 138 -178. -\bibitem{Moeller} H.-M. M\"oller: On decomposing systems of polynomial -equations with finitely many solutions. {\em J. AAECC \bf 4} (1993), -217 - 230. -\bibitem{MR88} T. Mora, L. Robbiano: The Gr\"obner fan of an ideal. -{\it J. Symb. Comp. \bf 6} (1988), 183 - 208. -\bibitem{Mo88} T. Mora: Seven variations on standard bases. -Preprint, Univ. Genova, 1988. -\bibitem{MPT} T. Mora, G. Pfister, C. Traverso: An introduction to -the tangent cone algorithm. In: {\em Issues in non-linear geometry and -robotics, C.M. Hoffman ed.}, JAI Press. -\bibitem{Ro} L. Robbiano: Computer algebra and commutative algebra. -LNCS 357 (1989), 31 - 44. -\bibitem{Ru} E. W. Rutman: \gr bases and primary decomposition of -modules. {\it J. Symb. Comp. \bf 14} (1992), 483 - 503. - -\end{thebibliography} - -\end{document} - +% CALI user documentation +% H.-G. Graebe | Univ. Leipzig | Version 2.2.1 + +\documentstyle[11pt]{article} +\date{June 28, 1995} + +\textheight 21cm +\textwidth 15cm +\voffset -60pt +\hoffset -45pt + +\newcommand{\gr}{Gr\"obner } +\newcommand{\x}{{\bf x}} +\newcommand{\ind}[1]{{\em #1}\index{#1}} +\newcommand{\pbx}[1]{\mbox{}\hfill \parbox[t]{12cm}{#1} \pagebreak[3]} +\newcommand{\nl}{\newline \hspace*{5mm}} + +\makeindex + +\title{CALI\\[20pt] A REDUCE Package for \\ + Commutative Algebra \\Version 2.2.1} + +\author{ +Hans-Gert Gr\"abe \\[15pt] +Universit\"at Leipzig\\ +Institut f\"ur Informatik \\ +Augustusplatz 10 -- 11\\ +04109 Leipzig / Germany\\[20pt] +email: graebe@informatik.uni-leipzig.de} + +\begin{document} + +\maketitle + +\vfill +Key words: +affine and projective monomial curves, +affine and projective sets of points, +analytic spread, +associated graded ring, +blowup, +border bases, +constructive commutative algebra, +dual bases, +elimination, +equidimensional part, +extended \gr factorizer, +free resolution, +\gr algorithms for ideals and module, +\gr factorizer, +ideal and module operations, +independent sets, +intersections, +lazy standard bases, +local free resolutions, +local standard bases, +minimal generators, +minors, +normal forms, +pfaffians, +polynomial maps, +primary decomposition, +quotients, +symbolic powers, +symmetric algebra, +triangular systems, +weighted Hilbert series, +primality test, +radical, +unmixed radical. + +\pagebreak + +\tableofcontents + +\pagebreak + +\section{Introduction} + +This package contains algorithms for computations in commutative +algebra closely related to the \gr algorithm for ideals and modules. +Its heart is a new implementation of the \gr algorithm\footnote{The +data representation even for polynomials is different from that given +in the {\tt groebner} package distributed with REDUCE (and rests on ideas +used in the {\tt dipoly} package).} that allows the computation of +syzygies, too. This implementation is also applicable to submodules of +free modules with generators represented as rows of a matrix. + +Moreover CALI contains facilities for local computations, using a +modern implementation of Mora's standard basis algorithm, see +\cite{MPT} and \cite{tcah}, that works for arbitrary term orders. +The full analogy between modules over the local ring \linebreak[1] +$k[x_v:v\in H]_{\bf m}$ and homogeneous (in fact H-local) modules +over $k[x_v:v\in H]$ is reflected through the switch +\ind{Noetherian}. Turn it on (\gr basis, the default) or off (local +standard basis) to choose appropriate algorithms +automatically. In v.\ 2.2 we present an unified approach to both +cases, using reduction with bounded ecart for non Noetherian term +orders, see \cite{ala} for details. This allows to have a common +driver for the \gr algorithm in both cases. + +CALI extends also the restricted term order facilities of the {\tt +groebner} package, defining term orders by degree vector lists, and +the rigid implementation of the sugar idea, by a more flexible +\ind{ecart} vector, in particular useful for local computations, see +\cite{tcah}. +\medskip + +The package was designed mainly as a symbolic mode programming +environment extending the build-in facilities of REDUCE for the +computational approach to problems arising naturally in commutative +algebra. An algebraic mode interface accesses (in a more rigid frame) +all important features implemented symbolically and thus +should be favored for short sample computations. + +On the other hand, tedious computations are strongly recommended to +be done symbolically since this allows considerably more flexibility +and avoids unnecessary translations of intermediate results from +CALI's internal data representation to the algebraic mode and vice +versa. Moreover, one can easily extend the package with new symbolic +mode scripts, or do more difficult interactive computations. For all +these purposes the symbolic mode interface offers substantially more +facilities than the algebraic one. +\medskip + +For a detailed description of special symbolic mode procedures one +should consult the source code and the comments therein. In this +manual we can give only a brief description of the main ideas +incorporated into the package CALI. We concentrate on the data +structure design and the description of the more advanced algorithms. +For sample computations from several fields of commutative algebra +the reader may consult also the {\em cali.tst} file. +\medskip + +As main topics CALI contains facilities for +\begin{itemize} +\item defining rings, ideals and modules, + +\item computing \gr bases and local standard bases, + +\item computing syzygies, resolutions and (graded) Betti numbers, + +\item computing (now also weighted) Hilbert series, multiplicities, +independent sets, and dimensions, + +\item computing normal forms and representations, + +\item computing sums, products, intersections, quotients, stable +quotients, elimination ideals etc., + +\item primality tests, computation of radicals, unmixed radicals, +equidimensional parts, primary decompositions etc. of ideals and +modules, + +\item advanced applications of \gr bases (blowup, associated graded +ring, analytic spread, symmetric algebra, monomial curves etc.), + +\item applications of linear algebra techniques to zero dimensional + ideals, as e.g.\ the FGLM change of term orders, border bases + and affine and projective ideals of sets of points, + +\item splitting polynomial systems of equations mixing factorization and +the \gr algorithm, triangular systems, and different versions of the +extended \gr factorizer. + +\end{itemize} + +Below we will use freely without further explanation the notions +common for text books and papers about constructive commutative +algebra, assuming the reader to be familiar with the corresponding +ideas and concepts. For further references see e.g.\ the text books +\cite{BKW}, \cite{CLO} and \cite{Mishra} or the survey papers +\cite{B1}, \cite{B2} and \cite{Ro}. + +\subsection{Description of the Documents Distributed with CALI} + +The CALI package contains the following files: +\begin{quote} +cali.chg + +\pbx{a detailed report of changes from v.\ 2.1 to v.\ 2.2. and 2.2.1} + +cali.log + +\pbx{the output file, that cali.tst should produce with +\begin{quote} \tt +load\_package cali; + +out "logfile"\$ + +in "cali.tst"; + +shut "logfile"\$ +\end{quote}} + +cali.red + +\pbx{the CALI source file.} + +cali.tex + +\pbx{this manual.} + +cali.tst + +\pbx{a test file with various examples and applications of CALI.} + +\end{quote} + +CALI should be precompiled as usual, i.e.\ either using the {\em +makefasl} utility of REDUCE or ``by hand'' via +\begin{verbatim} + faslout "cali"$ + in "cali.red"$ + faslend$ +\end{verbatim} +and then loaded via +\begin{verbatim} + load_package cali; +\end{verbatim} +Upon successful loading CALI responds with a message containing the +version number and the last update of the distribution. + +\begin{center} +\fbox{\parbox{12cm}{Feel free to contact me by email if You have +problems to get CALI started. Also comments, hints, bug reports etc. +are welcome.}} +\end{center} + +\subsection{CALI's Language Concept} + +From a certain point of view one of the major disadvantage of the +current RLISP (and the underlying PSL) language is the fact +that it supports modularity and data encapsulation only in a +rudimentary way. Since all parts of code loaded into a session are +visible all the time, name conflicts between different packages may +occur, will occur (even not issuing a warning message), and are hard +to prevent, since packages are developed (and are still developing) +by different research groups at different places and different time. + +A (yet rudimentary) concept of REDUCE packages and modules indicates the +direction into what the REDUCE designers are looking for a solution +for this general problem. +\medskip + +CALI (2.0 and higher) follows a name concept for internal procedures +to mimick data encapsulation at a semantical level. We hope this way +on the one hand to resolve the conflicts described above at least for +the internal part of CALI and on the other hand to anticipate a +desirable future and already foregoing development of REDUCE towards +a true modularity. + +The package CALI is divided into several modules, each of them +introducing either a single new data type together with basic +facilities, constructors, and selectors or a collection of algorithms +subject to a common problem. Each module contains \ind{internal +procedures}, conceptually hidden by this module, \ind{local +procedures}, designed for a CALI wide use, and \ind{global +procedures}, exported by CALI into the general (algebraic or +symbolic) environment of REDUCE. A header \ind{module cali} contains +all (fluid) global variables and switches defined by the pacakge +CALI. + +Along these lines the CALI procedures available in symbolic mode are +divided into three types with the following naming convention: +\begin{quote} +\verb|module!=procedure| + +\pbx{internal to the given module.} + +\verb|module_procedure| + +\pbx{exported by the given module into the local CALI environment.} + +\verb|procedure!*| + +\pbx{a global procedure usually having a semantically equivalent +procedure (possibly with another parameter list) without trailing +asterisk in algebraic mode.} +\end{quote} +There are also symbolic mode equivalents without trailing asterisk, if +the algebraic procedure is not a {\em psopfn}, but a {\em symbolic +operator}. They transfer data to CALI's internal structure and call +the corresponding procedure with trailing asterisk. CALI 2.2 +distinguishes between algebraic and symbolic calls of such a +procedure. In symbolic mode such a procedure calls the corresponding +procedure with trailing asterisk directly without data transfer. +\medskip + +CALI 2.2 follows also a more concise concept for global +variables. There are three types of them: +\begin{quote} +True {\em fluid} global variables, + +\pbx{that are part of the current data structure, as e.g.\ the current +base ring and the degree vector. They are often locally rebound to be +restored after interrupts.} + +Global variables, stored on the property list of the package name {\tt +cali}, + +\pbx{that reflect the state of the computational model as e.g.\ the +trace level, the output print level or the chosen version of the \gr +basis algorithm. There are several such parameters in the module +\ind{dualbases} to serve the common dual basis driver with +information for different applications.} + +{\em Switches,} + +\pbx{that allow to choose different branches of algorithms. Note that +this concept interferes with the second one. Different {\em versions} +of algorithms, that apply different functions in a common driver, are +{\em not} implemented through switches.} +\end{quote} + +\subsection{New and Improved Facilities in v.\ 2.1} + +The major changes in v.\ 2.1 reflect the experience we've got from the +use of CALI 2.0. The following changes are worth mentioning +explicitely: +\begin{enumerate} +\item The algebraic rule concept was adapted to CALI. It allows to +supply rule based coefficient domains. This is a more efficient way +to deal with (easy) algebraic numbers than through the {\em arnum +package}. + +\item \ind{listtest} and \ind{listminimize} provide an unified +concept for different list operations previously scattered in the +source text. + +\item There are several new quotient algorithms at the symbolic level +(both the general element and the intersection approaches are +available) and new features for the computation of equidimensional +hull and equidimensional radical. + +\item A new \ind{module scripts} offers advanced applications of \gr +bases. + +\item Several advanced procedures initialize a \gr basis computation +over a certain intermediate base ring or term order as e.g.\ +\ind{eliminate}, \ind{resolve}, \ind{matintersect} or all +\ind{primary decomposition} procedures. Interrupting a computation in +v.\ 2.1 now restores the original values of CALI's global variables, +since all intermediate procedures work with local copies of +the global variables.\footnote{Note that recovering the base +ring this way may cause some trouble since the intermediate ring, +installed with \ind{setring}, changed possibly the internal variable +order set by {\em setkorder}.} This doesn't apply to advanced +procedures that change the current base ring as e.g.\ \ind{blowup}, +\ind{preimage}, \ind{sym} etc. + +\end{enumerate} + +\subsection{New and Improved Facilities in v.\ 2.2} + +Version 2.2 (beside bug fixes) incorporates several new facilities of +constructive non linear algebra that we investigated the last two +years, as e.g.\ dual bases, the \gr factorizer, triangular systems, and +local standard bases. Essential changes concern the following topics: +\begin{enumerate} +\item The CALI modules \ind{red} and \ind{groeb} were rewritten and +the \ind{module mora} was removed. This is +due to new theoretical insight into standard bases theory as +e.g.\ described in \cite{tcah} or \cite{ala}. The \gr basis algorithm +is reorganized as a \gr driver with simplifier and base lists, that +involves different versions of polynomial reduction according to the +setting via \ind{gbtestversion}. It applies now to +both noetherian and non noetherian term orders in a unified way. + +The switches \ind{binomial} and \ind{lazy} were removed. + +\item The \gr factorizer was thoroughly revised, extended along the +lines explained in \cite{fgb}, and collected into a separate +\ind{module groebf}. It now allows a list of constraints also in +algebraic mode. Two versions of an \ind{extended \gr factorizer} +produce \ind{triangular systems}, +i.e.\ a decomposition into quasi prime components, see \cite{efgb}, +that are well suited for further (numerical) evaluation. There is also +a version of the \gr factorizer that allows a list of problems as +input. This is especially useful, if a system is splitted with respect +to a ``cheap'' (e.g. degrevlex) term order and the pieces are +recomputed with respect to a ``hard'' (e.g. pure lex) term order. + +The extended \gr factorizer involves, after change to dimension zero, +the computation of \ind{triangular systems}. The corresponding module +\ind{triang} extends the facilities for zero dimensional ideals and +modules in the \ind{module odim}. + +\item A new \ind{module lf} implements the \ind{dual bases} approach +as described in \cite{MMM}. On this basis there are new +implementations of \ind{affine\_points} and \ind{proj\_points}, that +are significantly faster than the old ones. The linear algebra +\ind{change of term orders} \cite{FGLM} is available, too. There are +two versions, one with precomputed \ind{border basis}, the other with +conventional normal forms. + +\item \ind{dpmat}s now have a \ind{gb-tag} that indicates, whether the +given ideal or module basis is already a \gr basis. This avoids +certain \gr basis recomputations especially during advanced algorithms +as e.g.\ prime decomposition. In the algebraic interface \gr bases are +computed automatically when needed rather than to issue an error +message as in v.\ 2.1. So one can call \ind{modequalp} or \ind{dim} +etc. not having computed \gr bases in advance. Note that such +automatic computation can be avoided with \ind{setgbasis}. + +\item Hilbert series are now \ind{weighted Hilbert series}, since +e.g.\ for blow up rings the generating ideal is multigraded. Usual +Hilbert series are computed as in v.\ 2.1 with respect to the +\ind{ecart vector}. Weighted Hilbert series accept a list of (integer) +weight lists as second parameter. + +\item There are some name and conceptual changes to existing +procedures and variables to have a more concise semantic concept. This +concerns +\begin{quote} +\ind{tracing} (the trace parameter is now stored on the property list +of {\tt cali} and should be set with \ind{setcalitrace}), + +choosing different versions of the \gr algorithm (through +\ind{gbtestversion}) and the Hilbert series computation (through +\ind{hftestversion}), + +some names (\ind{mat2list} replaced \ind{flatten}, \ind{HilbertSeries} +replaced {\em hilbseries}) and + +parameter lists of some local and internal procedures (consult {\em +cali.chg} for details). +\end{quote} + +\item The \ind{revlex term order} is now the reverse lexicographic +term order on the {\bf reversely} ordered variables. This is consistent +with other computer algebra systems (e.g.\ SINGULAR or +AXIOM)\footnote{But different to the currently distibuted {\tt +groebner} package in REDUCE. Note that the computations in +\cite{fgb} were done {\em before} these changes.} and implies the same +order on the variables for deglex and degrevlex term orders (this was +the main reason to change the definition). + +\item Ideals of minors, pfaffians and related stuff are now +implemented as extension of the internal {\tt matrix} package and +collected into a separate \ind{module calimat}. Thus they allow more +general expressions, especially with variable exponents, as general +REDUCE matrices do. So one can define generic ideals as e.g.\ ideals +of minors or pfaffians of matrices, containing generic expressions as +elements. They must be specified for further use in CALI substituting +general exponents by integers. + +\end{enumerate} + +\subsection{New and Improved Facilities in v.\ 2.2.1\label{221}} + +The main change concerns the primary decomposition algorithm, where I +fixed a serious bug for deciding, which embedded primes are really +embedded\footnote{That there must be a bug was pointed out to me by +Shimoyama Takeshi who compared different p.d.\ implementations. The +bug is due to an incorrect test for embedded primes: A (superfluous) +primary component may contain none of the isolated primary components, +but their intersection! Note that neither \cite{GTZ} nor \cite{BKW} +comment on that. Details of the implementation will appear in +\cite{primary}.}. During that remake I incorporated also the \gr +factorizer to compute isolated primes. Since REDUCE has no +multivariate {\em modular} factorizer, the switch \ind{factorprimes} +may be turned off to switch to the former algorithm. + + + +Some minor bugs are fixed, too, e.g.\ the bug that made \ind{radical} +crashing. + + + + +\section{The Computational Model} + +This section gives a short introduction into the data type design of +CALI at different levels. First (\S 1 and 2) we describe CALI's way +of algorithmic translation of the abstract algebraic objects {\em +ring of polynomials, ideal} and (finitely generated) {\em module}. +Then (\S 3 and 4) we describe the algebraic mode interface of CALI +and the switches and global variables to drive a session. In the next +chapter we give a more detailed overview of the basic (symbolic mode) data +structures involved with CALI. We refer to the appendix for a short +summary of the commands available in algebraic mode. + +\subsection{The Base Ring} + +A polynomial ring consists in CALI of the following data: +\begin{quote} +a list of variable names + +\pbx{All variables not occuring in the list of ring names are treated +as parameters. Computations are executed denominatorfree, but the +results are valid only over the corresponding parameter {\em field} +extension.} + +a term order and a term order tag + +\pbx{They describe the way in which the terms in each polynomial (and +polynomial vector) are ordered.} + +an ecart vector + +\pbx{A list of positive integers corresponding to the variable +names.} +\end{quote} + +A \ind{base ring} may be defined (in algebraic mode) through the +command +\begin{verbatim} + setring +\end{verbatim} +with $$ ::= \{\, vars,\,tord,\,tag\,[,\,ecart\,]\,\} resp. +\begin{verbatim} + setring(vars, tord, tag [,ecart]) +\end{verbatim} +\index{setring} +This sets the global (symbolic) variable \ind{cali!=basering}. Here +{\tt vars} is the list of variable names, {\tt tord} a (possibly +empty) list of weight lists, the \ind{degree vectors}, and {\tt tag} +the tag LEX or REVLEX. Optionally one can supply {\tt ecart}, a list +of positive integers of the same length as {\tt vars}, to set an ecart +vector different from the default one (see below). + +The degree vectors must have the same length as {\tt vars}. If $(w_1\ +\ldots\ w_k)$ is the list of degree vectors then +\[x^aj\ :\ a_i=b_i\quad\mbox{and}\quad a_j>b_j\ +\mbox{(revlex.)}\] + +Every term order can be represented in such a way, see \cite{MR88}. + +During the ring setting the term order will be checked to be +Noetherian (i.e.\ to fulfill the descending chain condition) provided +the \ind{switch Noetherian} is on (the default). The same applies +turning {\em noetherian on}: If the term order of the underlying +base ring isn't Noetherian the switch can't be turned over. Hence, +starting from a non Noetherian term order, one should define {\em +first} a new ring and {\em then} turn the switch on. + +Useful term orders can be defined by the procedures +\begin{quote} +\verb|degreeorder vars|, \index{degreeorder} + +\pbx{that returns $tord=\{\{1,\ldots ,1\}\}$.} + +\verb|localorder vars|, \index{localorder} + +\pbx{that returns $tord=\{\{-1,\ldots ,-1\}\}$ (a non Noetherian term +order for computations in local rings).} + +\verb|eliminationorder(vars,elimvars)|, \index{eliminationorder} + +\pbx{that returns a term order for elimination of the variables in +{\tt elimvars}, a subset of all {\tt vars}. It's recommended to +combine it with the tag REVLEX.} + +\verb|blockorder(vars,integerlist)|, \index{blockorder} + +\pbx{that returns the list of degree vectors for the block order with +block lengths given in the {\tt integerlist}. Note that these numbers +should sum up to the length of the variable list supplied as the first +argument.} +\end{quote} + +\noindent Examples: +\begin{verbatim} +vars:={x,y,z}; +tord:=degreeorder vars; % Returns {{1,1,1}}. +setring(vars,tord,lex); % GRADLEX in the groebner package. + +% or + +setring({a,b,c,d},{},lex); % LEX in the groebner package. + +% or + +vars:={a,b,c,x,y,z}; +tord:=eliminationorder(vars,{x,y,z}); +tord:=reverse blockorder(vars,{3,3}); + % Return both {{0,0,0,1,1,1},{1,1,1,0,0,0}}. +setring(vars,tord,revlex); +\end{verbatim} +\pagebreak[2] + +The base ring is initialized with \\[10pt] +\verb|{{t,x,y,z},{{1,1,1,1}},revlex,{1,1,1,1}}|,\\[10pt] +i.e.\ $S=k[t,x,y,z]$ supplied with the degree wise reverse +lexicographic term order. +\begin{quote} +\verb|getring m|\index{getring} + +\pbx{returns the ring attached to the object with the identifier +$m$. E.g.\ } + +\verb|setring getring m| + +\pbx{(re)sets the base ring to the base ring of the formerly defined +object (ideal or module) $m$.} + +\verb|getring()| + +\pbx{returns the currently active base ring.} +\end{quote} + +CALI defines also an \ind{ecart vector}, attaching to each variable a +positive weight with respect to that homogenizations and related +algorithms are executed. It may be set optionally by the user during +the \ind{setring} command. (Default: If the term order is a +(positive) degree order then the ecart is the first degree vector, +otherwise each ecart equals 1). + +The ecart vector is used in several places for efficiency reason (\gr +basis computation with the sugar strategy) or for termination (local +standard bases). If the input is homogeneous the ecart vector should +reflect this homogeneity rather than the first degree vector to +obtain the best possible performance. For a discussion of local +computations with encoupled ecart vector see \cite{tcah}. In general +the ecart vector is recommended to be chosen in such a way that the +input examples become close to be homogeneous. {\em Homogenizations} +and \ind{Hilbert series} are computed with respect to this ecart +vector. +\medskip + +\noindent \verb|getecart()|\index{getecart} returns the ecart vector +currently set. + + +\subsection{Ideals and Modules} + +If $S=k[x_v,\ v \in H]$ is a polynomial ring, a matrix $M$ of size +$r\times c$ defines a map +\[f\ :\ S^r \longrightarrow S^c\] +by the following rule +\[ f(v):=v\cdot M \qquad \mbox{ for } v \in S^r.\] +There are two modules, connected with such a map, $im\ f$, the +submodule of $S^c$ generated by the rows of $M$, and $coker\ f\ +(=S^c/im\ f)$. Conceptually we will identify $M$ with $im\ f$ for the +basic algebra, and with $coker\ f$ for more advanced topics of +commutative algebra (Hilbert series, dimension, resolution etc.) +following widely accepted conventions. + +With respect to a fixed basis $\{e_1,\ldots ,e_c\}$ one can define +module term orders on $S^c$, \gr bases of submodules of $S^c$ etc. +They generalize the corresponding notions for ideal bases. See +\cite{E} or \cite{MM} for a detailed introduction to this area of +computational commutative algebra. This allows to define joint +facilities for both ideals and submodules of free modules. Moreover +computing syzygies the latter come in in a natural way. + +CALI handles ideal and module bases in a unique way representing them +as rows of a \ind{dpmat} ({\bf d}istributive {\bf p}olynomial {\bf +mat}rix). It attaches to each unit vector $e_i$ a monomial $x^{a_i}$, +the $i$-th \ind{column degree} and represents the rows of a dpmat $M$ +as lists of module terms $x^ae_i$, sorted with respect to a +\ind{module term order}, that may be roughly\footnote{The correct +definition is even more difficult.} described as +\bigskip + +\begin{tabular}{cccp{6cm}} +$x^ae_ij$ (revlex.)\\} +\end{tabular} + +Every dpmat $M$ has its own column degrees (no default !). They are +managed through a global (symbolic) variable \ind{cali!=degrees}. +\begin{quote} +\verb|getdegrees m| \index{getdegrees} + +\pbx{returns the column degrees of the object with identifier m.} + +\verb|getdegrees()| + +\pbx{returns the current setting of {\em cali!=degrees}.} + +\verb|setdegrees | \index{setdegrees} + +\pbx{sets {\em cali!=degrees} correspondingly. Use this command +before executing {\em setmodule} to give a dpmat prescribed column +degrees since cali!=degrees has no default value and changes during +computations. A good guess is to supply the empty list (i.e.\ all +column degrees are equal to $\x^0$). Be careful defining modules +without prescribed column degrees.} +\end{quote} + +To distinguish between \ind{ideals} and \ind{modules} the former are +represented as a \ind{dpmat} with $c=0$ (and hence without column +degrees). If $I \subset S$ is such an ideal one has to distinguish +between the ideal $I$ (with $c=0$, allowing special ideal operations +as e.g.\ ideal multiplication) and the submodule $I$ of the free +one dimensional module $S^1$ (with $c=1$, allowing matrix operations +as e.g.\ transposition, matrix multiplication etc.). \ind{ideal2mat} +converts an (algebraic) list of polynomials into an (algebraic) +matrix column whereas \ind{mat2list} collects all matrix entries into +a list. + +\subsection{The Algebraic Mode Interface} + +Corresponding to CALI's general philosophy explained in the +introduction the algebraic mode interface translates algebraic input +into CALI's internal data representation, calls the corresponding +symbolic functions, and retranslates the result back into algebraic +mode. Since \gr basis computations may be very tedious even on small +examples, one should find a well balance between the storage of +results computed earlier and the unavoidable time overhead and memory +request associated with the management of these results. + +Therefore CALI distinguishes between {\em free} and {\em bounded} +\index{free identifier}\index{bounded identifier} identifiers. Free +identifiers stand only for their value whereas to bounded identifiers +several internal information is attached to their property list for +later use. +\medskip + +After the initialization of the {\em base ring} bounded identifiers +for ideals or modules should be declared via +\begin{verbatim} +setmodule(name,matrix value) +\end{verbatim} +resp. +\begin{verbatim} +setideal(name,list of polynomials) +\end{verbatim} +\index{setmodule}\index{setideal} +This way the corresponding internal representation (as \ind{dpmat}) +is attached to {\tt name} as the property \ind{basis}, the prefix +form as its value and the current base ring as the property +\ind{ring}. + +Performing any algebraic operation on objects defined this way their +ring will be compared with the current base ring (including the term +order). If they are different an error message occurs. If {\tt m} is +a valid name, after resetting the base ring +\begin{verbatim} +setmodule(m1,m) +\end{verbatim} +reevaluates {\tt m} with respect to the new base ring (since the +{\em value} of {\tt m} is its prefix form) and assigns the reordered +dpmat to {\tt m1} clearing all information previously computed for +{\tt m1} ({\tt m1} and {\tt m} may coincide). + +All computations are performed with respect to the ring $S=k[x_v\in +{\tt vars}]$ over the field $k$. Nevertheless by efficiency reasons +\ind{base coefficients} are represented in a denominator free way as +standard forms. Hence the computational properties of the base +coefficient domain depend on the \ind{dmode} and also on auxiliary +variables, contained in the expressions, but not in the variable +list. They are assumed to be parameters. + +Best performance will be obtained with integer or modular domain +modes, but one can also try \ind{algebraic numbers} as coefficients +as e.g.\ generated by {\tt sqrt} or the {\tt arnum} package. To avoid +an unnecessary slow-down connected with the management of simplified +algebraic expressions there is a \ind{switch hardzerotest} (default: +off) that may be turned on to force an additional simplification of +algebraic coefficients during each zero test. It should be turned on +only for domain modes without canonical representations as e.g.\ +mixtures of arnums and square roots. We remind the general zero +decision problem for such domains. + +Alternatively, CALI offers the possibility to define a set of +algebraic substitution rules that will affect CALI's base coefficient +arithmetic only. +\begin{quote} +\verb|setrules |\index{setrules} + +\pbx{transfers the (algebraic) rule list into the internal +representation stored at the {\tt cali} value {\tt rules}. + +In particular, {\tt setrules \{\}} clears the rules previously set.} + +\verb|getrules()|\index{getrules} + +\pbx{returns the internal CALI rules list in algebraic form.} +\end{quote} + +We recommend to use \ind{setrules} for computations with algebraic +numbers since they are better adapted to the data structure of CALI +than the algebraic numbers provided by the {\tt arnum} package. +Note, that due to the zero decision problem +complicated {\em setrules} based computations may produce wrong +results if base coefficient's pseudo division is involved (as e.g.\ +with \ind{dp\_pseudodivmod}). In this case we recommend to enlarge +the variable set and add the defining equations of the algebraic +numbers to the equations of the problem\footnote{A {\em qring} +facility for the computation over quotient rings will be incorporated +into future versions.}. +\medskip + +The standard domain (Integer) doesn't allow denominators for input. +\ind{setideal} clears automatically the common denominator of each +input expression whereas a polynomial matrix with true rational +coefficients will be rejected by \ind{setmodule}. +\medskip + +One can save/initialize ideal and module bases together with their +accompanying data (base ring, degrees) to/from a file: +\begin{verbatim} +savemat(m,name) +\end{verbatim} +resp. +\begin{verbatim} +initmat name +\end{verbatim} execute the file transfer from/to disk files with the +specified file {\tt name}. e.g.\ +\begin{verbatim} +savemat(m,"myfile"); +\end{verbatim} +saves the base ring and the ideal basis of $m$ to the file ``myfile'' +whereas +\begin{verbatim} +setideal(m,initmat "myfile"); +\end{verbatim} +sets the current base ring (via a call to \ind{setring}) to the base +ring of $m$ saved at ``myfile'' and then recovers the basis of $m$ +from the same file. + +\subsection{Switches and Global Variables} + +There are several switches, (fluid) global variables, a trace +facility, and global parameters on the property list of the package +name {\tt cali} to control CALI's computations. +\medskip + +\subsubsection*{Switches} + +\begin{quote} +\ind{bcsimp} + +\pbx{on: Cancel out gcd's of base coefficients. (Default: on)} + +\ind{detectunits} + +\pbx{on: replace polynomials of the form \newline +$\langle monomial\rangle * +\langle polynomial\ unit\rangle $ by $\langle monomial\rangle$ +during interreductions and standard basis computations. + +Affects only local computations. (Default: off)} + +\ind{factorprimes} + +\pbx{on: Invoke the \gr factorizer during computation of isolated +primes. (Default: on). Note that REDUCE lacks a modular multivariate +factorizer, hence for modular prime decomposition computations this +switch has to be turned off.} + +\ind{factorunits} + +\pbx{on: factor polynomials and remove polynomial unit factors +during interreductions and standard basis computations. + +Affects only local computations. (Default: off)} + +\ind{hardzerotest} + +\pbx{on: try an additional algebraic simplification of base +coefficients at each base coefficient's zero test. Useful only for +advanced base coefficient domains without canonical REDUCE +representation. May slow down the computation drastically. +(Default: off)} + +\ind{lexefgb} + +\pbx{on: Use the pure lexicographic term order and \ind{zerosolve} +during reduction to dimension zero in the \ind{extended \gr +factorizer}. This is a single, but possibly hard task compared to the +degrevlex invocation of \ind{zerosolve1}. See \cite{efgb} for a +discussion of different zero dimensional solver strategies. +(Default: off)} + +\ind{Noetherian} + +\pbx{on: choose algorithms for Noetherian term orders. + +off: choose algorithms for local term orders. + +(Default: on)} + +\ind{red\_total} + +\pbx{on: compute total normal forms, i.e. apply reduction (Noetherian +term orders) or reduction with bounded ecart (non Noetherian term +orders to tail terms of polynomials, too. + +off: Do only top reduction. + +(Default: on)} + +\end{quote} + +\subsubsection*{Tracing} + +Different to v.\ 2.1 now intermediate output during the computations +is controlled by the value of the {\tt trace} and {\tt printterms} +entries on the property list of the package name {\tt cali}. The +former value controls the intensity of the intermediate output +(Default: 0, no tracing), the latter the number of terms printed in +such intermediate polynomials (Default: all). +\begin{quote} +\verb|setcalitrace |\index{setcalitrace} + +\pbx{changes the trace intensity. Set $n=2$ for a sparse tracing (a +dot for each reduction step). +Other good suggestions are the values 30 or 40 for tracing the \gr +algorithm or $n>70$ for tracing the normal form algorithm. The higher +$n$ the more intermediate information will be given.} + +\verb|setcaliprintterms |\index{setcaliprintterms} + +\pbx{sets the number of terms that are printed in intermediate +polynomials. Note that this does not affect the output of whole {\em +dpmats}. The output of polynomials with more than $n$ terms ($n>0$) +breaks off and continues with ellipses.} + +\verb|clearcaliprintterms()|\index{clearcaliprintterms} + +\pbx{clears the {\tt printterms} value forcing full intermediate +output (according to the current trace level).} +\end{quote} + +\subsubsection*{Global Variables} + +\begin{quote} +\ind{cali!=basering} + +\pbx{The currently active base ring initialized e.g.\ by +\ind{setring}.} + +\ind{cali!=degrees} + +\pbx{The currently active module component degrees initialized e.g.\ +by \ind{setdegrees}.} + +\ind{cali!=monset} + +\pbx{A list of variable names considered as non zero divisors during +\gr basis computations initialized e.g.\ by \ind{setmonset}. Useful +e.g.\ for binomial ideals defining monomial varieties or other prime +ideals.} + +\end{quote} + +\subsubsection*{Entries on the Property List of {\tt cali}} + +This approach is new for v.\ 2.2. Information concerning the state of +the computational model as e.g.\ trace intensity, base coefficient +rules, or algorithm versions are stored as values on the property list +of the package name \ind{cali}. This concerns +\begin{quote} +\ind{trace} and \ind{printterms} + +\pbx{see above.} + +\ind{efgb} + +\pbx{Changed by the \ind{switch lexefgb}.} + +\ind{groeb!=rf} + +\pbx{Reduction function invoked during the \gr algorithm. It can be +changed with \ind{gbtestversion}\ $$ ($n=1,2,3$, default is 1).} + +\ind{hf!=hf} + +\pbx{Variant for the computation of the Hilbert series numerator. It +can be changed with \ind{hftestversion}\ $$ ($n=1,2$, default is 1).} + +\ind{rules} + +\pbx{Algebraic ``replaceby'' rules introduced to CALI with the +\ind{setrules} command.} + +\ind{evlf}, \ind{varlessp}, \ind{sublist}, \ind{varnames}, +\ind{oldborderbasis}, \ind{oldring}, \ind{oldbasis} + +\pbx{see \ind{module lf}, implementing the dual bases approach.} +\end{quote} + + +\section{Basic Data Structures} + +In the following we describe the data structure layers underlying the +dpmat representation in CALI and some important (symbolic) procedures +to handle them. We refer to the source code and the comments therein for +a more complete survey about the procedures available for different +data types. + +\subsection{The Coefficient Domain} + +Base coefficients as implemented in the \ind{module bcsf} are standard +forms in the variables outside the variable list of the current +ring. All computations are executed "denominator free" over the +corresponding quotient field, i.e.\ gcd's are canceled out without +request. To avoid this set the \ind{switch bcsimp} off.\footnote{This +induces a rapid base coefficient's growth and doesn't yield {\bf +Z}-\gr bases in the sense of \cite{GTZ} since the S-pair criteria are +different.} In the given implementation we use the s.f. procedure {\em +qremf} for effective divisibility test. We had some trouble with it +under {\em on factor}. + +Additionally it is possible to supply the +parameters occuring as base coefficients with a (global) set of +algebraic rules.\footnote{This is different from the LET rule +mechanism since they must be present in symbolic mode. Hence for a +simultaneous application of the same rules in algebraic mode outside +CALI they must additionally be declared in the usual way.} +\begin{quote} +\verb|setrules!* r|\index{setrules} + +\pbx{converts an algebraic mode rules list $r$ as e.g.\ used in +WHERE statements into the internal CALI format.} +\end{quote} + +\subsection{The Base Ring} + +The \ind{base ring} is defined by its {\tt name list}, the {\tt +degree matrix} (a list of lists of integers), the {\tt ring tag} (LEX +or REVLEX), and the {\tt ecart}. The name list contains a phantom +name {\tt cali!=mk} for the module component at place 0. +\medskip + +The \ind{module ring} exports among others the selectors +\ind{ring\_names}, \ind{ring\_degrees}, \ind{ring\_tag}, +\ind{ring\_ecart}, the test function \ind{ring\_isnoetherian} and the +transfer procedures from/to an (appropriate, printable by +\ind{mathprint}) algebraic prefix form \ind{ring\_from\_a} (including +extensive tests of the supplied parameters for consistency) and +\ind{ring\_2a}. + +The following procedures allow to define a base ring: +\begin{quote} +\verb|ring_define(name list, degree matrix, ring tag, ecart)| +\index{ring\_define} + +\pbx{combines the given parameters to a ring.} + +\verb|setring!* |\index{setring} + +\pbx{sets {\em cali!=basering} and checks for consistency with the +\ind{switch Noetherian}. It also sets through +\ind{setkorder} the current variable list as main variables. It is +strongly recommended to use {\em setring!* \ldots} instead of {\em +cali!=basering:=\ldots}.} +\end{quote} +\verb|degreeorder!*| , \verb|localorder!*|, \verb|eliminationorder!*|, and +\verb|blockorder!*| +\index{degreeorder} +\index{localorder} +\index{eliminationorder} +\index{blockorder} +define term order matrices in full analogy to algebraic mode. +\medskip + +There are three ring constructors for special purposes: +\begin{quote} +\verb|ring_sum(a,b)|\index{ring\_sum} + +\pbx{returns a ring, that is constructed in the following way: Its +variable list is the union of the (disjoint) lists of the variables +of the rings $a$ and $b$ (in this order) whereas the degree list is +the union of the (appropriately shifted) degree lists of $b$ and $a$ +(in this order). The ring tag is that of $a$. Hence it returns +(essentially) the ring $b\bigoplus a$ if $b$ has a degree part (e.g.\ +useful for elimination problems, introducing ``big'' new variables) +and the ring $a\bigoplus b$ if $b$ has no degree part (introducing +``small'' new variables).} + +\verb|ring_rlp(r,u)|\index{ring\_rlp} + +\pbx{$u$ is a subset of the names of the ring $r$. Returns the ring +$r$, but with a term order ``first degrevlex on $u$, then the order on +r''.} + +\verb|ring_lp(r,u)|\index{ring\_lp} + +\pbx{As $rlp$, but with a term order ``first lex on $u$, then the +order on r''.} +\end{quote} + +\noindent Example: +\begin{verbatim} +vars:='(x y z) +setring!* ring_define(vars,degreeorder!* vars,'lex,'(1 1 1)); + % GRADLEX in the groebner package. +\end{verbatim} + +\subsection{Monomials} + +The current version uses a place-driven exponent representation +closely related to a vector model. This model handles term orders on $S$ +and module term orders on $S^c$ in a unique way. The zero component of the +exponent list of a monomial contains its module component ($>0$) or 0 +(ring element). All computations are executed with respect to a +{\em current ring} (\ind{cali!=basering}) and {\em current (monomial) +weights} of the free generators $e_i, i=1,\ldots,c$, of $S^c$ +(\ind{cali!=degrees}). For efficiency reasons every monomial has a +precomputed degree part that should be reevaluated if {\tt +cali!=basering} (i.e.\ the term order) or {\tt cali!=degrees} were +changed. {\tt cali!=degrees} contains the list of column degrees of +the current module as an assoc. list and will be set automatically by +(almost) all dpmat procedure calls. Since monomial operations use the +degree list that was precomputed with respect to fixed column degrees +(and base ring) +\begin{quote}\bf +watch carefully for {\tt cali!=degrees} programming at the monomial +or dpoly level ! +\end{quote} + +As procedures there are selectors for the module component, the exponent and +the degree parts, comparison procedures, procedures for the management of +the module component and the degree vector, monomial arithmetic, transfer +from/to prefix form, and more special tools. + +\subsection{Polynomials and Polynomial Vectors} + +CALI uses a distributive representation as a list of terms for both +polynomials and polynomial vectors, where a \ind{term} is a dotted +pair +\[(\ .\ ).\] +The \ind{ecart} of a polynomial (vector) $f=\sum{t_i}$ with (module) +terms $t_i$ is defined as \[max(ec(t_i))-ec(lt(t_i)),\] see +\cite{tcah}. Here $ec(t_i)$ denotes the ecart of the term $t_i$, i.e.\ +the scalar product of the exponent vector of $t_i$ (including the +monomial weight of the module generator) with the ecart vector of the +current base ring. + +As procedures there are selectors, dpoly arithmetic including the management +of the module component, procedures for reordering (and reevaluating) +polynomials wrt.\ new term order degrees, for extracting common base +coefficient or monomial factors, for transfer from/to prefix form and for +homogenization and dehomogenization (wrt.\ the current ecart vector). + +Two advanced procedures use ideal theory ingredients: +\begin{quote} +\verb|dp_pseudodivmod(g,f)|\index{dp\_pseudodivmod} + +\pbx{returns a dpoly list $\{q,r,z\}$ such that $z\cdot g = q\cdot f + +r$ and $z$ is a dpoly unit (i.e.\ a scalar for Noetherian term +orders). For non Noetherian term orders the necessary modifications +are described in \cite{ala}. + +$g, f$ and $r$ belong to the same free module or ideal. +} + +\verb|dpgcd(a,b)| \index{dpgcd} + +\pbx{computes the gcd of two dpolys $a$ and $b$ by the syzygy method: +The syzygy module of $\{a,b\}$ is generated by a single element +$[-b_0\ \ a_0]$ with $a=ga_0, b=gb_0$, where $g$ is the gcd of $a$ +and $b$. Since it uses dpoly pseudodivision it may work not properly +with \ind{setrules}.} +\end{quote} + + +\subsection{Base Lists} + +Ideal bases are one of the main ingredients for dpmats. They are +represented as lists of \ind{base elements} and contain together with +each dpoly entry the following information: +\begin{itemize} +\item a number (the row number of the polynomial vector in the +corresponding dpmat). + +\item the dpoly, its ecart (as the main sort criterion), and length. + +\item a representation part, that may contain a representation of the +given dpoly in terms of a certain fixed basis (default: empty). +\end{itemize} + +The representation part is managed during normal form computations +and other row arithmetic of dpmats appropriately with the following +procedures: +\begin{quote} +\verb|bas_setrelations b|\index{bas\_setrelations} + +\pbx{sets the relation part of the base element $i$ in the base list +$b$ to $e_i$.} + +\verb|bas_removerelations b|\index{bas\_removerelations} + +\pbx{removes all relations, i.e.\ replaces them with the zero +polynomial vector.} + +\verb|bas_getrelations b|\index{bas\_getrelations} + +\pbx{gets the relation part of $b$ as a separate base list.} +\end{quote} + +Further there are procedures for selection and construction of base +elements and for the manipulation of lists of base elements as e.g.\ +sorting, renumbering, reordering, simplification, deleting zero base +elements, transfer from/to prefix form, homogenization and dehomogenization. + +\subsection{Dpoly Matrices} + +Ideals and matrices, represented as \ind{dpmat}s, are the central +data type of the CALI package, as already explained above. Every +dpmat $m$ combines the following information: +\begin{itemize} +\item its size (\ind{dpmat\_rows} m,\ind{dpmat\_cols} m), + +\item its base list (\ind{dpmat\_list} m) and + +\item its column degrees as an assoc. list of monomials +(\ind{dpmat\_coldegs} m). If this list is empty, all degrees are +assumed to be equal to $x^0$. + +\item New in v.\ 2.2 there is a \ind{gb-tag} (\ind{dpmat\_gbtag} m), +indicating that the given base list is already a \gr basis (under the +given term order). +\end{itemize} + +The \ind{module dpmat} contains selectors, constructors, and the +algorithms for the basic management of this data structure as e.g.\ +file transfer, transfer from/to algebraic prefix forms, reordering, +simplification, extracting row degrees and leading terms, dpmat matrix +arithmetic, homogenization and dehomogenization. + +The modules {\em matop} and {\em quot} collect more advanced procedures +for the algebraic management of dpmats. + +\subsection{Extending the REDUCE Matrix Package} + +In v.\ 2.2 minors, Jacobian matrix, and Pfaffians are available for +general REDUCE matrices. They are collected in the \ind{module +calimat} and allow to define procedures in more generality, especially +allowing variable exponents in polynomial expressions. Such a +generalization is especially useful for the investigation of whole +classes of examples that may be obtained from a generic one by +specialization. In the following $m$ is a matrix given in algebraic +prefix form. +\begin{quote} +\verb|matjac(m,l)|\index{matjac} + +\pbx{returns the Jacobian matrix of the ideal $m$ (given as an +algebraic mode list) with respect to the variable list $l$.} + +\verb|minors(m,k)|\index{minors} + +\pbx{returns the matrix of $k$-minors of the matrix $m$.} + +\verb|ideal_of_minors(m,k)|\index{ideal\_of\_minors} + +\pbx{returns the ideal of the $k$-minors of the matrix $m$.} + +\verb|pfaffian m|\index{pfaffian} + +\pbx{returns the pfaffian of a skewsymmetric matrix $m$.} + +\verb|ideal_of_pfaffians(m,k)|\index{ideal\_of\_pfaffians} + +\pbx{returns the ideal of the $2k$-pfaffians of the skewsymmetric +matrix $m$.} + +\verb|random_linear_form(vars,bound)|\index{random\_linear\_form} + +\pbx{returns a random linear form in algebraic prefix form in the +supplied variables $vars$ with integer coefficients bounded by the +supplied $bound$.} + +\verb|singular_locus!*(m,c)|\index{singular\_locus} + +\pbx{returns the singular locus of $m$ (as dpmat). $m$ must be an +ideal of codimension $c$ given as a list of polynomials in prefix +form. {\tt Singular\_locus} computes the ideal generated by the +corresponding Jacobian and $m$ itself.} +\end{quote} + +\section{About the Algorithms Implemented in CALI} + +Below we give a short explanation of the main algorithmic ideas of +CALI and the way they are implemented and may be accessed +(symbolically). + +\subsection{Normal Form Algorithms} + +For v.\ 2.2 we completely revised the implementation of normal form +algorithms due to the insight obtained from our investigations of +normal form procedures for local term orders in \cite{ala} and +\cite{tcah}. It allows a common handling of Noetherian and non +Noetherian term orders already on this level thus making superfluous +the former duplication of reduction procedures in the modules {\em +red} and {\em mora} as in v.\ 2.1. +\medskip + +Normal form algorithms reduce polynomials (or polynomial vectors) +with respect to a given finite set of generators of an ideal or +module. The result is not unique except for a total normal form with +respect to a \gr basis. Furthermore different reduction strategies +may yield significant differences in computing time. + +CALI reduces by first matching, usually keeping base lists sorted +with respect to the sort predicate \ind{red\_better}. In v.\ 2.2 we +sort solely by the dpoly length, since the introduction of +\ind{red\_TopRedBE}, i.e.\ reduction with bounded ecart, guarantees +termination also for non Noetherian term orders. Overload red\_better +for other reduction strategies. +\medskip + +Reduction procedures produce for a given ideal basis $B\subset S$ and +a polynomial $f\in S$ a (pseudo) normal form $h\in S$ such that +$h\equiv u\cdot f\ mod\ B$ where $u\in S$ is a polynomial unit, i.e.\ +a (polynomially represented) non zero domain element in the Noetherian +case (pseudodivision of $f$ by $B$) or a polynomial with a scalar as +leading term in the non Noetherian case. Following up the reduction +steps one can even produce a presentation of $h-u\cdot f$ as a +polynomial combination of the base elements in $B$. + +More general, given for $f_i\in B$ and $f$ representations $f_i = +\sum{r_{ik}e_k} = R_i\cdot E^T$ and $f=R\cdot E^T$ as polynomial +combinations wrt.\ a fixed basis $E$ one can produce such a +presentation also for $h$. For this purpose the dpoly $f$ and its +representation are collected into a base element and reduced +simultaneously by the base list $B$, that collects the base elements +and their representations. +\medskip + +The main procedures of the newly designed reduction package are the +following: +\begin{quote} +\verb|red_TopRedBE(bas,model)|\index{red\_TopRedBE} + +\pbx{Top reduction with bounded ecart of the base element $model$ by +the base list $bas$, i.e.\ only reducing the top term and only with +base elements with ecart bounded by that of $model$.} + +\verb|red_TopRed(bas,model)|\index{red\_TopRed} + +\pbx{Top reduction of $model$, but without restrictions.} + +\verb|red_TailRed(bas,model)|\index{red\_TailRed} + +\pbx{Make tail reduction on $model$, i.e.\ top reduction on the tail +terms. For convergence this uses reduction with bounded ecart for non +Noetherian term orders and full reduction otherwise.} +\medskip + +There is a common \ind{red\_TailRedDriver} that takes a top reduction +function as parameter. It can be used for experiments with other top +reduction procedure combinations. + +\verb|red_TotalRed(bas,model)|\index{red\_TotalRed} + +\pbx{A terminating total reduction, i.e. for Noetherian term orders +the classical one and for local term orders using tail reduction with +bounded ecart.} + +\verb|red_Straight bas|\index{red\_Straight} + +\pbx{Reduce (with {\em red\_TailRed}) the tails of the polynomials in +the base list $bas$.} + +\verb|red_TopInterreduce bas|\index{red\_TopInterreduce} + +\pbx{Reduces the base list $bas$ with $red\_TopRed$ until it +has pairwise incomparable leading terms, computes correct +representation parts, but does no tail reduction.} + +\verb|red_Interreduce bas|\index{red\_Interreduce} + +\pbx{Does top and, if {\tt on red\_total}, also tail interreduction on +the base list $bas$.} +\end{quote} + +Usually, e.g.\ for ideal generation problems, there is no need to care +about the multiplier $u$. If nevertheless one needs its value, the +base element $f$ may be prepared with \ind{red\_prepare} to collect +this information in the 0-slot of its representation part. Extract +this information with \ind{red\_extract}. +\begin{quote} +\verb|red_redpol(bas,model)|\index{red\_redpol} + +\pbx{combines this tool with a total reduction of the base element +$model$ and returns a dotted pair + +\centerline{$( . )$.}} +\end{quote} + +Advanced applications call the interfacing procedures +\begin{quote} +\verb|interreduce!* m|\index{interreduce} + +\pbx{that returns an interreduced basis of the dpmat $m$.} + +\verb|mod!*(f,m)|\index{mod} + +\pbx{that returns the dotted pair $(h.u)$ where $h$ is the pseudo +normal form of the dpoly $f$ modulo the dpmat $m$ and $u$ the +corresponding polynomial unit multiplier.} + +\verb|normalform!*(a,b)|\index{normalform} + +\pbx{that returns $\{a_1,r,z\}$ with $a_1=z*a-r*b$ where the rows of +the dpmat $a_1$ are the normalforms of the rows of the dpmat $a$ with +respect to the dpmat $b$.} +\end{quote} + +For local standard bases the ideal generated by the basic polynomials +may have components not passing through the origin. Although they do +not contribute to the ideal in $Loc(S)=S_{\bf m}$ they usually heavily +increase the necessary computational effort. Hence for local term +orders one should try to remove polynomial units as soon as they +are detected. To remove them from base elements in an early stage of +the computation one can either try the (cheap) test, whether $f\in S$ +is of the form $\langle monomial\rangle *\langle polynomial\ +unit\rangle$ or factor $f$ completely and remove polynomial unit +factors. For base elements this may be done with +\ind{bas\_detectunits} or \ind{bas\_factorunits}. + +Moreover there are two switches \ind{detectunits} and +\ind{factorunits}, both off by default, that force such automatic +simplifications during more advanced computations. + +The procedure \ind{deleteunits!*} tries explicitely to factor the +basis polynomials of a dpmat and to remove polynomial units occuring +as one of the factors. + +\subsection{The \gr and Standard Basis Algorithms} + +There is now a unique \ind{module groeb} that contains the \gr +resp. standard basis algorithms with syzygy computation facility and +related topics. There are common procedures (working for both +Noetherian and non Noetherian term orders) +\begin{quote} +\verb|gbasis!* m|\index{gbasis} + +\pbx{that returns a minimal \gr or standard basis of the dpmat $m$,} + +\verb|syzygies!* m|\index{syzygies} + +\pbx{that returns an interreduced basis of the first syzygy module of +the dpmat $m$ and} + +\verb|syzygies1!* m|\index{syzygies1} + +\pbx{that returns a (not yet interreduced) basis of the syzygy module +of the dpmat $m$.} +\end{quote} + +These procedures start the outer \gr engine (now also common for both +Noetherian and non Noetherian term orders) +\begin{quote} +\verb|groeb_stbasis(m,mgb,ch,syz)|\index{groeb\_stbasis} +\end{quote} +that returns, applied to the dpmat $m$, three dpmats $g,c,s$ with +\begin{quote} +$g$ --- the minimal reduced \gr basis of $m$ if $mgb=t$, + +$c$ --- the transition matrix $g=c\cdot m$ if $ch=t$, and + +$s$ --- the (not yet interreduced) syzygy matrix of $m$ if $syz=t$. +\end{quote} + +The next layer manages the preparation of the representation parts +of the base elements to carry the syzygy information, calls the +{\em general internal driver}, and extracts the relevant information +from the result of that computation. The general internal driver +branches according to different reduction functions into several +versions. Upto now there are three different strategies for the +reduction procedures for the S-polynomial reduction (different +versions may be chosen via \ind{gbtestversion}): +\begin{enumerate} +\item Total reduction with local simplifier lists. For local term +orders this is (almost) Mora's first version for the tangent cone (the +default). + +\item Total reduction with global simplifier list. For local term +orders this is (almost) Mora's SimpStBasis, see \cite{MPT}. + +\item Total reduction with bounded ecart. +\end{enumerate} +The first two versions (almost) coincide for Noetherian term +orders. The third version reduces only with bounded ecart, thus +forcing more pairs to be treated than necessary, but usually less +expensive to be reduced. It is not yet well understood, whether this +idea is of practical importance. + +\ind{groeb\_lazystbasis} calls the lazy standard basis driver instead, +that implements Mora's lazy algorithm, see \cite{MPT}. As +\ind{groeb\_homstbasis}, the computation of \gr and standard bases via +homogenization (Lazard's approach), it is not fully integrated into +the algebraic interface. Use +\begin{quote} +\verb|homstbasis!* m|\index{homstbasis} + +\pbx{for the invocation of the homogenization approach to compute a +standard basis of the dpmat $m$ and} + +\verb|lazystbasis!* m|\index{lazystbasis} + +\pbx{for the lazy algorithm.} +\end{quote} +Experts commonly agree that the classical approach is better for +``computable'' examples, but computations done by the author +on large examples indicate, that both approaches are in fact +independent. +\medskip + +The pair list management uses the sugar strategy, see \cite{GMNRT}, +with respect to the current ecart vector. If the input is homogeneous +and the ecart vector reflects this homogeneity then pairs are sorted +by ascending degree. Hence no superfluous base +elements will be computed in this case. In general the sugar strategy +performs best if the ecart vector is chosen to make the input close +to be homogeneous. + +There is another global variable \ind{cali!=monset} that may contain +a list of variable names (a subset of the variable names of the +current base ring). During the ``pure'' \gr algorithm (without syzygy +and representation computations) common monomial factors containing +only these variables will be canceled out. This shortcut is useful if +some of the variables are known to be non zero divisors as e.g.\ in +most implicitation problems. +\begin{quote} +\verb|setmonset!* vars|\index{setmonset} + +\pbx{initializes {\em cali!=monset} with a given list of variables +$vars$.} +\end{quote} + +The \gr tools as e.g.\ pair criteria, pair list update, pair +management and S-polynomial construction are available. +\begin{quote} +\verb|groeb_mingb m|\index{groeb\_mingb} + +\pbx{extracts a minimal \gr basis from the dpmat $m$, removing base +elements with leading terms, divisible by other leading terms.} + +\verb|groeb_minimize(bas,syz)|\index{groeb\_minimize} + +\pbx{minimizes the dpmat pair $(bas,syz)$ deleting superfluous base +elements from $bas$ using syzygies from $syz$ containing unit +entries.} +\end{quote} + +\subsection{The \gr Factorizer} + +If $\bar{k}$ is the algebraic closure of $k$, +$B:=\{f_1,\ldots,f_m\}\subset S$ a finite system of polynomials, and +$C:=\{g_1,\ldots,g_k\}$ a set of side conditions define the {\em +relative set of zeroes} +\[Z(B,C):=\{a\in \bar{k}^n : \forall\ f\in B\ f(a)=0\mbox{ and } +\forall g\in C\ g(a)\neq 0\}.\] +Its Zariski closure is the zero set of $I(B):<\prod C>$. + +The \gr factorizer solves the following problem: +\begin{quote} +\it Find a collection $(B_\alpha,C_\alpha)$ of \gr bases $B_\alpha$ +and side conditions $C_\alpha$ such that +\[Z(B,C) = \bigcup_\alpha Z(B_\alpha,C_\alpha).\] +\end{quote} +The \ind{module groebf} and the \ind{module triang} contain algorithms +related to that problem, triangular systems, and their generalizations +as described in \cite{fgb} and \cite{efgb}. V. 2.2 thus heavily +extends the algorithmic possibilities that were implemented in former +releases of CALI. + +Note that, different to v.\ 2.1, we work with constraint {\em lists}. +\begin{quote} +\verb|groebfactor!*(bas,con)|\index{groebfactor} + +\pbx{returns for the dpmat ideal $bas$ and the constraint list $con$ +(of dpolys) a minimal list of $(dpmat, constraint\ list)$ pairs with +the desired property.} +\end{quote} +During a preprocessing it splits the submitted basis $bas$ by a +recursive factorization of polynomials and interreduction of bases +into a (reduced) list of smaller subproblems consisting of a partly +computed \gr basis, a constraint list, and a list of pairs not yet +processed. The main procedure forces the next subproblem to be +processed until another factorization is possible. Then the +subproblem splits into subsubproblems, and the subproblem list will +be updated. Subproblems are kept sorted with respect to their +expected dimension \ind{easydim} forcing this way a {\em depth first} +recursion. Returned and not yet interreduced \gr bases are, after +interreduction, subject to another call of the preprocessor since +interreduced polynomials may factor anew. +\begin{quote} +\verb|listgroebfactor!* l|\index{listgroebfactor} + +\pbx{proceeds a whole list of dpmats (without constraints) at once and +strips off constraints at the end.} +\end{quote} +\medskip + +Using the (ordinary) \gr factorizer even components of different +dimension may keep gluing together. The \ind{extended \gr factorizer} +involves a postprocessing, that guarantees a decomposition into +puredimensional components, given by triangular systems instead of \gr +bases. Triangular systems in positive dimension must not be \gr bases +of the underlying ideal. They should be preferred, since they are more +simple but contain all information about the (quasi) prime component +that they represent. The complete \gr basis of the corresponding +component can be obtained by an easy stable quotient computation, see +\cite{efgb}. We refer to the same paper for the definition of +\ind{triangular systems} in positive dimension, that is consistent +with our approach. +\begin{quote} +\verb|extendedgroebfactor!*(bas,c)| and +\verb|extendedgroebfactor1!*(bas,c)| +\index{extendedgroebfactor} \index{extendedgroebfactor1} + +\pbx{return a list of results $\{b_i,c_i,v_i\}$ in algebraic prefix +form such that $b_i$ is a triangular set wrt.\ the variables $v_i$ and +$c_i$ is a list of constraints, such that $b_i:<\prod c_i>$ is the +(puredimensional) recontraction of the zerodimensional ideal +$b_i\bigotimes_k k(v_i)$. For the first version the recontraction is +not computed, hence the output may be not minimal. The second version +computes recontractions to decide superfluous components already +during the algorithm. Note that the stable quotient computation +involved for that purpose may drastically slow down the whole +attempt.} +\end{quote} +The postprocessing involves a change to dimension zero and invokes +(zero dimensional) triangular system computations from the +\ind{module triang}. In a first step \ind{groebf\_zeroprimes1} +incorporates the square free parts of certain univariate polynomials +into these systems and strips off the constraints (since relative sets +of zeroes in dimension zero are Zariski closed), using a splitting +approach analogous to the \gr factorizer. In a second step, according +to the \ind{switch lexefgb}, either \ind{zerosolve!*} or +\ind{zerosolve1!*} converts these intermediate results into lists of +triangular systems in prefix form. If \ind{lexefgb} is {\tt off} (the +default), the zero dimensional term order is degrevlex and +\ind{zerosolve1!*}, the ``slow turn to lex'' is involved, for {\tt on +lexefgb} the pure lexicographic term order and \ind{zerosolve!*}, +M\"ollers original approach, see \cite{Moeller}, are used. Note that +for this term order we need only a single \gr basis computation at +this level. + +A third version, \ind{zerosolve2!*}, mixes the first approach with the +FGLM change of term orders. It is not incorporated into the extended +\gr factorizer. + +\subsection{Basic Operations on Ideals and Modules} + +\gr and local standard bases are the heart of several basic +algorithms in ideal theory, see e.g.\ \cite[6.2.]{BKW}. CALI offers +the following facilities: +\begin{quote} +\verb|submodulep!*(m,n)|\index{submodulep} + +\pbx{tests the dpmat $m$ for being a submodule of the dpmat $n$ +reducing the basis elements of $m$ with respect to $n$. The result +will be correct provided $n$ is a \gr basis.} + +\verb|modequalp!*(m,n)|\index{modequalp} + +\pbx{ = submodulep!*(m,n) and submodulep!*(n,m).} + +\verb|eliminate!*(m,)| \index{eliminate} + +\pbx{computes the elimination ideal/module eliminating the variables +in the given variable list (a subset of the variables of the current +base ring). Changes temporarily the term order to degrevlex.} + +\verb|matintersect!* l|\index{matintersect} +\footnote{This can be done for ideals and +modules in an unique way. Hence {\em idealintersect!*} has been +removed in v.\ 2.1.} + +\pbx{computes the intersection of the dpmats in the dpmat list $l$ +along \cite[6.20]{BKW}.} +\end{quote} + +CALI offers several quotient algorithms. They rest on the computation +of quotients by a single element of the following kind: Assume +$M\subset S^c, v\in S^c, f\in S$. Then there are +\begin{quote} +the \ind{module quotient} $M : (v) = \{g\in S\ |\ gv\in M\}$, + +the \ind{ideal quotient} $M : (f) = \{w\in S^c\ |\ fw\in M\}$, and + +the \ind{stable quotient} $M : (f)^\infty = \{w\in S^c\ |\ \exists\, +n\, :\, f^nw\in M\}$. +\end{quote} +CALI uses the elimination approach \cite[4.4.]{CLO} and +\cite[6.38]{BKW} for their computation: +\begin{quote} +\verb|matquot!*(M,f)|\index{matquot} + +\pbx{returns the module or ideal quotient $M:(f)$ depending on $f$.} + +\verb|matqquot!*(M,f)|\index{matqquot} + +\pbx{returns the stable quotient $M:(f)^\infty$.} +\end{quote} +\ind{matquot!*} calls the pseudo division with remainder +\begin{quote} +\verb|dp_pseudodivmod(g,f)|\index{dp\_pseudodivmod} + +\pbx{that returns a dpoly list $\{q,r,z\}$ such that $z\cdot g = +q\cdot f + r$ with a dpoly unit $z$.\ ($g, f$ and $r$ must belong to +the same free module). This is done uniformly for noetherian and +local term orders with an extended normal form algorithm as described +in \cite{ala}.} +\end{quote} +\medskip + +In the same way one defines the quotient of a module by another +module (both embedded in a common free module $S^c$), the quotient of +a module by an ideal, and the stable quotient of a module by an +ideal. Algorithms for their computation can be obtained from the +corresponding algorithms for a single element as divisor either by +the generic element method \cite{E} or as an intersection +\cite[6.31]{BKW}. CALI offers both approaches (X=1 or 2 below) at +the symbolic level, but for true quotients only the latter one is +integrated into the algebraic mode interface. +\begin{quote} +\verb|idealquotientX!*(M,I)|\index{idealquotient} + +\pbx{returns the ideal quotient $M:I$ of the dpmat $M$ by the dpmat +ideal $I$.} + +\verb|modulequotientX!*(M,N)|\index{modulequotient} + +\pbx{returns the module quotient $M:N$ of the dpmat $M$ by the dpmat +$N$.} + +\verb|annihilatorX!* M|\index{annihilator} + +\pbx{returns the annihilator of $coker\ M$, i.e.\ the module quotient +$S^c:M$, if $M$ is a submodule of $S^c$.} + +\verb|matstabquot!*(M,I)|\index{matstabquot} + +\pbx{returns the stable quotient $M:I^\infty$ (only by the general element +method).} +\end{quote} + + +\subsection{Monomial Ideals} + +Monomial ideals occur as ideals of leading terms of (ideal's) \gr +bases and also as components of leading term modules of submodules of +free modules, see \cite{rois}, and reflect some properties of the +original ideal/module. Several parameters of the original ideal or +module may be read off from it as e.g.\ dimension and Hilbert series. + +The \ind{module moid} contains the corresponding algorithms on +monomial ideals. Monomial ideals are lists of monomials, kept sorted +by descending lexicographic order as proposed in \cite{BS}. + +\begin{quote} +\verb|moid_primes u| \index{moid\_primes} + +\pbx{returns the minimal primes (as a list of lists of variable +names) of the monomial ideal $u$ using an adaption of the algorithm, +proposed in \cite{BS} for the computation of the codimension.} + +\verb|indepvarsets!* m| \index{indepvarsets} + +\pbx{returns (based on {\em moid\_primes}) the list of strongly +independent sets of $m$, see \cite{KW} and \cite{rois} for +definitions.} + +\verb|dim!* m| \index{dim} + +\pbx{returns the dimension of $coker\ m$ as the size of the largest +independent set.} + +\verb|codim!* m| \index{codim} + +\pbx{returns the codimension of $coker\ m$.} + +\verb|easyindepset!* m| \index{easyindepset} + +\pbx{returns a maximal with respect to inclusion independent set of +$m$.} + +\verb|easydim!* m| \index{easydim} + +\pbx{is a fast dimension algorithm (based on {\em easyindepset}), that +will be correct if $m$ is (radically) unmixed. Since it is +significantly faster than the general dimension +algorithm\footnotemark, it should +be used, if all maximal independent sets are known to be of equal +cardinality (as e.g.\ for prime or unmixed ideals, see \cite{rois}).} +\footnotetext{This algorithm is of linear time as opposed to the +problem to determine the dimension of an arbitrary monomial ideal, +that is known to be NP-hard in the number of variables, see +\cite{BS}.} +\end{quote} + +\subsection{Hilbert Series} + +CALI v. 2.2 now offers also \ind{weighted Hilbert series}, i.e.\ +series that may reflect multihomogeneity of ideals and modules. For +this purpose +a weighted Hilbert series has a list of (integer) degree vectors +as second parameter, and the ideal(s) of leading terms are evaluated +wrt.\ these weights. For the output and polynomial arithmetic, +involved during the computation of the Hilbert series numerator, the +different weight levels are mapped onto the first variables of the +current ring. If $w$ is such a weight vector list and $I$ is a +monomial ideal in the polynomial ring $S=k[x_v\,:\,v\in V]$ we get +(using multi exponent notation) +\[H(S/I,t) := \sum_{\alpha}{|\{x^a\not\in I\,:\,w(a)=\alpha\}|\cdot +t^\alpha} = \frac{Q(t)}{\prod_{v\in V}{\left(1-t^{w(x_v)}\right)} }\] +for a certain polynomial Hilbert series numerator $Q(t)$. $H(R/I,t)$ +is known to be a rational function with pole order at $t=1$ equal to +$dim\ R/I$. Note that \ind{WeightedHilbertSeries} returns a {\em +reduced} rational function where the gcd of numerator and denominator +is canceled out. + +(Non weighted) Hilbert series call the weighted Hilbert series +procedure with a single weight vector, the ecart vector of the current +ring. + +The Hilbert series numerator $Q(t)$ is computed using (the obvious +generalizations to the weighted case of) the algorithms in \cite{BS} +and \cite{BCRT}. Experiments suggest that the former is better for few +generators of high degree whereas the latter has to be preferred for +many generators of low degree. Choose the version with +\ind{hftestversion} $n$, $n=1,\,2$. Bayer/Stillman's approach ($n=1$) +is the default. In the following $m$ is a dpmat and \gr basis. + +\begin{quote} +\verb|hf_whilb(m,w)| \index{hf\_whilb} + +\pbx{returns the weighted Hilbert series numerator $Q(t)$ of $m$ +according to the version chosen with \ind{hftestversion}.} + +\verb|WeightedHilbertSeries!*(m,w)| \index{WeightedHilbertSeries} + +\pbx{returns the weighted Hilbert series reduced rational function of +$m$ as s.q.} + +\verb|HilbertSeries!*(m,w)| \index{HilbertSeries} + +\pbx{returns the Hilbert series reduced rational function of $m$ wrt.\ +the ecart vector of the current ring as s.q.} + +\verb|hf_whilb3(u,w)| and \verb|hf_whs_from_resolution(u,w)| +\index{hf\_whilb3} +\index{hf\_whs\_from\_resolution} + +\pbx{compute the weighted Hilbert series numerator and the +corresponding reduced rational function from (the column degrees of) a +given resolution $u$.} + +\verb|degree!* m| \index{degree} + +\pbx{returns the value of the numerator of the reduced Hilbert series +of $m$ at $t=1$. i.e.\ the sum of its coefficients. For the standard +ecart this is the degree of $coker\ m$.} +\end{quote} + +\subsection{Resolutions} + +Resolutions of ideals and modules, represented as lists of dpmats, are +computed via repeated syzygy computation with minimization steps +between them to get minimal bases and generators of syzygy +modules. Note that the algorithms apply simultaneously to both +Noetherian and non Noetherian term orders. For compatibility reasons +with further releases v. 2.2 introduces a second parameter to +bound the number of syzygy modules to be computed, since Hilbert's +syzygy theorem applies only to regular rings. +\begin{quote} +\verb|Resolve!*(m,d)| \index{Resolve} + +\pbx{computes a minimal resolution of the dpmat $m$, i.e. a list of +dpmats $\{s_0, s_1, s_2,\ldots\}$, where $s_k$ is the $k$-th syzygy +module of $m$, upto part $s_d$.} + +\verb|BettiNumbers!* c| and \verb|GradedBettiNumbers!* c| +\index{BettiNumbers} +\index{GradedBettiNumbers} + +\pbx{returns the Betti numbers resp.\ the graded Betti numbers of the +resolution $c$, i.e.\ the list of the lengths resp.\ the degree lists +(according to the ecart) themselves of the dpmats in $c$.} +\end{quote} + +\subsection{Zero Dimensional Ideals and Modules} + +There are several algorithms that either force the reduction of a +given problem to dimension zero or work only for zero dimensional +ideals or modules. The \ind{module odim} offers such +algorithms. It contains, e.g.\ +\begin{quote} +\verb|dimzerop!* m| \index{dimzerop} + +\pbx{that tests a dpmat $m$ for being zero dimensional.} + +\verb|getkbase!* m| \index{getkbase} + +\pbx{that returns a (monomial) k-vector space basis of $Coker\ m$ +provided $m$ is a \gr basis.} + +\verb|odim_borderbasis m| \index{odim\_borderbasis} + +\pbx{that returns a border basis, see \cite{MMM}, of the +zero dimensional dpmat $m$ as a list of base elements.} + +\verb|odim_parameter m| \index{odim\_parameter} + +\pbx{that returns a parameter of the dpmat $m$, i.e.\ a variable $x +\in vars$ such that $k[x]\bigcap Ann\ S^c/m=(0)$, or {\em nil} if $m$ +is zero dimensional.} + +\verb|odim_up(a,m)| \index{odim\_up} + +\pbx{that returns an univariate polynomial (of smallest possible +degree if $m$ is a gbasis) in the variable $a$, that belongs to the +zero dimensional dpmat ideal $m$, using Buchberger's approach +\cite{B1}.} +\end{quote} + +\subsection{Primary Decomposition and Related Algorithms} + +The algorithms of the \ind{module prime} implement the ideas of +\cite{GTZ} with modifications along \cite{Kr} and their natural +generalizations to modules as e.g.\ explained in \cite{Ru}. Version +2.2.1 fixes a serious bug detecting superfluous embedded primary +components, see section \ref{221}, and contains now a second primary +decomposition algorithm, based on ideal separation, as standard. For a +discussion about embedded primes and the ideal separation approach, +see \cite{primary}. + + +CALI contains also algorithms for the computation of the unmixed part +of a given module and the unmixed radical of a given ideal (along the +same lines). We followed the stepwise recursion decreasing dimension +in each step by 1 as proposed in (the final version of) \cite{GTZ} +rather than the ``one step'' method described in \cite{BKW} since +handling leading coefficients, i.e.\ standard forms, depending on +several variables is a quite hard job for +REDUCE\footnote{\ind{prime!=decompose2} implements this strategy in +the symbolic mode layer.}. + +In the following procedures $m$ must be a \gr basis. +\begin{quote} +\verb|zeroradical!* m| \index{zeroradical} + +\pbx{returns the radical of the zero dimensional ideal $m$, using +squarefree decomposition of univariate polynomials.} + +\verb|zeroprimes!* m| \index{zeroprimes} + +\pbx{computes as in \cite{GTZ} the list of prime ideals of $Ann\ F/M$ +if $m$ is zero dimensional, using the (sparse) general position +argument from \cite{KW}.} + +\verb|zeroprimarydecomposition!* m| \index{zeroprimarydecomposition} + +\pbx{computes the primary components of the zero dimensional dpmat $m$ +using prime splitting with the prime ideals of $Ann\ F/M$. It returns +a list of pairs with first entry the primary component +and second entry the corresponding associated prime ideal.} + +\verb|isprime!* m| \index{isprime} + +\pbx{a (one step) primality test for ideals, extracted from +\cite{GTZ}.} + +\verb|isolatedprimes!* m| \index{isolatedprimes} + +\pbx{computes (only) the isolated prime ideals of $Ann\ F/M$.} + +\verb|radical!* m| \index{radical} + +\pbx{computes the radical of the dpmat ideal $m$, reducing as in +\cite{GTZ} to the zero dimensional case.} + +\verb|easyprimarydecomposition!* m| \index{easyprimarydecomposition} + +\pbx{computes the primary components of the dpmat $m$, if it has no +embedded components. The algorithm uses prime splitting with the +isolated prime ideals of $Ann\ F/M$. It returns a list of pairs as in +{\em zeroprimarydecomposition!*}.} + +\verb|primarydecomposition!* m| \index{primarydecomposition} + +\pbx{computes the primary components of the dpmat $m$ along the lines +of \cite{GTZ}. It returns a list of two-element lists as in {\em +zeroprimarydecomposition!*}.} + +\verb|unmixedradical!* m| \index{unmixedradical} + +\pbx{returns the unmixed radical, i.e.\ the intersection of the +isolated primes of top dimension, associated to the dpmat ideal $m$.} + +\verb|eqhull!* m| \index{eqhull} + +\pbx{returns the equidimensional hull, i.e.\ the intersection of the + top dimensional primary components of the dpmat $m$.} +\end{quote} + +\subsection{Advanced Algorithms} + +The \ind{module scripts} just under further development offers some +advanced topics of the \gr bases theory. It introduces the new data +structure of a \ind{map} between base rings: +\medskip + +A ring map +\[ \phi\ :\ R\longrightarrow S\] +for $R=k[r_i], S=k[s_j]$ is represented in symbolic mode as a list +\[ \{preimage\_ring\ R,\ image\_ring\ S, subst\_list\},\] +where {\tt subst\_list} is a substitution list $\{r_1=\phi_1(s), +r_2=\phi_2(s),\ldots \}$ in algebraic prefix form, i.e.\ looks like +{\tt (list (equal var image) \ldots )}. + +The central tool for several applications is the computation of the +preimage $\phi^{-1}(I)\subset R$ of an ideal $I\subset S$ either +under a polynomial map $\phi$ or its closure in $R$ under a rational +map $\phi$, see \cite[7.69 and 7.71]{BKW}. +\begin{quote} +\verb|preimage!*(m,map)| \index{preimage} + +\pbx{computes the preimage of the ideal $m$ in algebraic prefix form +under the given polynomial map and sets the current base ring to the +preimage ring. Returns the result also in algebraic prefix form.} + +\verb|ratpreimage!*(m,map)| \index{ratpreimage} + +\pbx{computes the closure of the preimage of the ideal $m$ in +algebraic prefix form under the given rational map and sets the +current base ring to the preimage ring. Returns the result also in +algebraic prefix form.} + +\end{quote} + +Derived applications are +\begin{quote} +\verb|affine_monomial_curve!*(l,vars)|\index{affine\_monomial\_curve} + +\pbx{$l$ is a list of integers, $vars$ a list of variable names of the +same length as $l$. The procedure sets the current base ring and +returns the defining ideal of the affine monomial curve with generic +point $(t^i\ :\ i\in l)$ computing the corresponding preimage.} + +\verb|analytic_spread!* M|\index{analytic\_spread} + +\pbx{Computes the analytic spread of $M$, i.e.\ the dimension of the +exceptional fiber ${\cal R}(M)/m{\cal R}(M)$ of the blowup along $M$ +over the irrelevant ideal $m$ of the current base ring.} + +\verb|assgrad!*(M,N,vars)|\index{assgrad} + +\pbx{Computes the associated graded ring \[gr_R(N):= +(R/N\oplus N/N^2\oplus\ldots)={\cal R}(N)/N{\cal R}(N)\] over the ring +$R=S/M$, where $M$ and +$N$ are dpmat ideals defined over the current base ring $S$. {\tt +vars} is a list of new variable names one for each generator of $N$. +They are used to create a second ring $T$ with degree order +corresponding to the ecart of the row degrees of $N$ and a ring map +\[\phi : S\oplus T\longrightarrow S.\] +It returns a dpmat ideal $J$ such that $(S\oplus T)/J$ is a +presentation of the +desired associated graded ring over the new current base ring +$S\oplus T$.} + +\verb|blowup!*(M,N,vars)|\index{blowup} + +\pbx{Computes the blow up ${\cal R}(N):=R[N\cdot t]$ of $N$ over +the ring $R=S/M$, where $M$ and $N$ are dpmat ideals defined over the +current base ring $S$. {\tt vars} is a list of new variable names one +for each generator of $N$. They are used to create a second ring $T$ +with degree order corresponding to the ecart of the row degrees of +$N$ and a ring map +\[\phi : S\oplus T\longrightarrow S.\] +It returns a dpmat ideal $J$ such that $(S\oplus T)/J$ is +a presentation of the +desired blowup ring over the new current base ring $S\oplus T$.} + +\verb|proj_monomial_curve!*(l,vars)|\index{proj\_monomial\_curve} + +\pbx{$l$ is a list of integers, $vars$ a list of variable names of the +same length as $l$. The procedure set the current base ring and +returns the defining ideal of the projective monomial curve with +generic point \mbox{$(s^{d-i}\cdot t^i\ :\ i\in l)$} in $R$, where +\mbox{$d=max\{ x\, :\, x\in l\}$}, computing the corresponding preimage.} + +\verb|sym!*(M,vars)|\index{sym} + +\pbx{Computes the symmetric algebra $Sym(M)$ where $M$ is a dpmat ideal +defined over the current base ring $S$. {\tt vars} is a list of new +variable names one for each generator of $M$. They are used to create +a second ring $R$ with degree order corresponding to the ecart of the +row degrees of $N$ and a ring map +\[\phi : S\oplus R\longrightarrow S.\] +It returns a dpmat ideal $J$ such that $(S\oplus R)/J$ is the +desired symmetric algebra over the new current base ring $S\oplus R$.} + +\end{quote} + + +There are several other applications: +\begin{quote} +\verb|minimal_generators!* m| \index{minimal\_generators} + +\pbx{returns a set of minimal generators of the dpmat $m$ inspecting +the first syzygy module.} + +\verb|nzdp!*(f,m)| \index{nzdp} + +\pbx{tests whether the dpoly $f$ is a non zero divisor on $coker\ +m$. $m$ must be a \gr basis.} + +\verb|symbolic_power!*(m,d)| \index{symbolic\_power} + +\pbx{returns the $d$\/th symbolic power of the prime dpmat ideal $m$ as +the equidimensional hull of the $d$\/th true power. (Hence applies also +to unmixed ideals.)} + +\verb|varopt!* m| \index{varopt} + +\pbx{finds a heuristically optimal variable order by the approach in +\cite{BGK} and returns the corresponding list of variables.} +\end{quote} + + +\subsection{Dual Bases} + + +For the general ideas underlying the dual bases approach see e.g.\ +\cite{MMM}. This paper explains, that constructive problems from very +different areas of commutative algebra can be formulated in a unified +way as the computation of a basis for the intersection of the kernels +of a finite number of linear functionals generating a dual +$S$-module. Our implementation honours +this point of view, presenting two general drivers \ind{dualbases} and +\ind{dualhbases} for the computation of such bases (even as submodules +of a free module $M=S^m$) with affine resp.\ projective dimension zero. + +Such a collection of $N$ linear functionals +\[L\,:\, M=S^m \longrightarrow k^N\] +should be given through values $\{[e_i,L(e_i)], i=1,\ldots,m\}$ on the +generators $e_i$ of $M$ and an evaluation function {\tt +evlf([p,L(p)],x)}, that evaluates $L(p\cdot x)$ from $L(p)$ for $p\in +M$ and the variable $x\in S$. + +\ind{dualbases} starts with a list of such generator/value constructs +generating $M$ and performs Gaussian reduction on expressions $[p\cdot +x,L(p\cdot x)]$, where $p$ was already processed, $L(p)\neq 0$, and +$x\in S$ is a variable. These elements are processed in ascending order +wrt.\ the term order on $M$. This guarantees both termination and that +the resulting basis of $ker\ L$ is a \gr basis. The $N$ values of $L$ +are attached to $N$ variables, that are ordered linearly. Gaussian +elimination is executed wrt.\ this variable order. + +To initialize the dual bases driver one has to supply the basic +generator/value list (through the parameter list; for ideals just the +one element list containing the generator $[1\in S,L(1)]$), the +evaluation function, and the linear algebra variable order. The latter +are supplied via the property list of {\tt cali} as properties {\tt +evlf} and {\tt varlessp}. Different applications need more entries +on the property list of {\tt cali} to manage the communication between +the driver and the calling routine. + +\ind{dualhbases} realizes the same idea for (homogeneous) ideals and +modules of (projective) dimension zero. It produces zerodimensional +``slices'' with ascending degree until it reaches a supremum supplied +by the user, see \cite{MMM} for details. +\medskip + +Applications concern affine and projective defining ideals of a finite +number of points\footnote{This substitutes the ``brute force'' method +computing the corresponding intersections directly as it was +implemented in v. 2.1. The new approach is significantly faster. The +old stuff is available as \ind{affine\_points1!*} and +\ind{proj\_points1!*}.} and two versions (with and without precomputed +border basis) of term order +changes for zerodimensional ideals and modules as first described in +\cite{FGLM}. +\begin{quote} +\verb|affine_points!* m| \index{affine\_points} + +\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) +with as many columns as the current base ring has ring variables. This +procedure returns the defining ideal of the collection of points in +affine space with coordinates given by the rows of $m$. Note that $m$ +may contain parameters. In this case $k$ is treated as rational +function field.} + +\verb|change_termorder!*(m,r)| and \verb|change_termorder1!*(m,r)| +\index{change\_termorder} +\index{change\_termorder1} + +\pbx{$m$ is a \gr basis of a zero dimensional ideal wrt.\ the current +base ring. These procedures change the current ring to $r$ and compute +the \gr basis of $m$ wrt.\ the new ring $r$. The former uses a +precomputed border basis.} + +\verb|proj_points!* m| \index{proj\_points} + +\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) +with as many columns as the current base ring has ring variables. This +procedure returns the defining ideal of the collection of points in +projective space with homogeneous coordinates given by the rows of +$m$. Note that $m$ may as for {\tt affine\_points} contain +parameters.} +\end{quote} + +\pagebreak + +\appendix +\section{A Short Description of Procedures Available in Algebraic +Mode} + +Here we give a short description, ordered alphabetically, of {\bf +algebraic} procedures offered by CALI in the algebraic mode +interface\footnote{It does {\bf not} contain switches, get\ldots\ +procedures, setting trace level and related stuff.}. + +If not stated explicitely procedures take (algebraic mode) polynomial +matrices ($c>0$) or polynomial lists ($c=0$) $m,m1,m2,\ldots\ $ as +input and return results of the same type. $gb$ stands for a bounded +identifier\footnote{Different to v. 2.1 a \gr basis will be computed +automatically, if necessary.}, $gbr$ for one with precomputed +resolution. For the mechanism of \ind{bounded identifier} see the +section ``Algebraic Mode Interface''. + +\begin{quote} +\verb|affine_monomial_curve(l,vars)|\index{affine\_monomial\_curve} + +\pbx{$l$ is a list of integers, $vars$ a list of variable names of the +same length as $l$. The procedure sets the current base ring and +returns the defining ideal of the affine monomial curve with generic +point $(t^i\ :\ i\in l)$.} + +\verb|affine_points m| \index{affine\_points} + +\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) +with as many columns as the current base ring has ring variables. This +procedure returns the defining ideal of the collection of points in +affine space with coordinates given by the rows of $m$. Note that $m$ +may contain parameters. In this case $k$ is treated as rational +function field.} + +\verb|analytic_spread m|\index{analytic\_spread} + +\pbx{Computes the analytic spread of $m$.} + +\verb|annihilator m| \index{annihilator} + +\pbx{returns the annihilator of the dpmat $m\subseteq S^c$, i.e.\ +$Ann\ S^c/M$.} + +\verb|assgrad(M,N,vars)|\index{assgrad} + +\pbx{Computes the associated graded ring $gr_R(N)$ over $R=S/M$, where +$S$ is the current +base ring. {\tt vars} is a list of new variable names, one for +each generator of $N$. They are used to create a second ring $T$ +to return an ideal $J$ such that $(S\oplus T)/J$ is the desired +associated graded ring over the new current base ring $S\oplus T$.} + +\verb|bettiNumbers gbr| \index{bettiNumbers} + +\pbx{extracts the list of Betti numbers from the resolution of $gbr$.} + +\verb|blowup(M,N,vars)|\index{blowup} + +\pbx{Computes the blow up ${\cal R}(N)$ of $N$ over the ring $R=S/M$, +where $S$ is the current base ring. {\tt vars} is a list of new +variable names, one for each generator of $N$. They are used to create +a second ring $T$ to return an ideal $J$ such that $(S\oplus T)/J$ is +the desired blowup ring over the new current base ring $S\oplus T$.} + +\verb|change_termorder(m,r)| and \verb|change_termorder1(m,r)| +\index{change\_termorder} +\index{change\_termorder1} + +\pbx{Change the current ring to $r$ and compute the \gr basis of $m$ +wrt.\ the new ring $r$ by the FGLM approach. The former uses +internally a precomputed border basis.} + +\verb|codim gb| \index{codim} + +\pbx{returns the codimension of $S^c/gb$.} + +\verb|degree gb| \index{degree} + +\pbx{returns the multiplicity of $gb$ as the sum of the coefficients +of the (classical) Hilbert series numerator.} + +\verb|degsfromresolution gbr| \index{degsfromresolution} + +\pbx{returns the list of column degrees from the minimal resolution +of $gbr$.} + +\verb|deleteunits m| \index{deleteunits} + +\pbx{factors each basis element of the dpmat ideal $m$ and removes +factors that are polynomial units. Applies only to non Noetherian +term orders.} + +\verb|dim gb| \index{dim} + +\pbx{returns the dimension of $S^c/gb$.} + +\verb|dimzerop gb| \index{dimzerop} + +\pbx{tests whether $S^c/gb$ is zerodimensional.} + +\verb|directsum(m1,m2,...)| \index{directsum} + +\pbx{returns the direct sum of the modules $m1,m2,\ldots$, embedded +into the direct sum of the corresponding free modules.} + +\verb|dpgcd(f,g)| \index{dpgcd} + +\pbx{returns the gcd of two polynomials $f$ and $g$, computed by the +syzygy method.} + +\verb|easydim m| and \verb|easyindepset m| +\index{easydim}\index{easyindepset} + +\pbx{ If the given ideal or module is unmixed (e.g.\ prime) then all +maximal strongly independent sets are of equal size and one can look +for a maximal with respect to inclusion rather than size strongly +independent set. These procedures don't test the input for being a +\gr basis or unmixed, but construct a maximal with respect to +inclusion independent set of the basic leading terms resp.\ detect +from this (an approximation for) the dimension.} + +\verb|easyprimarydecomposition m| \index{easyprimarydecomposition} + +\pbx{a short primary decomposition using ideal separation of isolated +primes of $m$, that yields true results only for modules without +embedded components. Returns a list of $\{component, associated\ +prime\}$ pairs.} + +\verb|eliminate(m,)| \index{eliminate} + +\pbx{computes the elimination ideal/module eliminating the variables +in the given variable list (a subset of the variables of the current +base ring). Changes temporarily the term order to degrevlex.} + +\verb|eqhull m| \index{eqhull} + +\pbx{returns the equidimensional hull of the dpmat $m$.} + +\verb|extendedgroebfactor(m,c)| and \verb|extendedgroebfactor1(m,c)| +\index{extendedgroebfactor} \index{extendedgroebfactor1} + +\pbx{return for a polynomial ideal $m$ and a list of (polynomial) +constraints $c$ a list of results $\{b_i,c_i,v_i\}$, where $b_i$ is a +triangular set wrt.\ the variables $v_i$ and $c_i$ is a list of +constraints, such that +$Z(m,c) = \bigcup Z(b_i,c_i)$. For the first version the output may be +not minimal. The second version decides superfluous components already +during the algorithm.} + +\verb|gbasis gb| \index{gbasis} + +\pbx{returns the \gr resp. local standard basis of $gb$.} + +\verb|getkbase gb| \index{getkbase} + +\pbx{returns a k-vector space basis of $S^c/gb$, consisting of module +terms, provided $gb$ is zerodimensional.} + +\verb|getleadterms gb| \index{getleadterms} + +\pbx{returns the dpmat of leading terms of a \gr resp. local standard +basis of $gb$.} + +\verb|GradedBettinumbers gbr| \index{GradedBettinumbers} + +\pbx{extracts the list of degree lists of the free summands in a +minimal resolution of $gbr$.} + +\verb|groebfactor(m[,c])|\index{groebfactor} + +\pbx{returns for the dpmat ideal $m$ and an optional constraint list +$c$ a (reduced) list of dpmats such that the union of their zeroes is +exactly $Z(m,c)$. Factors all polynomials involved in the \gr +algorithms of the partial results.} + +\verb|HilbertSeries gb| \index{HilbertSeries} + +\pbx{returns the Hilbert series of $gb$ with respect to the current +ecart vector.} + +\verb|homstbasis m| \index{homstbasis} + +\pbx{computes the standard basis of $m$ by Lazard's homogenization +approach.} + +\verb|ideal2mat m| \index{ideal2mat} + +\pbx{converts the ideal (=list of polynomials) $m$ into a column +vector.} + +\verb|ideal_of_minors(mat,k)| \index{ideal\_of\_minors} + +\pbx{computes the generators for the ideal of $k$-minors of the matrix +$mat$.} + +\verb|ideal_of_pfaffians(mat,k)| \index{ideal\_of\_pfaffians} + +\pbx{computes the generators for the ideal of the $2k$-pfaffians of +the skewsymmetric matrix $mat$.} + +\verb|idealpower(m,n)| \index{idealpower} + +\pbx{returns the interreduced basis of the ideal power $m^n$ with +respect to the integer $n\geq 0$.} + +\verb|idealprod(m1,m2,...)| \index{idealprod} + +\pbx{returns the interreduced basis of the ideal product +\mbox{$m1\cdot m2\cdot \ldots$} of the ideals $m1,m2,\ldots$.} + +\verb|idealquotient(m1,m2)| \index{idealquotient} + +\pbx{returns the ideal quotient $m1:m2$ of the module $m1\subseteq +S^c$ by the ideal $m2$.} + +\verb|idealsum(m1,m2,...)| \index{idealsum} + +\pbx{returns the interreduced basis of the ideal sum $m1+m2+\ldots$.} + +\verb|indepvarsets gb| \index{indepvarsets} + +\pbx{returns the list of strongly independent sets of $gb$ with +respect to the current term order, see \cite{KW} for a definition in +the case of ideals and \cite{rois} for submodules of free modules.} + +\verb|initmat(m,| \index{initmat} + +\pbx{initializes the dpmat $m$ together with its base ring, term order +and column degrees from a file.} + +\verb|interreduce m| \index{interreduce} + +\pbx{returns the interreduced module basis given by the rows of $m$, +i.e.\ a basis with pairwise indivisible leading terms.} + +\verb|isolatedprimes m| \index{isolatedprimes} + +\pbx{returns the list of isolated primes of the dpmat $m$, i.e.\ the +isolated primes of $Ann\ S^c/M$.} + +\verb|isprime gb| \index{isprime} + +\pbx{tests the ideal $gb$ to be prime.} + +\verb|iszeroradical gb| \index{iszeroradical} + +\pbx{tests the zerodimensional ideal $gb$ to be radical.} + +\verb|lazystbasis m| \index{lazystbasis} + +\pbx{computes the standard basis of $m$ by the lazy algorithm, see +e.g.\ \cite{MPT}.} + +\verb|listgroebfactor in| \index{listgroebfactor} + +\pbx{computes for the list $in$ of ideal bases a list $out$ of \gr +bases by the \gr factorization method, such that +$\bigcup_{m\in in}Z(m) = \bigcup_{m\in out}Z(m)$.} + +\verb|mat2list m| \index{mat2list} + +\pbx{converts the matrix $m$ into a list of its entries.} + +\verb|matappend(m1,m2,...)| \index{matappend} + +\pbx{collects the rows of the dpmats $m1,m2,\ldots $ to a common +matrix. $m1,m2,\ldots$ must be submodules of the same free module, +i.e.\ have equal column degrees (and size).} + +\verb|mathomogenize(m,var)| \index{mathomogenize} +\footnote{Dehomogenize with {\tt sub(z=1,m)} if $z$ is the +homogenizing variable.} + +\pbx{returns the result obtained by homogenization of the rows of m +with respect to the variable {\tt var} and the current \ind{ecart +vector}.} + +\verb|matintersect(m1,m2,...)| \index{matintersect} + +\pbx{returns the interreduced basis of the intersection $m1\bigcap +m2\bigcap \ldots$.} + +\verb|matjac(m,)| \index{matjac} + +\pbx{returns the Jacobian matrix of the ideal m with respect to the +supplied variable list} + +\verb|matqquot(m,f)| \index{matqquot} + +\pbx{returns the stable quotient $m:(f)^\infty$ of the dpmat $m$ by +the polynomial $f\in S$.} + +\verb|matquot(m,f)| \index{matquot} + +\pbx{returns the quotient $m:(f)$ of the dpmat $m$ by the polynomial +$f\in S$.} + +\verb|matstabquot(m1,id)| \index{matstabquot} + +\pbx{returns the stable quotient $m1:id^\infty$ of the dpmat $m1$ by +the ideal $id$.} + +\verb|matsum(m1,m2,...)| \index{matsum} + +\pbx{returns the interreduced basis of the module sum $m1+m2+\ldots$ +in a common free module.} + +\verb|minimal_generators m| \index{minimal\_generators} + +\pbx{returns a set of minimal generators of the dpmat $m$.} + +\verb|minors(m,b)| \index{minors} + +\pbx{returns the matrix of minors of size $b\times b$ of the matrix +$m$.} + +\verb|a mod m| \index{mod} + +\pbx{computes the (true) normal form(s), i.e.\ a standard quotient +representation, of $a$ modulo the dpmat $m$. $a$ may be either a +polynomial or a polynomial list ($c=0$) or a matrix ($c>0$) of the +correct number of columns.} + +\verb|modequalp(gb1,gb2)| \index{modequalp} + +\pbx{tests, whether $gb1$ and $gb2$ are equal (returns YES or NO).} + +\verb|modulequotient(m1,m2)| \index{modulequotient} + +\pbx{returns the module quotient $m1:m2$ of two dpmats $m1,m2$ in a +common free module.} + +\verb|normalform(m1,m2)| \index{normalform} + +\pbx{returns a list of three dpmats $\{m3,r,z\}$, where $m3$ is the +normalform of $m1$ modulo $m2$, $z$ a scalar matrix of polynomial +units (i.e.\ polynomials of degree 0 in the noetherian case and +polynomials with leading term of degree 0 in the tangent cone case), +and $r$ the relation matrix, such that \[m3=z*m1+r*m2.\]} + +\verb|nzdp(f,m)| \index{nzdp} + +\pbx{tests whether the dpoly $f$ is a non zero divisor on $coker\ +m$.} + +\verb|pfaffian mat| \index{pfaffian} + +\pbx{returns the pfaffian of a skewsymmetric matrix $mat$.} + +\verb|preimage(m,map)| \index{preimage} + +\pbx{computes the preimage of the ideal $m$ under the given +polynomial map and sets the current base ring to the preimage ring.} + +\verb|primarydecomposition m| +\index{primarydecomposition} + +\pbx{returns the primary decomposition of the dpmat $m$ as a list of +$\{component, associated\ prime\}$ pairs.} + +\verb|proj_monomial_curve(l,vars)|\index{proj\_monomial\_curve} + +\pbx{$l$ is a list of integers, $vars$ a list of variable names of the +same length as $l$. The procedure sets the current base ring and +returns the defining ideal of the projective monomial curve with +generic point \mbox{$(s^{d-i}\cdot t^i\ :\ i\in l)$} in $R$ where $d=max\{ +x\, :\, x\in l\}$.} + +\verb|proj_points m| \index{proj\_points} + +\pbx{$m$ is a matrix of domain elements (in algebraic prefix form) +with as many columns as the current base ring has ring variables. This +procedure returns the defining ideal of the collection of points in +projective space with homogeneous coordinates given by the rows of +$m$. Note that $m$ may as for {\tt affine\_points} contain +parameters.} + +\verb|radical m| \index{radical} + +\pbx{returns the radical of the dpmat ideal $m$.} + +\verb|random_linear_form(vars,bound)| \index{random\_linear\_form} + +\pbx{returns a random linear form in the variables {\tt vars} with integer +coefficients less than the supplied {\tt bound}.} + +\verb|ratpreimage(m,map)| \index{ratpreimage} + +\pbx{computes the closure of the preimage of the ideal $m$ under the +given rational map and sets the current base ring to the preimage +ring.} + +\verb|resolve(m[,d])| \index{resolve} + +\pbx{returns the first $d$ members of the minimal resolution of the +bounded identifier $m$ as a list of matrices. If the resolution has +less than $d$ non zero members, only those are collected. (Default: +$d=100$)} + +\verb|savemat(m,)| \index{savemat} + +\pbx{save the dpmat $m$ together with the settings of it base ring, +term order and column degrees to a file.} + +\verb|setgbasis m| \index{setgbasis} + +\pbx{declares the rows of the bounded identifier $m$ to be already a +\gr resp. local standard basis thus avoiding a possibly time +consuming \gr or standard basis computation.} + +\verb|sieve(m,)| \index{sieve} + +\pbx{sieves out all base elements with leading terms having a factor +contained in the specified variable list (a subset of the variables +of the current base ring). Useful for elimination problems solved +``by hand''.} + +\verb|singular_locus(M,c)| \index{singular\_locus} + +\pbx{returns the defining ideal of the singular locus of $Spec\ S/M$ +where $M$ is an ideal of codimension $c$, adding to $M$ the generators +of the ideal of the $c$-minors of the Jacobian of $M$.} + +\verb|submodulep(m,gb)| \index{submodulep} + +\pbx{tests, whether $m$ is a submodule of $gb$ (returns YES or NO).} + +\verb|sym(M,vars)|\index{sym} + +\pbx{Computes the symmetric algebra $Sym(M)$ where $M$ is an ideal +defined over the current base ring $S$. {\tt vars} is a list of new +variable names, one for each generator of $M$. They are used to create +a second ring $R$ to return an ideal $J$ such that $(S\oplus R)/J$ is +the desired symmetric algebra over the new current base ring $S\oplus +R$.} + +\verb|symbolic_power(m,d)| \index{symbolic\_power} + +\pbx{returns the $d$th symbolic power of the prime dpmat ideal $m$.} + +\verb|syzygies m| \index{syzygies} + +\pbx{returns the first syzygy module of the bounded identifier $m$.} + +\verb|tangentcone gb| \index{tangentcone} + +\pbx{returns the tangent cone part, i.e.\ the homogeneous part of +highest degree with respect to the first degree vector of the term +order from the \gr basis elements of the dpmat $gb$. The term order +must be a degree order.} + +\verb|unmixedradical m| \index{unmixedradical} + +\pbx{returns the unmixed radical of the dpmat ideal $m$.} + +\verb|varopt m| \index{varopt} + +\pbx{finds a heuristically optimal variable order, see \cite{BGK}. +\[\tt vars:=varopt\ m;\ setring(vars,\{\},lex);\ setideal(m,m);\] +changes to the lexicographic term order with heuristically best +performance for a lexicographic \gr basis computation.} + +\verb|WeightedHilbertSeries(m,w)| \index{WeightedHilbertSeries} + +\pbx{returns the weighted Hilbert series of the dpmat $m$. Note that +$m$ is not a bounded identifier and hence not checked to be a \gr +basis. $w$ is a list of integer weight vectors.} + +\verb|zeroprimarydecomposition m| \index{zeroprimarydecomposition} + +\pbx{returns the primary decomposition of the zerodimensional dpmat +$m$ as a list of $\{component, associated\ prime\}$ pairs.} + +\verb|zeroprimes m| \index{zeroprimes} + +\pbx{returns the list of primes of the zerodimensional dpmat $m$.} + +\verb|zeroradical gb| \index{zeroradical} + +\pbx{returns the radical of the zerodimensional ideal $gb$.} + +\verb|zerosolve m|, \verb|zerosolve1 m| and \verb|zerosolve2 m| +\index{zerosolve}\index{zerosolve1}\index{zerosolve2} + +\pbx{Returns for a zerodimensional ideal a list of triangular systems +that cover $Z(m)$. {\tt Zerosolve} needs a pure lex.\ term order for +the ``fast'' turn to lex.\ as described in \cite{Moeller}, {\tt +Zerosolve1} is the ``slow'' turn to lex.\ as described in \cite{efgb}, +and {\tt Zerosolve2} incorporated the FGLM term order change into {\tt +Zerosolve1}.} +\end{quote} +\pagebreak + + +\section{The CALI Module Structure} +\vfill + +\begin{tabular}{|p{1.5cm}||p{5.5cm}|p{2cm}|p{4cm}|} +\hline +\sloppy + +name & subject & data type & representation \\ +\hline + +cali & Header module, contains \linebreak +global variables, switches etc. & --- & ---\\ + +bcsf & Base coefficient arithmetic & base coeff. & standard forms \\ + +ring & Base ring setting, definition of the term order & base ring & +special type RING\\ + +mo & monomial arithmetic & monomials & (exp. list . degree list)\\ + +dpoly & Polynomial and vector arith\-metic & dpolys & list of terms\\ + +bas & Operations on base lists & base list & list of base elements \\ + +dpmat & Operations on polynomial matrices, the central data type of +CALI & dpmat & special type DPMAT\\ + +red & Normal form algorithms & --- & ---\\ + +groeb & \gr basis algorithm and related ones & --- & ---\\ + +groebf & the \gr factorizer and its extensions & --- & ---\\ + +matop & Operations on (lists of) \linebreak dpmats that correspond to +ideal/module operations & --- & ---\\ + +quot & Different quotient algorithms & --- & --- \\ + +moid & Monomial ideal algorithms & monomial ideal & list of monomials \\ + +hf & weighted Hilbert series & -- & -- \\ + +res & Resolutions of dpmats & resolution & list of dpmats \\ + +intf & Interface to algebraic mode & --- & ---\\ + +odim & Algorithms for zerodimensional ideals and modules & --- & ---\\ + +prime & Primary decomposition and related questions & --- & ---\\ + +scripts & Advanced applications & --- & ---\\ + +calimat & Extension of the matrix package & --- & ---\\ + +lf & The dual bases approach & --- & ---\\ + +triang & (Zero dimensional) triangular systems & --- & ---\\ +\hline +\end{tabular} +\vfill +\pagebreak + +\begin{theindex} + + \item affine\_monomial\_curve, 33, 36 + \item affine\_points, 7, 35, 36 + \item affine\_points1!*, 35 + \item algebraic numbers, 13 + \item analytic\_spread, 33, 36 + \item annihilator, 28, 36 + \item assgrad, 33, 36 + + \indexspace + + \item bas\_detectunits, 23 + \item bas\_factorunits, 23 + \item bas\_getrelations, 20 + \item bas\_removerelations, 20 + \item bas\_setrelations, 20 + \item base coefficients, 13 + \item base elements, 19 + \item base ring, 9, 17 + \item basis, 13 + \item bcsimp, 14 + \item BettiNumbers, 30, 36 + \item binomial, 7 + \item blockorder, 10, 18 + \item blowup, 7, 33, 36 + \item border basis, 8 + \item bounded identifier, 13, 36 + + \indexspace + + \item cali, 16 + \item cali!=basering, 9, 16, 18 + \item cali!=degrees, 12, 16, 18 + \item cali!=monset, 16, 25 + \item change of term orders, 7 + \item change\_termorder, 35, 37 + \item change\_termorder1, 35, 37 + \item clearcaliprintterms, 16 + \item codim, 29, 37 + \item column degree, 12 + + \indexspace + + \item degree, 30, 37 + \item degree vectors, 9 + \item degreeorder, 10, 18 + \item degsfromresolution, 37 + \item deleteunits, 23, 37 + \item detectunits, 14, 23 + \item dim, 8, 29, 37 + \item dimzerop, 31, 37 + \item directsum, 37 + \item dmode, 13 + \item dp\_pseudodivmod, 14, 19, 28 + \item dpgcd, 19, 37 + \item dpmat, 8, 12, 13, 20 + \item dpmat\_coldegs, 20 + \item dpmat\_cols, 20 + \item dpmat\_gbtag, 20 + \item dpmat\_list, 20 + \item dpmat\_rows, 20 + \item dual bases, 6, 7, 34, 35 + + \indexspace + + \item easydim, 26, 29, 37 + \item easyindepset, 29, 37 + \item easyprimarydecomposition, 32, 37 + \item ecart, 3, 19 + \item ecart vector, 8, 11, 40 + \item efgb, 16 + \item eliminate, 7, 27, 38 + \item eliminationorder, 10, 18 + \item eqhull, 32, 38 + \item evlf, 17 + \item extended \gr factorizer, 7, 15, 26 + \item extendedgroebfactor, 26, 38 + \item extendedgroebfactor1, 26, 38 + + \indexspace + + \item factorunits, 15, 23 + \item flatten, 8 + \item free identifier, 13 + + \indexspace + + \item gb-tag, 8, 20 + \item gbasis, 24, 38 + \item gbtestversion, 7, 8, 16, 24 + \item getdegrees, 12 + \item getecart, 11 + \item getkbase, 31, 38 + \item getleadterms, 38 + \item getring, 11 + \item getrules, 13 + \item global procedures, 5 + \item GradedBettiNumbers, 30 + \item gradedbettinumbers, 38 + \item groeb, 7 + \item groeb!=rf, 16 + \item groeb\_homstbasis, 24 + \item groeb\_lazystbasis, 24 + \item groeb\_mingb, 25 + \item groeb\_minimize, 25 + \item groeb\_stbasis, 24 + \item groebf\_zeroprimes1, 27 + \item groebfactor, 26, 38 + + \indexspace + + \item hardzerotest, 15 + \item hf!=hf, 16 + \item hf\_whilb, 30 + \item hf\_whilb3, 30 + \item hf\_whs\_from\_resolution, 30 + \item hftestversion, 8, 16, 30 + \item HilbertSeries, 8, 11, 30, 38 + \item homstbasis, 25, 38 + + \indexspace + + \item ideal2mat, 12, 38 + \item ideal\_of\_minors, 21, 38 + \item ideal\_of\_pfaffians, 21, 39 + \item idealpower, 39 + \item idealprod, 39 + \item idealquotient, 27, 28, 39 + \item ideals, 12 + \item idealsum, 39 + \item indepvarsets, 29, 39 + \item initmat, 39 + \item internal procedures, 5 + \item interreduce, 23, 39 + \item isolatedprimes, 32, 39 + \item isprime, 32, 39 + \item iszeroradical, 39 + + \indexspace + + \item lazy, 7 + \item lazystbasis, 25, 39 + \item lexefgb, 15, 27 + \item lexicographic, 9 + \item listgroebfactor, 26, 39 + \item listminimize, 6 + \item listtest, 6 + \item local procedures, 5 + \item localorder, 10, 18 + + \indexspace + + \item map, 32 + \item mat2list, 8, 12, 39 + \item matappend, 40 + \item mathomogenize, 40 + \item mathprint, 17 + \item matintersect, 7, 27, 40 + \item matjac, 21, 40 + \item matqquot, 28, 40 + \item matquot, 28, 40 + \item matstabquot, 28, 40 + \item matsum, 40 + \item minimal\_generators, 34, 40 + \item minors, 21, 40 + \item mod, 23, 40 + \item modequalp, 8, 27, 40 + \item module + \subitem bcsf, 17 + \subitem cali, 5 + \subitem calimat, 8, 21 + \subitem dpmat, 20 + \subitem groeb, 24 + \subitem groebf, 7, 26 + \subitem lf, 7, 17 + \subitem moid, 28 + \subitem mora, 7 + \subitem odim, 7, 31 + \subitem prime, 31 + \subitem ring, 17 + \subitem scripts, 7, 32 + \subitem triang, 26, 27 + \item module quotient, 27 + \item module term order, 12 + \item modulequotient, 28, 40 + \item modules, 12 + \item moid\_primes, 29 + + \indexspace + + \item Noetherian, 3, 15 + \item normalform, 23, 41 + \item nzdp, 34, 41 + + \indexspace + + \item odim\_borderbasis, 31 + \item odim\_parameter, 31 + \item odim\_up, 31 + \item oldbasis, 17 + \item oldborderbasis, 17 + \item oldring, 17 + + \indexspace + + \item pfaffian, 21, 41 + \item preimage, 7, 32, 41 + \item primarydecomposition, 7, 41 + \item printterms, 16 + \item proj\_monomial\_curve, 33, 41 + \item proj\_points, 7, 35, 41 + \item proj\_points1!*, 35 + + \indexspace + + \item radical, 32, 41 + \item random\_linear\_form, 21, 41 + \item ratpreimage, 33, 41 + \item red, 7 + \item red\_better, 22 + \item red\_extract, 23 + \item red\_Interreduce, 23 + \item red\_prepare, 23 + \item red\_redpol, 23 + \item red\_Straight, 22 + \item red\_TailRed, 22 + \item red\_TailRedDriver, 22 + \item red\_TopInterreduce, 23 + \item red\_TopRed, 22 + \item red\_TopRedBE, 22 + \item red\_total, 15 + \item red\_TotalRed, 22 + \item Resolve, 7, 30, 42 + \item reverse lexicographic, 8, 9 + \item ring, 13 + \item ring\_2a, 17 + \item ring\_define, 17 + \item ring\_degrees, 17 + \item ring\_ecart, 17 + \item ring\_from\_a, 17 + \item ring\_isnoetherian, 17 + \item ring\_lp, 18 + \item ring\_names, 17 + \item ring\_rlp, 18 + \item ring\_sum, 18 + \item ring\_tag, 17 + \item rules, 16 + + \indexspace + + \item savemat, 42 + \item setcaliprintterms, 16 + \item setcalitrace, 8, 15 + \item setdegrees, 12, 16 + \item setgbasis, 8, 42 + \item setideal, 13, 14 + \item setkorder, 18 + \item setmodule, 13, 14 + \item setmonset, 16, 25 + \item setring, 7, 9, 11, 14, 16, 18 + \item setrules, 13, 14, 16, 17, 19 + \item sieve, 42 + \item singular\_locus, 21, 42 + \item stable quotient, 27 + \item sublist, 17 + \item submodulep, 27, 42 + \item switch + \subitem bcsimp, 17 + \subitem hardzerotest, 13 + \subitem lexefgb, 16, 27 + \subitem Noetherian, 10, 18 + \item sym, 7, 34, 42 + \item symbolic\_power, 34, 42 + \item syzygies, 24, 42 + \item syzygies1, 24 + + \indexspace + + \item tangentcone, 42 + \item term, 19 + \item trace, 16 + \item tracing, 8 + \item triang, 7 + \item triangular systems, 7, 26 + + \indexspace + + \item unmixedradical, 32, 42 + + \indexspace + + \item varlessp, 17 + \item varnames, 17 + \item varopt, 34, 43 + + \indexspace + + \item WeightedHilbertSeries, 8, 29, 30, 43 + + \indexspace + + \item zeroprimarydecomposition, 31, 32, 43 + \item zeroprimes, 31, 43 + \item zeroradical, 31, 43 + \item zerosolve, 15, 27, 43 + \item zerosolve1, 15, 27, 43 + \item zerosolve2, 27, 43 + +\end{theindex} + +\pagebreak + +\begin{thebibliography}{xxx} +\bibitem{BS} D. Bayer, M. Stillman: Computation of Hilbert +functions. {\it J. Symb. Comp. \bf 14} (1992), 31 - 50. +\bibitem{BKW} T. Becker, H. Kredel, V. Weispfenning: \gr bases. A +computational approach to commutative algebra. Grad. Texts in Math. +141, Springer, New York 1993. +\bibitem{BCRT} A. M. Bigatti, P. Conti, L. Robbiano, C. Traverso: A +``divide and conquer'' algorithm for Hilbert-Poincare series, +multiplicity and dimension of monomial ideals. In: Proc. AAECC-10, +LNCS 673 (1993), 76 - 88. +\bibitem{BGK} W. Boege, R. Gebauer, H. Kredel: Some examples for +solving systems of algebraic equations by calculating \gr bases. {\it +J. Symb. Comp. \bf 2} (1986), 83 - 98. +\bibitem{B1} B. Buchberger: \gr bases: An algorithmic method in +polynomial ideal theory. In: Recent trends in multidimensional +system theory (N.~K.~Bose ed), Reidel, Dortrecht 1985, 184 - 232. +\bibitem{B2} B. Buchberger: Applications of \gr bases in non-linear +computational geometry. LNCS 296 (1988), 52 - 80. +\bibitem{CLO} D. Cox, J. Little, D. O'Shea: Ideals, varieties, and +algorithms. Undergraduate Texts in Math., Springer, New York 1992. +\bibitem{E} D. Eisenbud: Commutative algebra with a view toward +algebraic geometry. Springer, 1995. +\bibitem{FGLM} Faugere, Gianni, Lazard, Mora: Efficient computations +of zerodimensional \gr bases by change of ordering. {\it +J. Symb. Comp. \bf 16} (1993), 329 - 344. +\bibitem{GTZ} P. Gianni, B. Trager, G. Zacharias: \gr bases and +primary decomposition of polynomial ideals. {\it J. Symb. Comp. \bf +6} (1988), 149 - 167. +\bibitem{GMNRT} A. Giovini, T. Mora, G. Niesi, L. Robbiano, C. +Traverso: "One sugar cube, please" or Selection strategies in the +Buchberger algorithm. In: Proceedings of the ISSAC'91, ACM Press +1991, 49 - 54. +\bibitem{rois} H.-G. Gr\"abe: Two remarks on independent sets. +{\it J. Alg. Comb. \bf 2} (1993), 137 - 145. +\bibitem{tcah} H.-G. Gr\"abe: The tangent cone algorithm and +homogenization. {\it J. Pure Applied Alg.\bf 97} (1994), 303 - 312. + +\bibitem{ala} H.-G. Gr\"abe: Algorithms in local algebra. To appear + +\bibitem{fgb} H.-G. Gr\"abe: On factorized \gr bases. Report Nr. 6 +(1994), Inst. f. Informatik, Univ. Leipzig. + +To appear in: Proc. ``Computer Algebra in Science and Engineering'', +Bielefeld 1994. + +\bibitem{efgb} H.-G. Gr\"abe: Triangular systems and factorized \gr +bases. Report Nr. 7 (1995), Inst. f. Informatik, Univ. Leipzig. + +\bibitem{primary} H.-G. Gr\"abe: Factorized \gr bases and primary +decomposition. To appear. + +\bibitem{Kr} H. Kredel: Primary ideal decomposition. In: Proc. +EUROCAL'87, Lecture Notes in Comp. Sci. 378 (1986), 270 - 281. +\bibitem{KW} H. Kredel, V. Weispfenning: Computing dimension and +independent sets for polynomial ideals. {\it J. Symb. Comp. \bf 6} +(1988), 231 - 247. +\bibitem{MMM} M. Marinari, H.-M. M\"oller, T. Mora: \gr bases of +ideals given by dual bases. In: Proc. ISSAC'91, ACM Press 1991, 55 - +63. +\bibitem{Mishra} B. Mishra: Algorithmic Algebra. Springer, New York +1993. +\bibitem{MM} H.-M. M\"oller, F. Mora: New constructive methods in +classical ideal theory. {\it J. Alg. \bf 100} (1986), 138 -178. +\bibitem{Moeller} H.-M. M\"oller: On decomposing systems of polynomial +equations with finitely many solutions. {\em J. AAECC \bf 4} (1993), +217 - 230. +\bibitem{MR88} T. Mora, L. Robbiano: The Gr\"obner fan of an ideal. +{\it J. Symb. Comp. \bf 6} (1988), 183 - 208. +\bibitem{Mo88} T. Mora: Seven variations on standard bases. +Preprint, Univ. Genova, 1988. +\bibitem{MPT} T. Mora, G. Pfister, C. Traverso: An introduction to +the tangent cone algorithm. In: {\em Issues in non-linear geometry and +robotics, C.M. Hoffman ed.}, JAI Press. +\bibitem{Ro} L. Robbiano: Computer algebra and commutative algebra. +LNCS 357 (1989), 31 - 44. +\bibitem{Ru} E. W. Rutman: \gr bases and primary decomposition of +modules. {\it J. Symb. Comp. \bf 14} (1992), 483 - 503. + +\end{thebibliography} + +\end{document} + Index: r36/doc/CAMAL.BIB ================================================================== --- r36/doc/CAMAL.BIB +++ r36/doc/CAMAL.BIB @@ -1,105 +1,105 @@ -% Bibliography entry for camal.tex. - -@InProceedings{Barnes, - author = "A. Barnes and J. A. Padget", - title = "Univariate Power Series Expansions in {Reduce}", - booktitle = "Proceedings of ISSAC'90", - year = "1990", - editor = "S. Watanabe and M. Nagata", - pages = "82--7", - organization = "ACM", - publisher = "Addison-Wesley" -} - -@Article{Barton67a, - author = "D. Barton", - title = "", - journal = "Astronomical Journal", - year = "1967", - volume = "72", - pages = "1281--7" -} - -@Article{Barton67b, - author = "D. Barton", - title = "A scheme for manipulative algebra on a computer", - journal = "Computer Journal", - year = "1967", - volume = "9", - pages = "340--4" -} - -@Article{Barton72, - author = "D. Barton and J. P. Fitch", - title = "The Application of Symbolic Algebra System to Physics", - journal = "Reports on Progress in Physics", - year = "1972", - volume = "35", - pages = "235--314" -} - -@ARTICLE{Bourne, - AUTHOR = {Stephen R. Bourne}, - TITLE = {Literal expressions for the co-ordinates of the moon. - {I}. The first degree terms}, - JOURNAL = {Celestial Mechanics}, - VOLUME = {6}, - PAGES = {167--186}, - YEAR = {1972}, - GENERATED = {Mon Oct 23 19:42:01 GMT 1989 on fino} -} - -@Book{Brown, - author = "E. W. Brown", - title = "An Introductory Treatise on the Lunar Theory", - publisher = "Cambridge University Press", - year = "1896" -} - -@Manual{CAMALF, - title = "{CAMAL} {User's} {Manual}", - author = "J. P. Fitch", - organization = "University of Cambridge Computer Laboratory", - edition = "2nd", - year = "1983" -} - -@Book{Delaunay, - author = "C. Delaunay", - title = "Th\'eorie du Mouvement de la Lune", - publisher = "Mallet-Bachelier", - year = "1860", - series = "(Extraits des M\'em. Acad. Sci.)", - address = "Paris" -} - -@Article{Fateman, - author = {Richard J. Fateman}, - title = {On the Multiplication of Poisson Series}, - journal = {Celestial Mechanics}, - year = {1974}, - OPTkey = {}, - volume = {10}, - number = {2}, - month = {October}, - pages = {243--249} -} - -@Article{Jefferys, - author = "W. H. Jeffereys", - title = "", - journal = "Celestial Mechanics", - year = "1970", - volume = "2", - pages = "474--80" -} -@Article{LectureNotes, - author = "J. P. Fitch", - title = "Syllabus for Algebraic Manipulation Lectures in Cambridge", - journal = "SIGSAM Bulletin", - year = "1975", - volume = "32", - pages = "15" -} - - +% Bibliography entry for camal.tex. + +@InProceedings{Barnes, + author = "A. Barnes and J. A. Padget", + title = "Univariate Power Series Expansions in {Reduce}", + booktitle = "Proceedings of ISSAC'90", + year = "1990", + editor = "S. Watanabe and M. Nagata", + pages = "82--7", + organization = "ACM", + publisher = "Addison-Wesley" +} + +@Article{Barton67a, + author = "D. Barton", + title = "", + journal = "Astronomical Journal", + year = "1967", + volume = "72", + pages = "1281--7" +} + +@Article{Barton67b, + author = "D. Barton", + title = "A scheme for manipulative algebra on a computer", + journal = "Computer Journal", + year = "1967", + volume = "9", + pages = "340--4" +} + +@Article{Barton72, + author = "D. Barton and J. P. Fitch", + title = "The Application of Symbolic Algebra System to Physics", + journal = "Reports on Progress in Physics", + year = "1972", + volume = "35", + pages = "235--314" +} + +@ARTICLE{Bourne, + AUTHOR = {Stephen R. Bourne}, + TITLE = {Literal expressions for the co-ordinates of the moon. + {I}. The first degree terms}, + JOURNAL = {Celestial Mechanics}, + VOLUME = {6}, + PAGES = {167--186}, + YEAR = {1972}, + GENERATED = {Mon Oct 23 19:42:01 GMT 1989 on fino} +} + +@Book{Brown, + author = "E. W. Brown", + title = "An Introductory Treatise on the Lunar Theory", + publisher = "Cambridge University Press", + year = "1896" +} + +@Manual{CAMALF, + title = "{CAMAL} {User's} {Manual}", + author = "J. P. Fitch", + organization = "University of Cambridge Computer Laboratory", + edition = "2nd", + year = "1983" +} + +@Book{Delaunay, + author = "C. Delaunay", + title = "Th\'eorie du Mouvement de la Lune", + publisher = "Mallet-Bachelier", + year = "1860", + series = "(Extraits des M\'em. Acad. Sci.)", + address = "Paris" +} + +@Article{Fateman, + author = {Richard J. Fateman}, + title = {On the Multiplication of Poisson Series}, + journal = {Celestial Mechanics}, + year = {1974}, + OPTkey = {}, + volume = {10}, + number = {2}, + month = {October}, + pages = {243--249} +} + +@Article{Jefferys, + author = "W. H. Jeffereys", + title = "", + journal = "Celestial Mechanics", + year = "1970", + volume = "2", + pages = "474--80" +} +@Article{LectureNotes, + author = "J. P. Fitch", + title = "Syllabus for Algebraic Manipulation Lectures in Cambridge", + journal = "SIGSAM Bulletin", + year = "1975", + volume = "32", + pages = "15" +} + + Index: r36/doc/CAMAL.TEX ================================================================== --- r36/doc/CAMAL.TEX +++ r36/doc/CAMAL.TEX @@ -1,631 +1,631 @@ -\documentstyle[11pt]{article} -\title{REDUCE Meets CAMAL} -\author{J. P. Fitch \\ -School of Mathematical Sciences\\ -University of Bath\\ -BATH, BA2 7AY, United Kingdom} -\def\today{} -\begin{document}\maketitle - -\begin{abstract} -{\em It is generally accepted that special purpose algebraic systems -are more efficient than general purpose ones, but as machines get -faster this does not matter. An experiment has been performed to see -if using the ideas of the special purpose algebra system CAMAL(F) it -is possible to make the general purpose system REDUCE perform -calculations in celestial mechanics as efficiently as CAMAL did twenty -years ago. To this end a prototype Fourier module is created for -REDUCE, and it is tested on some small and medium-sized problems taken -from the CAMAL test suite. The largest calculation is the -determination of the Lunar Disturbing Function to the sixth order. An -assessment is made as to the progress, or lack of it, which computer -algebra has made, and how efficiently we are using modern hardware. -} -\end{abstract} - -\section{Introduction} - -A number of years ago there emerged the divide between general-purpose -algebra systems and special purpose one. Here we investigate how far -the improvements in software and more predominantly hardware have -enabled the general systems to perform as well as the earlier special -ones. It is similar in some respects to the Possion program for -MACSYMA \cite{Fateman} which was written in response to a similar -challenge. - -The particular subject for investigation is the Fourier series -manipulator which had its origins in the Cambridge University -Institute for Theoretical Astronomy, and later became the F subsystem -of CAMAL \cite{Barton67b,CAMALF}. In the late 1960s this system was -used for both the Delaunay Lunar Theory \cite{Delaunay,Barton67a} and -the Hill Lunar Theory \cite{Bourne}, as well as other related -calculations. Its particular area of application had a number of -peculiar operations on which the general speed depended. These are -outlined below in the section describing how CAMAL worked. There have -been a number of subsequent special systems for celestial mechanics, -but these tend to be restricted to the group of the originator. - -The main body of the paper describes an experiment to create within -the REDUCE system a sub-system for the efficient manipulation of -Fourier series. This prototype program is then assessed against both -the normal (general) REDUCE and the extant CAMAL results. The tests -are run on a number of small problems typical of those for which CAMAL -was used, and one medium-sized problem, the calculation of the Lunar -Disturbing Function. The mathematical background to this problem is -also presented for completeness. It is important as a problem as it -is the first stage in the development of a Delaunay Lunar Theory. - -The paper ends with an assessment of how close the performance of a -modern REDUCE on modern equipment is to the (almost) defunct CAMAL of -eighteen years ago. - -\section{How CAMAL Worked} - -The Cambridge Algebra System was initially written in assembler for -the Titan computer, but later was rewritten a number of times, and -matured in BCPL, a version which was ported to IBM mainframes and a -number of microcomputers. In this section a brief review of the main -data structures and special algorithms is presented. - -\subsection{CAMAL Data Structures} - -CAMAL is a hierarchical system, with the representation of polynomials -being completely independent of the representations of the angular -parts. - -The angular part had to represent a polynomial coefficient, either a -sine or cosine function and a linear sum of angles. In the problems -for which CAMAL was designed there are 6 angles only, and so the -design restricted the number, initially to six on the 24 bit-halfword -TITAN, and later to eight angles on the 32-bit IBM 370, each with -fixed names (usually u through z). All that is needed is to remember -the coefficients of the linear sum. As typical problems are -perturbations, it was reasonable to restrict the coefficients to small -integers, as could be represented in a byte with a guard bit. This -allowed the representation to pack everything into four words. -\begin{verbatim} - [ NextTerm, Coefficient, Angles0-3, Angles4-7 ] -\end{verbatim} -The function was coded by a single bit in the {\tt Coefficient} field. This -gives a particularly compact representation. For example the Fourier -term $\sin(u-2v+w-3x)$ would be represented as -\begin{verbatim} - [ NULL, "1"|0x1, 0x017e017d, 0x00000000 ] -or - [ NULL, "1"|0x1, 1:-2:1:-3, 0:0:0:0 ] -\end{verbatim} -where {\tt "1"} is a pointer to the representation of the polynomial -1. In all this representation of the term took 48 bytes. As the -complexity of a term increased the store requirements to no grow much; -the expression $(7/4) a e^3 f^5 \cos(u-2v+3w-4x+5y+6z)$ also takes 48 -bytes. There is a canonicalisation operation to ensure that the -leading angle is positive, and $\sin(0)$ gets removed. It should be -noted that $\cos(0)$ is a valid and necessary representation. - -The polynomial part was similarly represented, as a chain of terms -with packed exponents for a fixed number of variables. There is no -particular significance in this except that the terms were held in -{\em increasing} total order, rather than the decreasing order which -is normal in general purpose systems. This had a number of important -effects on the efficiency of polynomial multiplication in the presence -of a truncation to a certain order. We will return to this point -later. Full details of the representation can be found in -\cite{LectureNotes}. - -The space administration system was based on explicit return rather -than garbage collection. This meant that the system was sometimes -harder to write, but it did mean that much attention was focussed on -efficient reuse of space. It was possible for the user to assist in -this by marking when an expression was needed no longer, and the -compiler then arranged to recycle the space as part of the actual -operation. This degree of control was another assistance in running -of large problems on relatively small machines. - -\subsection{Automatic Linearisation} - -In order to maintain Fourier series in a canonical form it is -necessary to apply the transformations for linearising products of -sine and cosines. These will be familiar to readers of the REDUCE -test program as -\begin{eqnarray} -\cos \theta \cos \phi & \Rightarrow & - (\cos(\theta+\phi)+\cos(\theta-\phi))/2, \\ -\cos \theta \sin \phi & \Rightarrow & - (\sin(\theta+\phi)-\sin(\theta-\phi))/2, \\ -\sin \theta \sin \phi & \Rightarrow & - (\cos(\theta-\phi)-\cos(\theta+\phi))/2, \\ -\cos^2 \theta & \Rightarrow & (1+\cos(2\theta))/2, \\ -\sin^2 \theta & \Rightarrow & (1-\cos(2\theta))/2. -\end{eqnarray} -In CAMAL these transformations are coded directly into the -multiplication routines, and no action is necessary on the part of the -user to invoke them. Of course they cannot be turned off either. - -\subsection{Differentiation and Integration} - -The differentiation of a Fourier series with respect to an angle is -particularly simple. The integration of a Fourier series is a little -more interesting. The terms like $\cos(n u + \ldots)$ are easily -integrated with respect to $u$, but the treatment of terms independent -of the angle would normally introduce a secular term. By convention -in Fourier series these secular terms are ignored, and the constant of -integration is taken as just the terms independent of the angle in the -integrand. This is equivalent to the substitution rules -\begin{eqnarray*} -\sin(n \theta) & \Rightarrow & -(1/n) \cos(n \theta) \\ -\cos(n \theta) & \Rightarrow & (1/n) \sin(n \theta) -\end{eqnarray*} - -In CAMAL these operations were coded directly, and independently of -the differentiation and integration of the polynomial coefficients. - -\subsection{Harmonic Substitution} - -An operation which is of great importance in Fourier operations is the -{\em harmonic substitution}. This is the substitution of the sum of -some angles and a general expression for an angle. In order to -preserve the format, the mechanism uses the translations -\begin{eqnarray*} -\sin(\theta + A) & \Rightarrow & \sin(\theta) \cos(A) + - \cos(\theta) \sin(A) \\ -\cos(\theta + A) & \Rightarrow & \cos(\theta) \cos(A) - - \sin(\theta) \sin(A) \\ -\end{eqnarray*} -and then assuming that the value $A$ is small it can be replaced by -its expansion: -\begin{eqnarray*} -\sin(\theta + A) & \Rightarrow & \sin(\theta) \{1 - A^2/2! + A^4/4!\ldots\} +\\ - & & \cos(\theta) \{A - A^3/3! + A^5/5!\ldots\} \\ -\cos(\theta + A) & \Rightarrow & \cos(\theta) \{1 - A^2/2! + A^4/4!\ldots\} -\\ - & & \sin(\theta) \{A - A^3/3! + A^5/5! \ldots\} \\ -\end{eqnarray*} -If a truncation is set for large powers of the polynomial variables -then the series will terminate. In CAMAL the {\tt HSUB} operation -took five arguments; the original expression, the angle for which -there is a substitution, the new angular part, the expression part -($A$ in the above), and the number of terms required. - -The actual coding of the operation was not as expressed above, but by -the use of Taylor's theorem. As has been noted above the -differentiation of a harmonic series is particularly easy. - -\subsection{Truncation of Series} - -The main use of Fourier series systems is in generating perturbation -expansions, and this implies that the calculations are performed to -some degree of the small quantities. In the original CAMAL all -variables were assumed to be equally small (a restriction removed in -later versions). By maintaining polynomials in increasing maximum -order it is possible to truncate the multiplication of two -polynomials. Assume that we are multiplying the two polynomials -\begin{eqnarray*} - A = a_0 + a_1 + a_2 + \ldots \\ - B = b_0 + b_1 + b_2 + \ldots -\end{eqnarray*} -If we are generating the partial answer -\[ - a_i (b_0 + b_1 + b_2 + \ldots) -\] -then if for some $j$ the product $a_i b_j$ vanishes, then so will all -products $a_i b_k$ for $k>j$. This means that the later terms need -not be generated. In the product of $1+x+x^2+x^3+\ldots+x^{10}$ and -$1+y+y^2+y^3+\ldots+y^10$ to a total order of 10 instead of generating -100 term products only 55 are needed. The ordering can also make the -merging of the new terms into the answer easier. - -\section{Towards a CAMAL Module} - -For the purposes of this work it was necessary to reproduce as many of -the ideas of CAMAL as feasible within the REDUCE framework and -philosophy. It was not intended at this stage to produce a complete -product, and so for simplicity a number of compromises were made with -the ``no restrictions'' principle in REDUCE and the space and time -efficiency of CAMAL. This section describes the basic design -decisions. - -\subsection{Data Structures} - -In a fashion similar to CAMAL a two level data representation is used. -The coefficients are the standard quotients of REDUCE, and their -representation need not concern us further. The angular part is -similar to that of CAMAL, but the ability to pack angle multipliers -and use a single bit for the function are not readily available in -Standard LISP, so instead a longer vector is used. Two versions were -written. One used a balanced tree rather than a linear list for the -Fourier terms, this being a feature of CAMAL which was considered but -never coded. The other uses a simple linear representation for sums. -The angle multipliers are held in a separate vector in order to allow -for future flexibility. This leads to a representation as a vector of -length 6 or 4; -\begin{verbatim} -Version1: [ BalanceBits, Coeff, Function, Angles, LeftTree, RightTree ] -Version2: [ Coeff, Function, Angles, Next ] -\end{verbatim} -where the {\tt Angles} field is a vector of length 8, for the -multipliers. It was decided to forego packing as for portability we -do not know how many to pack into a small integer. The tree system -used is AVL, which needs 2 bits to maintain balance information, but -these are coded as a complete integer field in the vector. We can -expect the improvements implicit in a binary tree to be advantageous -for large expressions, but the additional overhead may reduce its -utility for smaller expressions. - -A separate vector is kept relating the position of an angle to its -print name, and on the property list of each angle the allocation of -its position is kept. So long as the user declares which variables -are to be treated as angles this mechanism gives flexibility which was -lacking in CAMAL. - -\subsection{Linearisation} - -As in the CAMAL system the linearisation of products of sines and -cosines is done not by pattern matching but by direct calculation at -the heart of the product function, where the transformations (1) -through (3) are made in the product of terms function. A side effect -of this is that there are no simple relations which can be used from -within the Fourier multiplication, and so a full addition of partial -products is required. There is no need to apply linearisations -elsewhere as a special case. Addition, differentiation and -integration cannot generate such products, and where they can occur in -substitution the natural algorithm uses the internal multiplication -function anyway. - -\subsection{Substitution} - -Substitution is the main operation of Fourier series. It is useful to -consider three different cases of substitutions. -\begin{enumerate} -\item Angle Expression for Angle: -\item Angle Expression + Fourier Expression for Angle: -\item Fourier Expression for Polynomial Variable. -\end{enumerate} - -The first of these is straightforward, and does not require any -further comment. The second substitution requires a little more care, -but is not significantly difficult to implement. The method follows -the algorithm used in CAMAL, using TAYLOR series. Indeed this is the -main special case for substitution. - -The problem is the last case. Typically many variables used in a -Fourier series program have had a WEIGHT assigned to them. This means -that substitution must take account of any possible WEIGHTs for -variables. The standard code in REDUCE does this in effect by -translating the expression to prefix form, and recalculating the value. -A Fourier series has a large number of coefficients, and so this -operations are repeated rather too often. At present this is the -largest problem area with the internal code, as will be seen in the -discussion of the Disturbing Function calculation. - -\section{Integration with REDUCE} - -The Fourier module needs to be seen as part of REDUCE rather than as a -separate language. This can be seen as having internal and external -parts. - -\subsection{Internal Interface} - -The Fourier expressions need to co-exist with the normal REDUCE syntax -and semantics. The prototype version does this by (ab)using the -module method, based in part on the TPS code \cite{Barnes}. Of course -Fourier series are not constant, and so are not really domain -elements. However by asserting that Fourier series form a ring of -constants REDUCE can arrange to direct basic operations to the Fourier -code for addition, subtraction, multiplication and the like. - -The main interface which needs to be provided is a simplification -function for Fourier expressions. This needs to provide compilation -for linear sums of angles, as well as constructing sine and cosine -functions, and creating canonical forms. - -\subsection{User Interface} - -The creation of {\tt HDIFF} and {\tt HINT} functions for -differentiation disguises this. An unsatisfactory aspect of the -interface is that the tokens {\tt SIN} and {\tt COS} are already in -use. The prototype uses the operator form -\begin{verbatim} - fourier sin(u) -\end{verbatim} -to introduce harmonically represented sine functions. An alternative of -using the tokens {\tt F\_SIN} and {\tt F\_COS} is also available. - -It is necessary to declare the names of the angles, which is achieved -with the declaration -\begin{verbatim} - harmonic theta, phi; -\end{verbatim} - -At present there is no protection against using a variable as both an -angle and a polynomial varaible. This will nooed to be done in a -user-oriented version. - -\section{The Simple Experiments} - -The REDUCE test file contains a simple example of a Fourier -calculation, determining the value of $(a_1 \cos({wt}) + a_3 -\cos(3{wt}) + b_1 \sin({wt}) + b_3 \sin(3{wt}))^3$. For the purposes -of this system this is too trivial to do more than confirm the correct -answers. - -The simplest non-trivial calculation for a Fourier series manipulator -is to solve Kepler's equation for the eccentric anomoly E in terms of -the mean anomoly u, and the eccentricity of an orbit e, considered as a -small quantity -\[ - E = u + e \sin E -\] -The solution procedes by repeated approximation. Clearly the initial -approximation is $E_0 = u$. The $n^{th}$ approximation can be written -as $u + A_n$, and so $A_n$ can be calculated by -\[ - A_k = e \sin (u + A_{k-1}) -\] -This is of course precisely the case for which the HSUB operation is -designed, and so in order to calculate $E_n - u$ all one requires is -the code -\begin{verbatim} - bige := fourier 0; - for k:=1:n do << - wtlevel k; - bige:=fourier e * hsub(fourier(sin u), u, u, bige, k); - >>; - write "Kepler Eqn solution:", bige$ -\end{verbatim} - -It is possible to create a regular REDUCE program to simulate this (as -is done for example in Barton and Fitch\cite{Barton72}, page 254). -Comparing these two programs indicates substantial advantages to the -Fourier module, as could be expected. -\medskip -\begin{center} -\begin{tabular}{ | c | l l |} -\multicolumn{3}{c}{\bf Solving Kepler's Equation} \\ -\hline -Order & REDUCE & Fourier Module \\ -5 & 9.16 & 2.48 \\ -6 & 17.40 & 4.56 \\ -7 & 33.48 & 8.06 \\ -8 & 62.76 & 13.54 \\ -9 & 116.06 & 21.84 \\ -10 & 212.12 & 34.54 \\ -11 & 381.78 & 53.94 \\ -12 & 692.56 & 82.96 \\ -13 & 1247.54 & 125.86 \\ -14 & 2298.08 & 187.20 \\ -15 & 4176.04 & 275.60 \\ -16 & 7504.80 & 398.62 \\ -17 & 13459.80 & 569.26 \\ -18 & *** & 800.00 \\ -19 & *** & 1116.92 \\ -20 & *** & 1536.40 \\ -\hline -\end{tabular} -\end{center} -\medskip -These results were with the linear representation of Fourier series. -The tree representation was slightly slower. The ten-fold speed-up -for the 13th order is most satisfactory. - -\section{A Medium-Sized Problem} - -Fourier series manipulators are primarily designed for large-scale -calculations, but for the demonstration purposes of this project a -medium problem is considered. The first stage in calculating the -orbit of the Moon using the Delaunay theory (of perturbed elliptic -motion for the restricted 3-body problem) is to calculate the energy -of the Moon's motion about the Earth --- the Hamiltonian of the -system. This is the calculation we use for comparisons. - -\subsection{Mathematical Background} - -The full calculation is described in detail in \cite{Brown}, but a -brief description is given here for completeness, and to grasp the -extent of the calculation. - -Referring to the figure 1 which gives the cordinate system, the basic -equations are -\begin{eqnarray} -S & = & (1-\gamma ^2)\cos(f + g +h -f' -g' -h') -+ \gamma ^2 cos(f + g -h +f' +g' +h') \\ -r & = & a (1 - e \cos E) \\ -l & = & E - e \sin E \\ -a & = & r {{\bf d} E} \over {{\bf d} l} \\ -r ^2 {{\bf d} f} \over {{\bf d} l} & = & a^2 (1 - e^2)^{1 \over 2}\\ -R & = & m' {a^2 \over {a'} ^3} {{a'}\over {r -'}} \left \{ \left ({r \over a}\right )^2 -\left ({{a'} \over {r'}}\right )^2 P_2(S) + -\left ({a \over {a'}}\right )\left -({r \over a}\right )^3 \left ({{a'} \over {r'}}\right )^3 P_3(S) -+ \ldots \right \} -\end{eqnarray} - -There are similar equations to (7) to (10) for the quantities $r'$, -$a'$, $e'$, $l'$, $E'$ and $f'$ which refer to the position of the Sun -rather than the Moon. The problem is to calculate the expression $R$ -as an expansion in terms of the quantities $e$, $e'$, $\gamma$, -$a/a'$, $l$, $g$, $h$, $l'$, $g'$ and $h'$. The first three -quantities are small quantities of the first order, and $a/a'$ is of -second order. - -The steps required are -\begin{enumerate} -\item Solve the Kepler equation (8) -\item Substiture into (7) to give $r/a$ in terms of $e$ and $l$. -\item Calculate $a/r$ from (9) and $f$ from (10) -\item Substitute for $f$ and $f'$ into $S$ using (6) -\item Calculate $R$ from $S$, $a'/r'$ and $r/a$ -\end{enumerate} - -The program is given in the Appendix. - -\subsection{Results} - -The Lunar Disturbing function was calculated by a direct coding of the -previous sections' mathematics. The program was taken from Barton -and Fitch \cite{Barton72} with just small changes to generalise it for -any order, and to make it acceptable for Reduce3.4. The Fourier -program followed the same pattern, but obviously used the {\tt HSUB} -operation as appropriate and the harmonic integration. It is very -similar to the CAMAL program in \cite{Barton72}. - -The disturbing function was calculated to orders 2, 4 and 6 using -Cambridge LISP on an HLH Orion 1/05 (Intergraph Clipper), with the -three programs $\alpha$) Reduce3.4, $\beta$) Reduce3.4 + Camal Linear -Module and $\gamma$) Reduce3.4 + Camal AVL Module. The timings for -CPU seconds (excluding garbage collection time) are summarised the -following table: -\medskip -\begin{center} -\begin{tabular}{ | c || l | l | l |} -\hline -Order of DDF & Reduce & Camal Linear & Camal Tree \\ -\hline -2 & 23.68 & 11.22 & 12.9 \\ -4 & 429.44 & 213.56 & 260.64 \\ -6 & $>$7500 & 3084.62 & 3445.54 \\ -\hline -%%% Linear n=4 138.72 (4Mb + unsafe vector access + recurrance) -%%% Linear n=6 1870.10 (4Mb + unsafe vector access + recurrance) -\end{tabular} -\end{center} -\medskip - -If these numbers are normalised so REDUCE calculating the DDF is 100 -units for each order the table becomes -\medskip -\begin{center} -\begin{tabular}{ | c || l | l | l |} -\hline -Order of DDF & Reduce & Camal Linear & Camal Tree \\ \hline -2 & 100 & 47.38 & 54.48 \\ -4 & 100 & 49.73 & 60.69 \\ -6 & 100 & $<$41.13 & $<$45.94 \\ -\hline -\end{tabular} -\end{center} -\medskip - -From this we conclude that a doubling of speed is about correct, and -although the balanced tree system is slower as the problem size -increases the gap between it and the simpler linear system is -narrowing. - -It is disappointing that the ratio is not better, nor the absolute -time less. It is worth noting in this context that Jefferys claimed -that the sixth order DDF took 30s on a CDC6600 with TRIGMAN in 1970 -\cite{Jefferys}, and Barton and Fitch took about 1s for the second -order DDF on TITAN with CAMAL \cite{Barton72}. A closer look at the -relative times for individual sections of the program shows that the -substitution case of replacing a polynomial variable by a Fourier -series is only marginally faster than the simple REDUCE program. In -the DDF program this operation is only used once in a major form, -substituting into the Legendre polynomials, which have been previously -calculated by Rodrigues formula. This suggests that we replace this -with the recurrence relationship. - -Making this change actually slows down the normal REDUCE by a small -amount but makes a significant change to the Fourier module; it -reduces the run time for the 6th order DDF from 3084.62s to 2002.02s. -This gives some indication of the problems with benchmarks. What is -clear is that the current implementation of substitution of a Fourier -series for a polynomial variable is inadequate. - -\section{Conclusion} - -The Fourier module is far from complete. The operations necessary for -the solution of Duffing's and Hill's equations are not yet written, -although they should not cause much problem. The main defficiency is -the treatment of series truncation; at present it relies on the REDUCE -WTLEVEL mechanism, and this seems too coarse for efficient truncation. -It would be possible to re-write the polynomial manipulator as well, -while retaining the REDUCE syntax, but that seems rather more than one -would hope. - -The real failure so far is the large time lag between the REDUCE-based -system on a modern workstation against a mainframe of 25 years ago -running a special system. The CAMAL Disturbing function program could -calculate the tenth order with a maximum of 32K words (about -192Kbytes) whereas this system failed to calculate the eigth order in -4Mbytes (taking 2000s before failing). I have in my archives the -output from the standard CAMAL test suite, which includes a sixth -order DDF on an IBM 370/165 run on 2 June 1978, taking 22.50s and -using a maximum of 15459 words of memory for heap --- or about -62Kbytes. A rough estimate is that the Orion 1/05 is comparable in -speed to the 360/165, but with more real memory and virtual memory. - -However, a simple Fourier manipulator has been created for REDUCE which -performs between twice and three times the speed of REDUCE using -pattern matching. It has been shown that this system is capable of -performing the calculations of celestial mechanics, but it still -seriously lags behind the efficiency of the specialist systems of -twenty years before. It is perhaps fortunate that it was not been -possible to compare it with a modern specialist system. - -There is still work to do to provide a convenient user interface, but -it is intended to develop the system in this direction. It would be -pleasant to have again a system of the efficiency of CAMAL(F). - -I would like to thank Codemist Ltd for the provision of computing -resources for this project, and David Barton who taught be so much -about Fourier series and celstial mechanics. Thank are also due to -the National Health Service, without whom this work and paper could not -have been produced. - -\section*{Appendix: The DDF Function} -\begin{verbatim} -array p(n/2+2); -harmonic u,v,w,x,y,z; -weight e=1, b=1, d=1, a=1; - -%% Generate Legendre Polynomials to sufficient order -for i:=2:n/2+2 do << - p(i):=(h*h-1)^i; - for j:=1:i do p(i):=df(p(i),h)/(2j) ->>; - -%%%%%%%%%%%%%%%% Step1: Solve Kepler equation -bige := fourier 0; -for k:=1:n do << - wtlevel k; - bige:=fourier e * hsub(fourier(sin u), u, u, bige, k); ->>; - -%% Ensure we do not calculate things of too high an order -wtlevel n; - -%%%%%%%%%%%%%%%% Step 2: Calculate r/a in terms of e and l -dd:=-e*e; hh:=3/2; j:=1; cc := 1; -for i:=1:n/2 do << - j:=i*j; hh:=hh-1; cc:=cc+hh*(dd^i)/j ->>; -bb:=hsub(fourier(1-e*cos u), u, u, bige, n); -aa:=fourier 1+hdiff(bige,u); ff:=hint(aa*aa*fourier cc,u); - -%%%%%%%%%%%%%%%% Step 3: a/r and f -uu := hsub(bb,u,v); uu:=hsub(uu,e,b); -vv := hsub(aa,u,v); vv:=hsub(vv,e,b); -ww := hsub(ff,u,v); ww:=hsub(ww,e,b); - -%%%%%%%%%%%%%%%% Step 4: Substitute f and f' into S -yy:=ff-ww; zz:=ff+ww; -xx:=hsub(fourier((1-d*d)*cos(u)),u,u-v+w-x-y+z,yy,n)+ - hsub(fourier(d*d*cos(v)),v,u+v+w+x+y-z,zz,n); - -%%%%%%%%%%%%%%%% Step 5: Calculate R -zz:=bb*vv; yy:=zz*zz*vv; - -on fourier; -for i := 2:n/2+2 do << - wtlevel n+4-2i; p(i) := hsub(p(i), h, xx) >>; - -wtlevel n; -for i:=n/2+2 step -1 until 3 do - p(n/2+2):=fourier(a*a)*zz*p(n/2+2)+p(i-1); -yy*p(n/2+2); - -\end{verbatim} -\newpage -\bibliographystyle{plain} -\bibliography{camal} - -\end{document} +\documentstyle[11pt]{article} +\title{REDUCE Meets CAMAL} +\author{J. P. Fitch \\ +School of Mathematical Sciences\\ +University of Bath\\ +BATH, BA2 7AY, United Kingdom} +\def\today{} +\begin{document}\maketitle + +\begin{abstract} +{\em It is generally accepted that special purpose algebraic systems +are more efficient than general purpose ones, but as machines get +faster this does not matter. An experiment has been performed to see +if using the ideas of the special purpose algebra system CAMAL(F) it +is possible to make the general purpose system REDUCE perform +calculations in celestial mechanics as efficiently as CAMAL did twenty +years ago. To this end a prototype Fourier module is created for +REDUCE, and it is tested on some small and medium-sized problems taken +from the CAMAL test suite. The largest calculation is the +determination of the Lunar Disturbing Function to the sixth order. An +assessment is made as to the progress, or lack of it, which computer +algebra has made, and how efficiently we are using modern hardware. +} +\end{abstract} + +\section{Introduction} + +A number of years ago there emerged the divide between general-purpose +algebra systems and special purpose one. Here we investigate how far +the improvements in software and more predominantly hardware have +enabled the general systems to perform as well as the earlier special +ones. It is similar in some respects to the Possion program for +MACSYMA \cite{Fateman} which was written in response to a similar +challenge. + +The particular subject for investigation is the Fourier series +manipulator which had its origins in the Cambridge University +Institute for Theoretical Astronomy, and later became the F subsystem +of CAMAL \cite{Barton67b,CAMALF}. In the late 1960s this system was +used for both the Delaunay Lunar Theory \cite{Delaunay,Barton67a} and +the Hill Lunar Theory \cite{Bourne}, as well as other related +calculations. Its particular area of application had a number of +peculiar operations on which the general speed depended. These are +outlined below in the section describing how CAMAL worked. There have +been a number of subsequent special systems for celestial mechanics, +but these tend to be restricted to the group of the originator. + +The main body of the paper describes an experiment to create within +the REDUCE system a sub-system for the efficient manipulation of +Fourier series. This prototype program is then assessed against both +the normal (general) REDUCE and the extant CAMAL results. The tests +are run on a number of small problems typical of those for which CAMAL +was used, and one medium-sized problem, the calculation of the Lunar +Disturbing Function. The mathematical background to this problem is +also presented for completeness. It is important as a problem as it +is the first stage in the development of a Delaunay Lunar Theory. + +The paper ends with an assessment of how close the performance of a +modern REDUCE on modern equipment is to the (almost) defunct CAMAL of +eighteen years ago. + +\section{How CAMAL Worked} + +The Cambridge Algebra System was initially written in assembler for +the Titan computer, but later was rewritten a number of times, and +matured in BCPL, a version which was ported to IBM mainframes and a +number of microcomputers. In this section a brief review of the main +data structures and special algorithms is presented. + +\subsection{CAMAL Data Structures} + +CAMAL is a hierarchical system, with the representation of polynomials +being completely independent of the representations of the angular +parts. + +The angular part had to represent a polynomial coefficient, either a +sine or cosine function and a linear sum of angles. In the problems +for which CAMAL was designed there are 6 angles only, and so the +design restricted the number, initially to six on the 24 bit-halfword +TITAN, and later to eight angles on the 32-bit IBM 370, each with +fixed names (usually u through z). All that is needed is to remember +the coefficients of the linear sum. As typical problems are +perturbations, it was reasonable to restrict the coefficients to small +integers, as could be represented in a byte with a guard bit. This +allowed the representation to pack everything into four words. +\begin{verbatim} + [ NextTerm, Coefficient, Angles0-3, Angles4-7 ] +\end{verbatim} +The function was coded by a single bit in the {\tt Coefficient} field. This +gives a particularly compact representation. For example the Fourier +term $\sin(u-2v+w-3x)$ would be represented as +\begin{verbatim} + [ NULL, "1"|0x1, 0x017e017d, 0x00000000 ] +or + [ NULL, "1"|0x1, 1:-2:1:-3, 0:0:0:0 ] +\end{verbatim} +where {\tt "1"} is a pointer to the representation of the polynomial +1. In all this representation of the term took 48 bytes. As the +complexity of a term increased the store requirements to no grow much; +the expression $(7/4) a e^3 f^5 \cos(u-2v+3w-4x+5y+6z)$ also takes 48 +bytes. There is a canonicalisation operation to ensure that the +leading angle is positive, and $\sin(0)$ gets removed. It should be +noted that $\cos(0)$ is a valid and necessary representation. + +The polynomial part was similarly represented, as a chain of terms +with packed exponents for a fixed number of variables. There is no +particular significance in this except that the terms were held in +{\em increasing} total order, rather than the decreasing order which +is normal in general purpose systems. This had a number of important +effects on the efficiency of polynomial multiplication in the presence +of a truncation to a certain order. We will return to this point +later. Full details of the representation can be found in +\cite{LectureNotes}. + +The space administration system was based on explicit return rather +than garbage collection. This meant that the system was sometimes +harder to write, but it did mean that much attention was focussed on +efficient reuse of space. It was possible for the user to assist in +this by marking when an expression was needed no longer, and the +compiler then arranged to recycle the space as part of the actual +operation. This degree of control was another assistance in running +of large problems on relatively small machines. + +\subsection{Automatic Linearisation} + +In order to maintain Fourier series in a canonical form it is +necessary to apply the transformations for linearising products of +sine and cosines. These will be familiar to readers of the REDUCE +test program as +\begin{eqnarray} +\cos \theta \cos \phi & \Rightarrow & + (\cos(\theta+\phi)+\cos(\theta-\phi))/2, \\ +\cos \theta \sin \phi & \Rightarrow & + (\sin(\theta+\phi)-\sin(\theta-\phi))/2, \\ +\sin \theta \sin \phi & \Rightarrow & + (\cos(\theta-\phi)-\cos(\theta+\phi))/2, \\ +\cos^2 \theta & \Rightarrow & (1+\cos(2\theta))/2, \\ +\sin^2 \theta & \Rightarrow & (1-\cos(2\theta))/2. +\end{eqnarray} +In CAMAL these transformations are coded directly into the +multiplication routines, and no action is necessary on the part of the +user to invoke them. Of course they cannot be turned off either. + +\subsection{Differentiation and Integration} + +The differentiation of a Fourier series with respect to an angle is +particularly simple. The integration of a Fourier series is a little +more interesting. The terms like $\cos(n u + \ldots)$ are easily +integrated with respect to $u$, but the treatment of terms independent +of the angle would normally introduce a secular term. By convention +in Fourier series these secular terms are ignored, and the constant of +integration is taken as just the terms independent of the angle in the +integrand. This is equivalent to the substitution rules +\begin{eqnarray*} +\sin(n \theta) & \Rightarrow & -(1/n) \cos(n \theta) \\ +\cos(n \theta) & \Rightarrow & (1/n) \sin(n \theta) +\end{eqnarray*} + +In CAMAL these operations were coded directly, and independently of +the differentiation and integration of the polynomial coefficients. + +\subsection{Harmonic Substitution} + +An operation which is of great importance in Fourier operations is the +{\em harmonic substitution}. This is the substitution of the sum of +some angles and a general expression for an angle. In order to +preserve the format, the mechanism uses the translations +\begin{eqnarray*} +\sin(\theta + A) & \Rightarrow & \sin(\theta) \cos(A) + + \cos(\theta) \sin(A) \\ +\cos(\theta + A) & \Rightarrow & \cos(\theta) \cos(A) - + \sin(\theta) \sin(A) \\ +\end{eqnarray*} +and then assuming that the value $A$ is small it can be replaced by +its expansion: +\begin{eqnarray*} +\sin(\theta + A) & \Rightarrow & \sin(\theta) \{1 - A^2/2! + A^4/4!\ldots\} +\\ + & & \cos(\theta) \{A - A^3/3! + A^5/5!\ldots\} \\ +\cos(\theta + A) & \Rightarrow & \cos(\theta) \{1 - A^2/2! + A^4/4!\ldots\} -\\ + & & \sin(\theta) \{A - A^3/3! + A^5/5! \ldots\} \\ +\end{eqnarray*} +If a truncation is set for large powers of the polynomial variables +then the series will terminate. In CAMAL the {\tt HSUB} operation +took five arguments; the original expression, the angle for which +there is a substitution, the new angular part, the expression part +($A$ in the above), and the number of terms required. + +The actual coding of the operation was not as expressed above, but by +the use of Taylor's theorem. As has been noted above the +differentiation of a harmonic series is particularly easy. + +\subsection{Truncation of Series} + +The main use of Fourier series systems is in generating perturbation +expansions, and this implies that the calculations are performed to +some degree of the small quantities. In the original CAMAL all +variables were assumed to be equally small (a restriction removed in +later versions). By maintaining polynomials in increasing maximum +order it is possible to truncate the multiplication of two +polynomials. Assume that we are multiplying the two polynomials +\begin{eqnarray*} + A = a_0 + a_1 + a_2 + \ldots \\ + B = b_0 + b_1 + b_2 + \ldots +\end{eqnarray*} +If we are generating the partial answer +\[ + a_i (b_0 + b_1 + b_2 + \ldots) +\] +then if for some $j$ the product $a_i b_j$ vanishes, then so will all +products $a_i b_k$ for $k>j$. This means that the later terms need +not be generated. In the product of $1+x+x^2+x^3+\ldots+x^{10}$ and +$1+y+y^2+y^3+\ldots+y^10$ to a total order of 10 instead of generating +100 term products only 55 are needed. The ordering can also make the +merging of the new terms into the answer easier. + +\section{Towards a CAMAL Module} + +For the purposes of this work it was necessary to reproduce as many of +the ideas of CAMAL as feasible within the REDUCE framework and +philosophy. It was not intended at this stage to produce a complete +product, and so for simplicity a number of compromises were made with +the ``no restrictions'' principle in REDUCE and the space and time +efficiency of CAMAL. This section describes the basic design +decisions. + +\subsection{Data Structures} + +In a fashion similar to CAMAL a two level data representation is used. +The coefficients are the standard quotients of REDUCE, and their +representation need not concern us further. The angular part is +similar to that of CAMAL, but the ability to pack angle multipliers +and use a single bit for the function are not readily available in +Standard LISP, so instead a longer vector is used. Two versions were +written. One used a balanced tree rather than a linear list for the +Fourier terms, this being a feature of CAMAL which was considered but +never coded. The other uses a simple linear representation for sums. +The angle multipliers are held in a separate vector in order to allow +for future flexibility. This leads to a representation as a vector of +length 6 or 4; +\begin{verbatim} +Version1: [ BalanceBits, Coeff, Function, Angles, LeftTree, RightTree ] +Version2: [ Coeff, Function, Angles, Next ] +\end{verbatim} +where the {\tt Angles} field is a vector of length 8, for the +multipliers. It was decided to forego packing as for portability we +do not know how many to pack into a small integer. The tree system +used is AVL, which needs 2 bits to maintain balance information, but +these are coded as a complete integer field in the vector. We can +expect the improvements implicit in a binary tree to be advantageous +for large expressions, but the additional overhead may reduce its +utility for smaller expressions. + +A separate vector is kept relating the position of an angle to its +print name, and on the property list of each angle the allocation of +its position is kept. So long as the user declares which variables +are to be treated as angles this mechanism gives flexibility which was +lacking in CAMAL. + +\subsection{Linearisation} + +As in the CAMAL system the linearisation of products of sines and +cosines is done not by pattern matching but by direct calculation at +the heart of the product function, where the transformations (1) +through (3) are made in the product of terms function. A side effect +of this is that there are no simple relations which can be used from +within the Fourier multiplication, and so a full addition of partial +products is required. There is no need to apply linearisations +elsewhere as a special case. Addition, differentiation and +integration cannot generate such products, and where they can occur in +substitution the natural algorithm uses the internal multiplication +function anyway. + +\subsection{Substitution} + +Substitution is the main operation of Fourier series. It is useful to +consider three different cases of substitutions. +\begin{enumerate} +\item Angle Expression for Angle: +\item Angle Expression + Fourier Expression for Angle: +\item Fourier Expression for Polynomial Variable. +\end{enumerate} + +The first of these is straightforward, and does not require any +further comment. The second substitution requires a little more care, +but is not significantly difficult to implement. The method follows +the algorithm used in CAMAL, using TAYLOR series. Indeed this is the +main special case for substitution. + +The problem is the last case. Typically many variables used in a +Fourier series program have had a WEIGHT assigned to them. This means +that substitution must take account of any possible WEIGHTs for +variables. The standard code in REDUCE does this in effect by +translating the expression to prefix form, and recalculating the value. +A Fourier series has a large number of coefficients, and so this +operations are repeated rather too often. At present this is the +largest problem area with the internal code, as will be seen in the +discussion of the Disturbing Function calculation. + +\section{Integration with REDUCE} + +The Fourier module needs to be seen as part of REDUCE rather than as a +separate language. This can be seen as having internal and external +parts. + +\subsection{Internal Interface} + +The Fourier expressions need to co-exist with the normal REDUCE syntax +and semantics. The prototype version does this by (ab)using the +module method, based in part on the TPS code \cite{Barnes}. Of course +Fourier series are not constant, and so are not really domain +elements. However by asserting that Fourier series form a ring of +constants REDUCE can arrange to direct basic operations to the Fourier +code for addition, subtraction, multiplication and the like. + +The main interface which needs to be provided is a simplification +function for Fourier expressions. This needs to provide compilation +for linear sums of angles, as well as constructing sine and cosine +functions, and creating canonical forms. + +\subsection{User Interface} + +The creation of {\tt HDIFF} and {\tt HINT} functions for +differentiation disguises this. An unsatisfactory aspect of the +interface is that the tokens {\tt SIN} and {\tt COS} are already in +use. The prototype uses the operator form +\begin{verbatim} + fourier sin(u) +\end{verbatim} +to introduce harmonically represented sine functions. An alternative of +using the tokens {\tt F\_SIN} and {\tt F\_COS} is also available. + +It is necessary to declare the names of the angles, which is achieved +with the declaration +\begin{verbatim} + harmonic theta, phi; +\end{verbatim} + +At present there is no protection against using a variable as both an +angle and a polynomial varaible. This will nooed to be done in a +user-oriented version. + +\section{The Simple Experiments} + +The REDUCE test file contains a simple example of a Fourier +calculation, determining the value of $(a_1 \cos({wt}) + a_3 +\cos(3{wt}) + b_1 \sin({wt}) + b_3 \sin(3{wt}))^3$. For the purposes +of this system this is too trivial to do more than confirm the correct +answers. + +The simplest non-trivial calculation for a Fourier series manipulator +is to solve Kepler's equation for the eccentric anomoly E in terms of +the mean anomoly u, and the eccentricity of an orbit e, considered as a +small quantity +\[ + E = u + e \sin E +\] +The solution procedes by repeated approximation. Clearly the initial +approximation is $E_0 = u$. The $n^{th}$ approximation can be written +as $u + A_n$, and so $A_n$ can be calculated by +\[ + A_k = e \sin (u + A_{k-1}) +\] +This is of course precisely the case for which the HSUB operation is +designed, and so in order to calculate $E_n - u$ all one requires is +the code +\begin{verbatim} + bige := fourier 0; + for k:=1:n do << + wtlevel k; + bige:=fourier e * hsub(fourier(sin u), u, u, bige, k); + >>; + write "Kepler Eqn solution:", bige$ +\end{verbatim} + +It is possible to create a regular REDUCE program to simulate this (as +is done for example in Barton and Fitch\cite{Barton72}, page 254). +Comparing these two programs indicates substantial advantages to the +Fourier module, as could be expected. +\medskip +\begin{center} +\begin{tabular}{ | c | l l |} +\multicolumn{3}{c}{\bf Solving Kepler's Equation} \\ +\hline +Order & REDUCE & Fourier Module \\ +5 & 9.16 & 2.48 \\ +6 & 17.40 & 4.56 \\ +7 & 33.48 & 8.06 \\ +8 & 62.76 & 13.54 \\ +9 & 116.06 & 21.84 \\ +10 & 212.12 & 34.54 \\ +11 & 381.78 & 53.94 \\ +12 & 692.56 & 82.96 \\ +13 & 1247.54 & 125.86 \\ +14 & 2298.08 & 187.20 \\ +15 & 4176.04 & 275.60 \\ +16 & 7504.80 & 398.62 \\ +17 & 13459.80 & 569.26 \\ +18 & *** & 800.00 \\ +19 & *** & 1116.92 \\ +20 & *** & 1536.40 \\ +\hline +\end{tabular} +\end{center} +\medskip +These results were with the linear representation of Fourier series. +The tree representation was slightly slower. The ten-fold speed-up +for the 13th order is most satisfactory. + +\section{A Medium-Sized Problem} + +Fourier series manipulators are primarily designed for large-scale +calculations, but for the demonstration purposes of this project a +medium problem is considered. The first stage in calculating the +orbit of the Moon using the Delaunay theory (of perturbed elliptic +motion for the restricted 3-body problem) is to calculate the energy +of the Moon's motion about the Earth --- the Hamiltonian of the +system. This is the calculation we use for comparisons. + +\subsection{Mathematical Background} + +The full calculation is described in detail in \cite{Brown}, but a +brief description is given here for completeness, and to grasp the +extent of the calculation. + +Referring to the figure 1 which gives the cordinate system, the basic +equations are +\begin{eqnarray} +S & = & (1-\gamma ^2)\cos(f + g +h -f' -g' -h') ++ \gamma ^2 cos(f + g -h +f' +g' +h') \\ +r & = & a (1 - e \cos E) \\ +l & = & E - e \sin E \\ +a & = & r {{\bf d} E} \over {{\bf d} l} \\ +r ^2 {{\bf d} f} \over {{\bf d} l} & = & a^2 (1 - e^2)^{1 \over 2}\\ +R & = & m' {a^2 \over {a'} ^3} {{a'}\over {r +'}} \left \{ \left ({r \over a}\right )^2 +\left ({{a'} \over {r'}}\right )^2 P_2(S) + +\left ({a \over {a'}}\right )\left +({r \over a}\right )^3 \left ({{a'} \over {r'}}\right )^3 P_3(S) ++ \ldots \right \} +\end{eqnarray} + +There are similar equations to (7) to (10) for the quantities $r'$, +$a'$, $e'$, $l'$, $E'$ and $f'$ which refer to the position of the Sun +rather than the Moon. The problem is to calculate the expression $R$ +as an expansion in terms of the quantities $e$, $e'$, $\gamma$, +$a/a'$, $l$, $g$, $h$, $l'$, $g'$ and $h'$. The first three +quantities are small quantities of the first order, and $a/a'$ is of +second order. + +The steps required are +\begin{enumerate} +\item Solve the Kepler equation (8) +\item Substiture into (7) to give $r/a$ in terms of $e$ and $l$. +\item Calculate $a/r$ from (9) and $f$ from (10) +\item Substitute for $f$ and $f'$ into $S$ using (6) +\item Calculate $R$ from $S$, $a'/r'$ and $r/a$ +\end{enumerate} + +The program is given in the Appendix. + +\subsection{Results} + +The Lunar Disturbing function was calculated by a direct coding of the +previous sections' mathematics. The program was taken from Barton +and Fitch \cite{Barton72} with just small changes to generalise it for +any order, and to make it acceptable for Reduce3.4. The Fourier +program followed the same pattern, but obviously used the {\tt HSUB} +operation as appropriate and the harmonic integration. It is very +similar to the CAMAL program in \cite{Barton72}. + +The disturbing function was calculated to orders 2, 4 and 6 using +Cambridge LISP on an HLH Orion 1/05 (Intergraph Clipper), with the +three programs $\alpha$) Reduce3.4, $\beta$) Reduce3.4 + Camal Linear +Module and $\gamma$) Reduce3.4 + Camal AVL Module. The timings for +CPU seconds (excluding garbage collection time) are summarised the +following table: +\medskip +\begin{center} +\begin{tabular}{ | c || l | l | l |} +\hline +Order of DDF & Reduce & Camal Linear & Camal Tree \\ +\hline +2 & 23.68 & 11.22 & 12.9 \\ +4 & 429.44 & 213.56 & 260.64 \\ +6 & $>$7500 & 3084.62 & 3445.54 \\ +\hline +%%% Linear n=4 138.72 (4Mb + unsafe vector access + recurrance) +%%% Linear n=6 1870.10 (4Mb + unsafe vector access + recurrance) +\end{tabular} +\end{center} +\medskip + +If these numbers are normalised so REDUCE calculating the DDF is 100 +units for each order the table becomes +\medskip +\begin{center} +\begin{tabular}{ | c || l | l | l |} +\hline +Order of DDF & Reduce & Camal Linear & Camal Tree \\ \hline +2 & 100 & 47.38 & 54.48 \\ +4 & 100 & 49.73 & 60.69 \\ +6 & 100 & $<$41.13 & $<$45.94 \\ +\hline +\end{tabular} +\end{center} +\medskip + +From this we conclude that a doubling of speed is about correct, and +although the balanced tree system is slower as the problem size +increases the gap between it and the simpler linear system is +narrowing. + +It is disappointing that the ratio is not better, nor the absolute +time less. It is worth noting in this context that Jefferys claimed +that the sixth order DDF took 30s on a CDC6600 with TRIGMAN in 1970 +\cite{Jefferys}, and Barton and Fitch took about 1s for the second +order DDF on TITAN with CAMAL \cite{Barton72}. A closer look at the +relative times for individual sections of the program shows that the +substitution case of replacing a polynomial variable by a Fourier +series is only marginally faster than the simple REDUCE program. In +the DDF program this operation is only used once in a major form, +substituting into the Legendre polynomials, which have been previously +calculated by Rodrigues formula. This suggests that we replace this +with the recurrence relationship. + +Making this change actually slows down the normal REDUCE by a small +amount but makes a significant change to the Fourier module; it +reduces the run time for the 6th order DDF from 3084.62s to 2002.02s. +This gives some indication of the problems with benchmarks. What is +clear is that the current implementation of substitution of a Fourier +series for a polynomial variable is inadequate. + +\section{Conclusion} + +The Fourier module is far from complete. The operations necessary for +the solution of Duffing's and Hill's equations are not yet written, +although they should not cause much problem. The main defficiency is +the treatment of series truncation; at present it relies on the REDUCE +WTLEVEL mechanism, and this seems too coarse for efficient truncation. +It would be possible to re-write the polynomial manipulator as well, +while retaining the REDUCE syntax, but that seems rather more than one +would hope. + +The real failure so far is the large time lag between the REDUCE-based +system on a modern workstation against a mainframe of 25 years ago +running a special system. The CAMAL Disturbing function program could +calculate the tenth order with a maximum of 32K words (about +192Kbytes) whereas this system failed to calculate the eigth order in +4Mbytes (taking 2000s before failing). I have in my archives the +output from the standard CAMAL test suite, which includes a sixth +order DDF on an IBM 370/165 run on 2 June 1978, taking 22.50s and +using a maximum of 15459 words of memory for heap --- or about +62Kbytes. A rough estimate is that the Orion 1/05 is comparable in +speed to the 360/165, but with more real memory and virtual memory. + +However, a simple Fourier manipulator has been created for REDUCE which +performs between twice and three times the speed of REDUCE using +pattern matching. It has been shown that this system is capable of +performing the calculations of celestial mechanics, but it still +seriously lags behind the efficiency of the specialist systems of +twenty years before. It is perhaps fortunate that it was not been +possible to compare it with a modern specialist system. + +There is still work to do to provide a convenient user interface, but +it is intended to develop the system in this direction. It would be +pleasant to have again a system of the efficiency of CAMAL(F). + +I would like to thank Codemist Ltd for the provision of computing +resources for this project, and David Barton who taught be so much +about Fourier series and celstial mechanics. Thank are also due to +the National Health Service, without whom this work and paper could not +have been produced. + +\section*{Appendix: The DDF Function} +\begin{verbatim} +array p(n/2+2); +harmonic u,v,w,x,y,z; +weight e=1, b=1, d=1, a=1; + +%% Generate Legendre Polynomials to sufficient order +for i:=2:n/2+2 do << + p(i):=(h*h-1)^i; + for j:=1:i do p(i):=df(p(i),h)/(2j) +>>; + +%%%%%%%%%%%%%%%% Step1: Solve Kepler equation +bige := fourier 0; +for k:=1:n do << + wtlevel k; + bige:=fourier e * hsub(fourier(sin u), u, u, bige, k); +>>; + +%% Ensure we do not calculate things of too high an order +wtlevel n; + +%%%%%%%%%%%%%%%% Step 2: Calculate r/a in terms of e and l +dd:=-e*e; hh:=3/2; j:=1; cc := 1; +for i:=1:n/2 do << + j:=i*j; hh:=hh-1; cc:=cc+hh*(dd^i)/j +>>; +bb:=hsub(fourier(1-e*cos u), u, u, bige, n); +aa:=fourier 1+hdiff(bige,u); ff:=hint(aa*aa*fourier cc,u); + +%%%%%%%%%%%%%%%% Step 3: a/r and f +uu := hsub(bb,u,v); uu:=hsub(uu,e,b); +vv := hsub(aa,u,v); vv:=hsub(vv,e,b); +ww := hsub(ff,u,v); ww:=hsub(ww,e,b); + +%%%%%%%%%%%%%%%% Step 4: Substitute f and f' into S +yy:=ff-ww; zz:=ff+ww; +xx:=hsub(fourier((1-d*d)*cos(u)),u,u-v+w-x-y+z,yy,n)+ + hsub(fourier(d*d*cos(v)),v,u+v+w+x+y-z,zz,n); + +%%%%%%%%%%%%%%%% Step 5: Calculate R +zz:=bb*vv; yy:=zz*zz*vv; + +on fourier; +for i := 2:n/2+2 do << + wtlevel n+4-2i; p(i) := hsub(p(i), h, xx) >>; + +wtlevel n; +for i:=n/2+2 step -1 until 3 do + p(n/2+2):=fourier(a*a)*zz*p(n/2+2)+p(i-1); +yy*p(n/2+2); + +\end{verbatim} +\newpage +\bibliographystyle{plain} +\bibliography{camal} + +\end{document} Index: r36/doc/CHANGEVR.TEX ================================================================== --- r36/doc/CHANGEVR.TEX +++ r36/doc/CHANGEVR.TEX @@ -1,183 +1,183 @@ -\newcommand{\definedas}{\stackrel{\triangle}{=}} -\newcommand{\spc}{\;\;\;\;\;} -\newcommand{\mspc}{\;\;\;\;\;\;\;\;\;\;} -\newcommand{\lspc}{\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;} - -\documentstyle[fleqn,11pt]{article} - -\renewcommand{\baselinestretch}{1.1} -\newcommand{\eg}[1]{\begin{quote}{\tt #1} \end{quote}} -\setlength{\textwidth}{15cm} -\addtolength{\oddsidemargin}{-1cm} - -\title{ CHANGEVR, \\ - A REDUCE Facility \\ - to \\ - Perform Change of Independent Variable(s)\\ - in \\ - Differential Equations\\[2cm] - } -\author{ - G. \"{U}\c{c}oluk - \thanks{Email address: UCOLUK@TRMETU.BITNET} - \\ - Department of Physics \\ - Middle East Technical University \\ - Ankara, Turkey - } -\date{October 1989} - -\begin{document} -\maketitle -\newpage - -\section{Introduction} -The mathematics behind the change of independent variable(s) in differential -equations is quite straightforward. It is basically the application of the -chain rule. If the dependent variable of the differential equation is $F$, -the independent variables are $x_{i}$ and the new independent variables are -$u_{i}$ (where ${\scriptstyle i=1\ldots n}$) then the first derivatives are: -\[ - \frac{\partial F}{\partial x_{i}} = \frac{\partial F}{\partial u_{j}} - \frac{\partial u_{j}}{\partial x_{i}} -\] -We assumed Einstein's summation convention. Here the problem is to -calculate the $\partial u_{j}/\partial x_{i}$ terms if the change of variables -is given by -\[ - x_{i} = f_{i}(u_{1},\ldots,u_{n}) -\] -The first thought might be solving the above given equations for $u_{j}$ and -then differentiating them with respect to $x_{i}$, then again making use of the -equations above, substituting new variables for the old ones in the calculated -derivatives. This is not always a preferable way to proceed. Mainly because -the functions $f_{i}$ may not always be easily invertible. Another approach -that makes use of the Jacobian is better. Consider the above given equations -which relate the old variables to the new ones. Let us differentiate them: -\begin{eqnarray*} - \frac{\partial x_{j}}{\partial x_{i}} & = & - \frac{\partial f_{j}}{\partial x_{i}} \\ - \delta_{ij} & = & - \frac{\partial f_{j}}{\partial u_{k}} - \frac{\partial u_{k}}{\partial x_{i}} -\end{eqnarray*} -The first derivative is nothing but the $(j,k)$ th entry of the Jacobian matrix. - -So if we speak in matrix language -\[ {\bf 1 = J \cdot D} \] -where we defined the Jacobian -\[ {\bf J}_{ij} \definedas \frac{\partial f_{i}}{\partial u_{j}} \] -and the matrix of the derivatives we wanted to obtain as -\[ {\bf D}_{ij} \definedas \frac{\partial u_{i}}{\partial x_{j}}. \] -If the Jacobian has a non-vanishing determinant then it is invertible and -we are able to write from the matrix equation above: -\[ {\bf D = J^{-1}} \] -so finally we have what we want -\[ - \frac{\partial u_{i}}{\partial x_{j}} = \left[{\bf J^{-1}}\right]_{ij} -\] - -The higher derivatives are obtained by the successive application of the chain -rule and using the definitions of the old variables in terms of the new ones. It - -can be easily verified that the only derivatives that are needed to be -calculated are the first order ones which are obtained above. - -\section{How to Use CHANGEVR} -{\bf This facility requires the matrix package to be present in the session}. -So if it is not autoloaded in your REDUCE implementation, say -\eg{LOAD\PACKAGE MATRIX;} -in the REDUCE environment. Then load {\tt CHANGEVR} by the statement: -\eg{LOAD\_PACKAGE CHANGEVR\$} -Now the REDUCE function {\tt CHANGEVAR} is ready to use. {\bf Note: The -package is named CHANGEVR, but the function has the name CHANGEVAR}. The -function {\tt CHANGEVAR} has (at least) four different arguments. Here we -give a list them: -\begin{itemize} -\item {\bf FIRST ARGUMENT} \\ - Is a list of the dependent variables of the differential equation. - They shall be enclosed in a pair of curly braces and separated by commas. - If there is only one dependent variable there is no need for the curly - braces. -\item {\bf SECOND ARGUMENT} \\ - Is a list of the {\bf new} independent variables. Similar to what is said - for the first argument, these shall also be separated by commas, - enclosed in curly braces and the curly braces can be omitted if there is - only one new variable. -\item {\bf THIRD ARGUMENT} \\ - Is a list of equations separated by commas, where each of the equation - is of the form - \eg{{\em old variable} = {\em a function in new variables}} - The left hand side cannot be a non-kernel structure. In this argument - the functions which give the old variables in terms of the new ones are - introduced. It is possible to omit totally the curly braces which enclose - the list. {\bf Please note that only for this argument it is allowed to - omit the curly braces even if the list has \underline{more than one} - items}. -\item {\bf LAST ARGUMENT} \\ - Is a list of algebraic expressions which evaluates to differential - equations, separated by commas, enclosed in curly braces. - So, variables in which differential equations are already stored may be - used freely. Again it is possible to omit the curly braces if there is - only {\bf one} differential equation. -\end{itemize} - -If the last argument is a list then the result of {\tt CHANGEVAR} is also a -list. - -It is possible to display the entries of the inverse Jacobian, explained -in the introduction. To do so, turn {\tt ON} the flag {DISPJACOBIAN} by a -statement: \eg{ON DISPJACOBIAN;} - -\section{AN EXAMPLE\ldots\ldots The 2-dim. Laplace Equation} -The 2-dimensional Laplace equation in cartesian coordinates is: -\[ - \frac{\partial^{2} u}{\partial x^{2}} + - \frac{\partial^{2} u}{\partial y^{2}} = 0 -\] -Now assume we want to obtain the polar coordinate form of Laplace equation. -The change of variables is: -\[ - x = r \cos \theta, \mspc y = r \sin \theta -\] -The solution using {\tt CHANGEVAR} (of course after it is properly loaded) -is as follows -\eg{CHANGEVAR(\{u\},\{r,theta\},\{x=r*cos theta,y=r*sin theta\}, \\ - \hspace*{2cm} \{df(u(x,y),x,2)+df(u(x,y),y,2)\} )} -Here we could omit the curly braces in the first and last arguments (because -those lists have only one member) and the curly braces in the third argument -(because they are optional), but you cannot leave off the curly braces in the -second argument. So one could equivalently write -\eg{CHANGEVAR(u,\{r,theta\},x=r*cos theta,y=r*sin theta, \\ - \hspace*{2cm} df(u(x,y),x,2)+df(u(x,y),y,2) )} - -If you have tried out the above example, you will notice that the denominator -contains a $\cos^{2} \theta + \sin^{2} \theta$ which is actually equal to $1$. -This has of course nothing to do with the {\tt CHANGEVAR} facility introduced -here. One has to be overcome these pattern matching problems by the -conventional methods REDUCE provides (a {\tt LET} statement, for example, -will fix it). - -Secondly you will notice that your {\tt u(x,y)} operator has changed to -{\tt u(r,theta)} in the result. Nothing magical about this. That is just what -we do with pencil and paper. {\tt u(r,theta)} represents the the transformed -dependent variable. - -\section{ANOTHER EXAMPLE\ldots\ldots An Euler Equation} -Consider a differential equation which is of Euler type, for instance: -\[ - x^{3}y''' - 3 x^{2}y'' + 6 x y' - 6 y = 0 -\] -Where prime denotes differentiation with respect to $x$. As is well known, -Euler type of equations are solved by a change of variable: -\[ - x = e^{u} -\] -So our {\tt CHANGEVAR} call reads as follows: -\eg{CHANGEVAR(y, u, x=e**u, x**3*df(y(x),x,3)- \\ - \hspace*{2cm} 3*x**2*df(y(x),x,2)+6*x*df(y(x),x)-6*y(x))} - -\end{document} - - - +\newcommand{\definedas}{\stackrel{\triangle}{=}} +\newcommand{\spc}{\;\;\;\;\;} +\newcommand{\mspc}{\;\;\;\;\;\;\;\;\;\;} +\newcommand{\lspc}{\;\;\;\;\;\;\;\;\;\;\;\;\;\;\;} + +\documentstyle[fleqn,11pt]{article} + +\renewcommand{\baselinestretch}{1.1} +\newcommand{\eg}[1]{\begin{quote}{\tt #1} \end{quote}} +\setlength{\textwidth}{15cm} +\addtolength{\oddsidemargin}{-1cm} + +\title{ CHANGEVR, \\ + A REDUCE Facility \\ + to \\ + Perform Change of Independent Variable(s)\\ + in \\ + Differential Equations\\[2cm] + } +\author{ + G. \"{U}\c{c}oluk + \thanks{Email address: UCOLUK@TRMETU.BITNET} + \\ + Department of Physics \\ + Middle East Technical University \\ + Ankara, Turkey + } +\date{October 1989} + +\begin{document} +\maketitle +\newpage + +\section{Introduction} +The mathematics behind the change of independent variable(s) in differential +equations is quite straightforward. It is basically the application of the +chain rule. If the dependent variable of the differential equation is $F$, +the independent variables are $x_{i}$ and the new independent variables are +$u_{i}$ (where ${\scriptstyle i=1\ldots n}$) then the first derivatives are: +\[ + \frac{\partial F}{\partial x_{i}} = \frac{\partial F}{\partial u_{j}} + \frac{\partial u_{j}}{\partial x_{i}} +\] +We assumed Einstein's summation convention. Here the problem is to +calculate the $\partial u_{j}/\partial x_{i}$ terms if the change of variables +is given by +\[ + x_{i} = f_{i}(u_{1},\ldots,u_{n}) +\] +The first thought might be solving the above given equations for $u_{j}$ and +then differentiating them with respect to $x_{i}$, then again making use of the +equations above, substituting new variables for the old ones in the calculated +derivatives. This is not always a preferable way to proceed. Mainly because +the functions $f_{i}$ may not always be easily invertible. Another approach +that makes use of the Jacobian is better. Consider the above given equations +which relate the old variables to the new ones. Let us differentiate them: +\begin{eqnarray*} + \frac{\partial x_{j}}{\partial x_{i}} & = & + \frac{\partial f_{j}}{\partial x_{i}} \\ + \delta_{ij} & = & + \frac{\partial f_{j}}{\partial u_{k}} + \frac{\partial u_{k}}{\partial x_{i}} +\end{eqnarray*} +The first derivative is nothing but the $(j,k)$ th entry of the Jacobian matrix. + +So if we speak in matrix language +\[ {\bf 1 = J \cdot D} \] +where we defined the Jacobian +\[ {\bf J}_{ij} \definedas \frac{\partial f_{i}}{\partial u_{j}} \] +and the matrix of the derivatives we wanted to obtain as +\[ {\bf D}_{ij} \definedas \frac{\partial u_{i}}{\partial x_{j}}. \] +If the Jacobian has a non-vanishing determinant then it is invertible and +we are able to write from the matrix equation above: +\[ {\bf D = J^{-1}} \] +so finally we have what we want +\[ + \frac{\partial u_{i}}{\partial x_{j}} = \left[{\bf J^{-1}}\right]_{ij} +\] + +The higher derivatives are obtained by the successive application of the chain +rule and using the definitions of the old variables in terms of the new ones. It + +can be easily verified that the only derivatives that are needed to be +calculated are the first order ones which are obtained above. + +\section{How to Use CHANGEVR} +{\bf This facility requires the matrix package to be present in the session}. +So if it is not autoloaded in your REDUCE implementation, say +\eg{LOAD\PACKAGE MATRIX;} +in the REDUCE environment. Then load {\tt CHANGEVR} by the statement: +\eg{LOAD\_PACKAGE CHANGEVR\$} +Now the REDUCE function {\tt CHANGEVAR} is ready to use. {\bf Note: The +package is named CHANGEVR, but the function has the name CHANGEVAR}. The +function {\tt CHANGEVAR} has (at least) four different arguments. Here we +give a list them: +\begin{itemize} +\item {\bf FIRST ARGUMENT} \\ + Is a list of the dependent variables of the differential equation. + They shall be enclosed in a pair of curly braces and separated by commas. + If there is only one dependent variable there is no need for the curly + braces. +\item {\bf SECOND ARGUMENT} \\ + Is a list of the {\bf new} independent variables. Similar to what is said + for the first argument, these shall also be separated by commas, + enclosed in curly braces and the curly braces can be omitted if there is + only one new variable. +\item {\bf THIRD ARGUMENT} \\ + Is a list of equations separated by commas, where each of the equation + is of the form + \eg{{\em old variable} = {\em a function in new variables}} + The left hand side cannot be a non-kernel structure. In this argument + the functions which give the old variables in terms of the new ones are + introduced. It is possible to omit totally the curly braces which enclose + the list. {\bf Please note that only for this argument it is allowed to + omit the curly braces even if the list has \underline{more than one} + items}. +\item {\bf LAST ARGUMENT} \\ + Is a list of algebraic expressions which evaluates to differential + equations, separated by commas, enclosed in curly braces. + So, variables in which differential equations are already stored may be + used freely. Again it is possible to omit the curly braces if there is + only {\bf one} differential equation. +\end{itemize} + +If the last argument is a list then the result of {\tt CHANGEVAR} is also a +list. + +It is possible to display the entries of the inverse Jacobian, explained +in the introduction. To do so, turn {\tt ON} the flag {DISPJACOBIAN} by a +statement: \eg{ON DISPJACOBIAN;} + +\section{AN EXAMPLE\ldots\ldots The 2-dim. Laplace Equation} +The 2-dimensional Laplace equation in cartesian coordinates is: +\[ + \frac{\partial^{2} u}{\partial x^{2}} + + \frac{\partial^{2} u}{\partial y^{2}} = 0 +\] +Now assume we want to obtain the polar coordinate form of Laplace equation. +The change of variables is: +\[ + x = r \cos \theta, \mspc y = r \sin \theta +\] +The solution using {\tt CHANGEVAR} (of course after it is properly loaded) +is as follows +\eg{CHANGEVAR(\{u\},\{r,theta\},\{x=r*cos theta,y=r*sin theta\}, \\ + \hspace*{2cm} \{df(u(x,y),x,2)+df(u(x,y),y,2)\} )} +Here we could omit the curly braces in the first and last arguments (because +those lists have only one member) and the curly braces in the third argument +(because they are optional), but you cannot leave off the curly braces in the +second argument. So one could equivalently write +\eg{CHANGEVAR(u,\{r,theta\},x=r*cos theta,y=r*sin theta, \\ + \hspace*{2cm} df(u(x,y),x,2)+df(u(x,y),y,2) )} + +If you have tried out the above example, you will notice that the denominator +contains a $\cos^{2} \theta + \sin^{2} \theta$ which is actually equal to $1$. +This has of course nothing to do with the {\tt CHANGEVAR} facility introduced +here. One has to be overcome these pattern matching problems by the +conventional methods REDUCE provides (a {\tt LET} statement, for example, +will fix it). + +Secondly you will notice that your {\tt u(x,y)} operator has changed to +{\tt u(r,theta)} in the result. Nothing magical about this. That is just what +we do with pencil and paper. {\tt u(r,theta)} represents the the transformed +dependent variable. + +\section{ANOTHER EXAMPLE\ldots\ldots An Euler Equation} +Consider a differential equation which is of Euler type, for instance: +\[ + x^{3}y''' - 3 x^{2}y'' + 6 x y' - 6 y = 0 +\] +Where prime denotes differentiation with respect to $x$. As is well known, +Euler type of equations are solved by a change of variable: +\[ + x = e^{u} +\] +So our {\tt CHANGEVAR} call reads as follows: +\eg{CHANGEVAR(y, u, x=e**u, x**3*df(y(x),x,3)- \\ + \hspace*{2cm} 3*x**2*df(y(x),x,2)+6*x*df(y(x),x)-6*y(x))} + +\end{document} + + + Index: r36/doc/COMPACT.BIB ================================================================== --- r36/doc/COMPACT.BIB +++ r36/doc/COMPACT.BIB @@ -1,11 +1,11 @@ -@INPROCEEDINGS{Hornfeldt:82, - AUTHOR = "L. Hornfeldt", - TITLE = "A Sum-Substitutor used as Trigonometric Simplifier", - BOOKTITLE = "Proc. {EUROCAM} '82", - PAGES = "188-195", - SERIES = "Lecture Notes on Comp. Science", - NUMBER = 144, - PUBLISHER = "Springer-Verlag", - ADDRESS = "Berlin", - YEAR = 1982} - +@INPROCEEDINGS{Hornfeldt:82, + AUTHOR = "L. Hornfeldt", + TITLE = "A Sum-Substitutor used as Trigonometric Simplifier", + BOOKTITLE = "Proc. {EUROCAM} '82", + PAGES = "188-195", + SERIES = "Lecture Notes on Comp. Science", + NUMBER = 144, + PUBLISHER = "Springer-Verlag", + ADDRESS = "Berlin", + YEAR = 1982} + Index: r36/doc/COMPACT.TEX ================================================================== --- r36/doc/COMPACT.TEX +++ r36/doc/COMPACT.TEX @@ -1,107 +1,107 @@ -\documentstyle[11pt,reduce]{article} -\title{COMPACT: Reduction of a Polynomial in the Presence of Side Relations} -\date{} -\author{Anthony C. Hearn\\ RAND\\ -Santa Monica CA 90407-2138\\ -Email: hearn@rand.org} -\begin{document} -\maketitle - -\index{COMPACT package} \index{side relations} \index{relations ! side} -{COMPACT} is a package of functions for the reduction of a polynomial in -the presence of side relations. The package defines one operator {COMPACT} -\index{COMPACT operator} -whose syntax is: - -\begin{quote} -\k{COMPACT}(\s{expression}, \s{list}):\s{expression} -\end{quote} - -\s{expression} can be any well-formed algebraic expression, and -\s{list} an expression whose value is a list -of either expressions or equations. For example - -\begin{verbatim} - compact(x**2+y**3*x-5y,{x+y-z,x-y-z1}); - compact(sin(x)**10*cos(x)**3+sin(x)**8*cos(x)**5, - {cos(x)**2+sin(x)**2=1}); - let y = {cos(x)**2+sin(x)**2-1}; - compact(sin(x)**10*cos(x)**3+sin(x)**8*cos(x)**5,y); -\end{verbatim} - -{COMPACT} applies the relations to the expression so that an equivalent -expression results with as few terms as possible. The method used is -briefly as follows: - -\begin{enumerate} -\item Side relations are applied separately to numerator and denominator, so -that the problem is reduced to the reduction of a polynomial with respect to -a set of polynomial side relations. - -\item Reduction is performed sequentially, so that the problem is reduced -further to the reduction of a polynomial with respect to a single -polynomial relation. - -\item The polynomial being reduced is reordered so that the variables -(kernels) occurring in the side relation have least precedence. - -\item Each coefficient of the remaining kernels (which now only contain -the kernels -in the side relation) is reduced with respect to that side relation. - -\item A polynomial quotient/remainder calculation is performed on the -coefficient. The remainder is -used instead of the original if it has fewer terms. - -\item The remaining expression is reduced with respect to the side relation -using a ``nearest neighbor'' approach. -\end{enumerate} - -As with the traveling salesman problem, a nearest neighbor approach to -reduction does not necessarily achieve an optimal result. In most cases -it will be within a factor of two from the optimal result, but in extreme -cases it may be much further away. - -Another source of sub-optimal results is that the given expression -is reduced sequentially with respect to the side relations. So for -example in the case - -\begin{verbatim} - compact((a+b+c)*(a-b-c)*(-a+b-c)*(-a-b+c), - {x1=a+b+c,x2=a-b-c,x3=-a+b-c,x4=-a-b+c}) -\end{verbatim} - -the expression is actually $x_{1}x_{2}x_{3}x_{4}$, but any given relation -cannot reduce the size of the expanded form -$a^{4}-2a^{2}b^{2}-2a^{2}c^{2}+b^{4}-2b^{2}c^{2}+c^{4}$ -of the original expression, and so the final result is far from optimal. - -The only other program we have heard about that considers the compaction -problem is that of Hornfeldt~\cite{Hornfeldt:82}. -However, Hornfeldt reorders expressions so that the kernels in a side -relation have highest order. Consequently, their coefficients are -polynomials rather than integers or other constants as in our approach. -Furthermore, it is not clear just how general Hornfeldt's approach is from -his description, since he only talks about sine and cosine substitutions. - -There are a number of projects that this work immediately suggests. For -example: - -\begin{enumerate} -\item How does one do the reduction with the side relations in parallel? -The above example shows this is necessary for an optimal solution. - -\item Should one reduce the side relations to a Groebner or other basis -before doing any reduction? - -\item Should one check for the consistency of the basis? - -\item How does one do factorization and gcds on a polynomial whose -variables are related by a set of side relations? -\end{enumerate} - -The author would be interested in hearing from anyone wishing to work with -him on any of these problems. -\bibliography{compact} -\bibliographystyle{plain} -\end{document} +\documentstyle[11pt,reduce]{article} +\title{COMPACT: Reduction of a Polynomial in the Presence of Side Relations} +\date{} +\author{Anthony C. Hearn\\ RAND\\ +Santa Monica CA 90407-2138\\ +Email: hearn@rand.org} +\begin{document} +\maketitle + +\index{COMPACT package} \index{side relations} \index{relations ! side} +{COMPACT} is a package of functions for the reduction of a polynomial in +the presence of side relations. The package defines one operator {COMPACT} +\index{COMPACT operator} +whose syntax is: + +\begin{quote} +\k{COMPACT}(\s{expression}, \s{list}):\s{expression} +\end{quote} + +\s{expression} can be any well-formed algebraic expression, and +\s{list} an expression whose value is a list +of either expressions or equations. For example + +\begin{verbatim} + compact(x**2+y**3*x-5y,{x+y-z,x-y-z1}); + compact(sin(x)**10*cos(x)**3+sin(x)**8*cos(x)**5, + {cos(x)**2+sin(x)**2=1}); + let y = {cos(x)**2+sin(x)**2-1}; + compact(sin(x)**10*cos(x)**3+sin(x)**8*cos(x)**5,y); +\end{verbatim} + +{COMPACT} applies the relations to the expression so that an equivalent +expression results with as few terms as possible. The method used is +briefly as follows: + +\begin{enumerate} +\item Side relations are applied separately to numerator and denominator, so +that the problem is reduced to the reduction of a polynomial with respect to +a set of polynomial side relations. + +\item Reduction is performed sequentially, so that the problem is reduced +further to the reduction of a polynomial with respect to a single +polynomial relation. + +\item The polynomial being reduced is reordered so that the variables +(kernels) occurring in the side relation have least precedence. + +\item Each coefficient of the remaining kernels (which now only contain +the kernels +in the side relation) is reduced with respect to that side relation. + +\item A polynomial quotient/remainder calculation is performed on the +coefficient. The remainder is +used instead of the original if it has fewer terms. + +\item The remaining expression is reduced with respect to the side relation +using a ``nearest neighbor'' approach. +\end{enumerate} + +As with the traveling salesman problem, a nearest neighbor approach to +reduction does not necessarily achieve an optimal result. In most cases +it will be within a factor of two from the optimal result, but in extreme +cases it may be much further away. + +Another source of sub-optimal results is that the given expression +is reduced sequentially with respect to the side relations. So for +example in the case + +\begin{verbatim} + compact((a+b+c)*(a-b-c)*(-a+b-c)*(-a-b+c), + {x1=a+b+c,x2=a-b-c,x3=-a+b-c,x4=-a-b+c}) +\end{verbatim} + +the expression is actually $x_{1}x_{2}x_{3}x_{4}$, but any given relation +cannot reduce the size of the expanded form +$a^{4}-2a^{2}b^{2}-2a^{2}c^{2}+b^{4}-2b^{2}c^{2}+c^{4}$ +of the original expression, and so the final result is far from optimal. + +The only other program we have heard about that considers the compaction +problem is that of Hornfeldt~\cite{Hornfeldt:82}. +However, Hornfeldt reorders expressions so that the kernels in a side +relation have highest order. Consequently, their coefficients are +polynomials rather than integers or other constants as in our approach. +Furthermore, it is not clear just how general Hornfeldt's approach is from +his description, since he only talks about sine and cosine substitutions. + +There are a number of projects that this work immediately suggests. For +example: + +\begin{enumerate} +\item How does one do the reduction with the side relations in parallel? +The above example shows this is necessary for an optimal solution. + +\item Should one reduce the side relations to a Groebner or other basis +before doing any reduction? + +\item Should one check for the consistency of the basis? + +\item How does one do factorization and gcds on a polynomial whose +variables are related by a set of side relations? +\end{enumerate} + +The author would be interested in hearing from anyone wishing to work with +him on any of these problems. +\bibliography{compact} +\bibliographystyle{plain} +\end{document} Index: r36/doc/CRACK.TEX ================================================================== --- r36/doc/CRACK.TEX +++ r36/doc/CRACK.TEX @@ -1,1213 +1,1213 @@ -% This is a LaTeX file -\documentstyle[12pt]{article} - -%Sets size of page and margins -\oddsidemargin 10mm \evensidemargin 10mm -\topmargin 0pt \headheight 0pt \headsep 0pt -\footheight 14pt \footskip 40pt -\textheight 23cm \textwidth 15cm -%\textheight 15cm \textwidth 10cm - -%spaces lines at one and a half spacing -%\def\baselinestretch{1.5} - -%\parskip = \baselineskip - -%Defines capital R for the reals, ... -%\font\Edth=msym10 -%\def\Integer{\hbox{\Edth Z}} -%\def\Rational{\hbox{\Edth Q}} -%\def\Real{\hbox{\Edth R}} -%\def\Complex{\hbox{\Edth C}} - -\title{The Computer Algebra Package {\tt CRACK} for Investigating PDEs} -\author{Thomas Wolf \\ - School of Mathematical Sciences \\ - Queen Mary and Westfield College \\ - University of London \\ - London E1 4NS \\ - T.Wolf@maths.qmw.ac.uk -\\ \\ -Andreas Brand \\ Institut f\"{u}r -Informatik \\ Friedrich Schiller Universit\"{a}t Jena \\ 07740 Jena -\\ Germany \\ maa@hpux.rz.uni-jena.de -} - -\begin{document} -\maketitle -\tableofcontents -\section{The purpose of {\tt CRACK}} -The package {\tt CRACK} attempts the solution of an overdetermined -system of ordinary or partial differential -equations (ODEs/PDEs) with at most polynomial nonlinearities. -Under `normal circumstances' the number of DEs which describe physical -processes matches the number of unknown functions which are involved. -Moreover none of those equations can be solved or integrated and -integrability conditions yield only identities. Though the package -{\tt CRACK} applied to solve such `difficult' systems -directly will not be of much help usually, it is possible to -investigate them indirectly by -studying analytic properties which would be useful for their -solution. Such `simpler' overdetermined PDEs also result from -investigating properties of ODEs and problems in differential geometry. -The property of overdetermination (by which we only mean the fact -that there are more equations than unknown functions) is not a -prerequisite for applying the package but it simplifies the problem -and it is usually necessary for success in solving or simplifying the -system. - -The following examples are quite different in nature. They demonstrate -typical applications of {\tt CRACK} and give an impression of its efficiency. -In principle it makes no difference to investigate more general -symmetries, more general coordinate transformations and so on, except that the -computational complexity may grow very rapidly for more general -ans\"atze, especially for nonlinear problems, such that a solution -becomes practically impossible. - -The following overview makes suggestions for possible -applications; the mathematics of the applications and of the -algorithms which are applied in {\tt CRACK} are described only -superficially. These applications are only examples. The user will usually -have to write own procedures to formulate his problem in form of -an overdetermined system of PDEs which is then solved or simplified with -{\tt CRACK}. - -\begin{enumerate} - \item - DEs as well as differential geometric objects, like a metric which - describes infinitesimal distances in a manifold, can have - infinitesimal symmetries, i.e.\ there exist transformations of dependent - and independent variables, which leave the DE or metric - form-invariant. According to a theory of Sophus Lie such - symmetries of an ODE can be used to integrate the - ODE and symmetries of a PDE can be used to decrease the number - of independent variables. - - The determining conditions for the generators of this - symmetry are given by a system of linear PDEs. - -\item - Other ans\"atze, e.g.\ for finding -\begin{itemize} -\item integrating factors of DEs, or -\item a variational principle, i.e.\ a Lagrangian which is equivalent - to a given ODE, or -\item a factorization ansatz which transforms a given $n$-th order - ODE into two ODEs of order $k$ and $n-k,$ -\end{itemize} - lead to PDE-systems for the remaining free functions with good - prospects for solution. -\item - The ability of {\tt CRACK} to decouple systems of DEs with at most polynomial - nonlinearity can be used to perform very general transformations of - undetermined functions. If, for example, an equation -\begin{equation} - 0 = D_1(x, f) \label{df} -\end{equation} - for a function $f(x)$ is given with $D_1$ as a differential -expression in $x$ and $f$, and a further function $g$ of $x$ -is related to $f$ through a differential relation -\begin{equation} - 0 = D_2(x, g, f), \label{dg} -\end{equation} -then, to obtain an equation equivalent to (\ref{df}) for the function $g,$ -the system (\ref{df},\ref{dg}) could be decoupled w.r.t.\ $f$ to -obtain an equation -\[ 0 = D_3(x, g) \] -which contains only $g$. - - Such generalized transformations can in principle also be done for more -than one equation of the form (\ref{df}), more old and new functions and -variables, and more relations of the form (\ref{dg}). - -\item - If a PDE or `well defined' system is too complicated to be solved in - general, and one has some idea of the dependence of one of the - functions which are to be calculated (e.g. $f$) on at least one - variable (e.g. $x$), then one could try an ansatz for $f$ which - involves $x$ (and possibly other variables) - only explicitly and furthermore only unknown functions - that are independent of $x$. Also other - ans\"atze are possible where no variable occurs explicitly but all new - functions involve only a subset of all variables. This approach - includes separations such as the well known product ansatz $f(r, - \theta, \varphi) = R(r)Y(\theta, \varphi)$ to solve the Laplace - equation $\triangle f = 0$ in spherical coordinates. After such a - substitution the resulting system is simplified and can be solved - usually, because the - number of functions of all independent variables is decreased and is - now less than the number of equations. - -\item - A difficult DE-system is simplified usually if further conditions - in the form of differential equations are added, - because then the resulting system is not necessarily in involution - and integrability conditions can be used to lower the order or to - solve it. -\end{enumerate} - -To explain the input to {\tt CRACK}, which corresponds to examples -given in the final two sections, the way to call {\tt CRACK} is described next. - -\section{How to apply {\tt CRACK}} -\subsection{The call} -{\tt CRACK} is written in the symbolic mode of REDUCE 3.4 and is loaded by -{\tt load CRACK;}. Then {\tt CRACK} is called by -\begin{tabbing} - {\tt CRACK}(\=\{{\it equ}$_1$, {\it equ}$_2$, \ldots , {\it equ}$_m$\}, \\ - \>\{{\it ineq}$_1$, {\it ineq}$_2$, \ldots , {\it ineq}$_n$\}, \\ - \>\{{\it fun}$_1$, {\it fun}$_2$, \ldots , {\it fun}$_p$\}, \\ - \>\{{\it var}$_1$, {\it var}$_2$, \ldots , {\it var}$_q$\}); -\end{tabbing} - $m,n,p,q$ are arbitrary. -\begin{itemize} -\item -The {\it equ}$_i$ are identically vanishing partial differential expressions, -i.e.\ -they represent equations $0 = {\it equ}_i$, which are to be solved for the -functions ${\it fun}_j$ as far as possible, thereby drawing only necessary -conclusions and not restricting the general solution. -\item -The {\it ineq}$_i$ are expressions which must not vanish identically for -any solution to be determined, i.e. only such solutions are computed for which -none of the {\it ineq}$_i$ vanishes identically in all independent variables. -\item -The dependence of the (scalar) functions ${\it fun}_j$ on possibly a number of -variables is assumed to have been defined with DEPEND rather than -declaring these functions -as operators. Their arguments may themselves only be independent variables -and not expressions. -\item -The functions ${\it fun}_j$ and their derivatives may only occur polynomially. -Other unknown functions in ${\it equ}_i$ may be represented as operators. -\item -The ${\it var}_k$ are further independent variables, which are not -already arguments -of any of the ${\it fun}_j$. If there are none then the third argument is -the empty list \{\}. -\item -The dependence of the ${\it equ}_i$ on the independent variables and on -constants and functions other than ${\it fun}_j$ is arbitrary. -\end{itemize} - -\subsection{The result} -The result is a list of solutions -\[ \{{\it sol}_1, \ldots \} \] -where each solution is a list of 3 lists: -\begin{tabbing} - \{\=\{${\it con}_1, \; {\it con}_2, \ldots , \; {\it con}_q$\}, \\ - \>\{${\it fun}_a={\it ex}_a, \;\; -{\it fun}_b={\it ex}_b, \ldots , \;\; {\it fun}_p={\it ex}_p$\},\= \\ - \>\{${\it fun}_c, \;\; {\it fun}_d, \ldots , \;\; {\it fun}_r$\} \>\} -\end{tabbing} -with integer $a, b, c, d, p, q, r.$ -If {\tt CRACK} finds a contradiction as e.g. $0=1$ then there exists no -solution and it returns the empty list \{\}. -The empty list is also returned if no solution exists -which does not violate the inequalities -{\it ineq}$_i \neq 0.$ -For example, in the case of a linear system as input, there is -at most one solution ${\it sol}_1$. - -The expressions ${\it con}_i$ (if there are any), are the -remaining necessary and sufficient conditions for the functions -${\it fun}_c,\ldots,{\it fun}_r$ in the third list. Those -functions can be original functions from the equations to be -solved (of the second argument of the call of {\tt CRACK}) or new -functions or constants which arose from integrations. -The dependence of new functions on variables is declared with {\tt DEPEND} -and to visualize this dependence the algebraic mode function -${\tt FARGS({\it fun}_i)}$ can be used. -If there are no ${\it con}_i$ then all equations are solved and the -functions in the third list are unconstrained. - -The second list contains -equations ${\it fun}_i={\it ex}_i$ where each ${\it fun}_i$ is an -original function and ${\it ex}_i$ is the computed expression -for ${\it fun}_i$. - -\subsection{Flags} -Possible flags which can be changed in symbolic mode -after {\tt CRACK} has been loaded are (initial values in brackets): -\begin{description} -\item[{\tt cont\_ :}] if t then if the maximal number of terms of an expression - is greater then {\tt fcteval\_} or {\tt odesolve\_} then - the user is asked - whether or not the expression is to be substituted or integrated - with {\tt ODESOLVE} respectively. (default: {\tt nil}) -\item[{\tt decouple\_ :}] maximal number of decoupling attempts for a - function (default: 2) -\item[{\tt factorize\_ :}] If an equation can be factored with more than one - factor - containing unknown functions then independent investigations - start. In each investigation exactly one of these factors is set - to zero. If - many equations can be factorized then this may lead to a large - number of individual investigations. {\tt factorize\_} is the - maximal number - of factorizations. If the starting system is linear then - an attempt at factorization would be unsuccessful, i.e. - {\tt factorize\_:=0} prevents this unnecessary - attempt. (default: 4) -\item[{\tt fcteval\_ :}] if a function has been computed from an equation and - is to - be substituted in other equations then {\tt fcteval\_} is the - upper limit for the number of terms of the equated expression - for which substitution is done. (default: 100) -\item[{\tt fname\_ :}] the name to be used for new constants and functions - which result from integrations (default: {\tt c}) -\item[{\tt genint\_ :}] generalized integration disabled/enabled - (default: {\tt nil}) -\item[{\tt logoprint\_ :}] If t then printing of a standard message whenever - {\tt CRACK} is called (default: {\tt t}) -\item[{\tt independence\_ :}] If t then the user will be asked during - separation whether expressions are considered to - be linear independent or not. This should be set true if - in a previous run the assumption of linear independence made by - {\tt CRACK} automatically was false. (default: {\tt nil}) -\item[{\tt odesolve\_ :}] the maximal number of terms of expressions which - are to be - investigated with {\tt ODESOLVE}. (default: $100$) -\item[{\tt print\_ :}] If nil then there is no output during calculation - otherwise {\tt print\_} is the maximal number of terms - of equations which are to be output. (default: 8) -\item[{\tt sp\_cases :}] After a factorization factors are dropped - if they do not contain functions which are to be solved. An - exceptional case is if a factor contains other (parametric) - functions or constants. Then a corresponding message is given - at the first appearance of each factor. These factors are - stored in a list {\tt special\_cases}. If {\tt sp\_cases} - is not {\tt nil} then such factors are not dropped. - (default: {\tt nil}) -\item[{\tt time\_ :}] If t then printing the time necessary for the last - {\tt CRACK} run (default: {\tt t}) -\item[{\tt tr\_gensep :}] to trace of the generalized separation - (default: nil) -\end{description} - -\subsection{Help} -Parts of this text are provided after typing - -{\tt crackhp();} - -The authors are grateful for critical comments -on the interface, efficiency and computational errors. - -\section{Contents of the {\tt CRACK} package} -The package {\tt CRACK} contains modules for decoupling PDEs, integrating -exact PDEs, separating PDEs, solving DEs containing functions of only -a subset of all variables and solving standard ODEs (of Bernoulli or -Euler type, linear, homogeneous and separable ODEs). These facilities -will be described briefly together with examples. - -\subsection{Decoupling} -The decoupling module differentiates equations and combines them algebraically -to obtain if possible decoupled and simplified equations of lower order. -How this could work is demonstrated in the following example. -The integrability condition for the system -\[ \begin{array}{cccl} -f = f(x,y), \; \; & f,_{x} & = & 1 \\ - & f,_{y} & = & (f-x-1/y)x - 1/y^2 -\end{array} \] -provides an algebraic condition for the function $f$ -which turns out not only to be necessary but also sufficient to solve both -equations: -\begin{eqnarray*} - 0 = f,_{xy} - f,_{yx} & = & - xf,_x - f + 2x + 1/y \\ - & = & - f + x + 1/y \; \; \; \; \; \; - \mbox{(with $f,_x$ from above)} -\end{eqnarray*} -\[ \rightarrow f = x + 1/y. \] -A general algorithm to bring a system of PDEs into a standard form -where all integrability conditions are satisfied by applying -a finite number of additions, multiplications and differentiations -is based on the general theory of involutive systems \cite{Riq,Th,Ja}. -Essential to this theory is a total ordering of partial derivatives -which allows assignment to each PDE of a {\em Leading Derivative} -(LD) according to a chosen ordering of functions -and derivatives. Examples for possible orderings are -\begin{itemize} -\item lex.\ order of functions $>$ lex.\ order of variables -\item lex.\ order of functions $>$ total differential order $>$ lex.\ - order of variables -\item total order $>$ lex.\ order of functions $>$ lex.\ order of variables -\end{itemize} -or mixtures of them by giving weights to individual functions and variables. -Above, the `$>$' indicate ``before'' in priority of criteria. The principle -is then to -\begin{itemize} -\item take two equations at a time and differentiate them as often as -necessary to get equal LDs, -\item regard these two equations as algebraic equations in -the common LD and calculate the remainder w.r.t.\ the LD, i.e.\ to -generate an equation without the LD by the Euclidean algorithm, and -\item add this equation to the system. -\end{itemize} -Usually pairs of equations are taken first, such that only one must be -differentiated. If in such a generation step one of both equations is not -differentiated then it is called a -simplification step and this equation will be replaced by the new equation. -The algorithm ends if each combination of two equations yields only equations -which simplify to an identity modulo the other equations. -A more detailed description is given e.g. in \cite{Alex,Reid1}. - -In {\tt CRACK}, a reduced version of this algorithm has so far been -implemented, which applies the first of the above orderings with -lexicographical ordering of functions having the highest -priority. This is done to get decoupled equations, i.e.\ a system with -a ``triangular dependence'' of the equations on the functions, -which is usually easier to solve -successively (starting with the equation containing the fewest -functions) than are coupled DEs. To save memory not all equations -are stored but new equations replace in general older ones. -Details of the algorithm used -in {\tt CRACK} are given in \cite{Wo}. -Programs implementing the standard algorithm are described e.g. in -\cite{FS,Alex,Fush} and \cite{Reid1}. - -The possible variations of orderings or even the switch between -them open possibilities for future optimization. - -{\em Example:} -Applying the decoupling module alone without factorization and integration -to the two equations -\[ \begin{array}{rclcl} - D_1 & := & f + f,_{yy}f,_x & = & 0 \\ \\ - D_2 & := & f,_y + f,_x^2 & = & 0 -\end{array} \] -for $f(x,y)$, using the lexicographic ordering of variables $y>x>1,$ -the steps would be -\begin{tabbing} -$D_1:=$\=$D_1-D_{2y}f_x=f-2f_x^2f_{yx}$ \\ - \> $\rightarrow$ a second 1st order eqn. in $y$\\ \\ -$D_1:=$\>$D_1+2f_x^2D_{2x}=f+4f_x^3f_{xx} \rightarrow$ first ODE \\ - \> to get a second ODE we need an extra equation $D_3:$ \\ \\ -$D_3:=$\>$4f_x^3D_{2xx}-D_{1y}=8f_{xx}^2f_x^3+8f_{xxx}f_x^4-12f_x^2f_{xx}f_{xy} --f_y$ \\ \\ -$D_3:=$\>$D_3+12f_x^2f_{xx}D_{2x}=32f_{xx}^2f_x^3+8f_{xxx}f_x^4-f_y$ -\\ \\ -$D_2:=$\>$D_2+D_3=32f_{xx}^2f_x^3+8f_{xxx}f_x^4+f_x^2 \rightarrow$ -second ODE \\ \\ -$D_2:=$\>$2f_xD_{1x}-D_2=-8f_{xx}^2f_x^3+f_x^2$ \\ \\ -$D_2:=$\>$D_2+2f_{xx}D_1=2ff_{xx}+f_x^2$ \\ \\ -$D_2:=$\>$D_1f-2f_x^3D_2=f^2-2f_x^5$ \\ \\ -$D_1:=$\>$2D_{2x}+5f_xD_1=9ff_x$ \\ \\ -$D_2:=$\>$2f_x^4D_1+9fD_2=9f^3 \rightarrow f=0$ is necessary and \\ - \> as a test shows also sufficient, \\ \\ -$D_1:=$\>$D_{2x}-3fD_2=0 \rightarrow$ end -\end{tabbing} -Here $D_1:=\ldots$ means that the old expression for $D_1$ is replaced -by the result of the calculation of the right side. As the indices -show the calculation can be done by storing only 3 equations at a time, -which is the purpose of the chosen total ordering of derivatives. If -we have $n$ independent variables and $k$ equations at the beginning, -then the calculation can be done by storing not more than $k+n-1$ -equations at a time (plus the original $k$ equations to test results for -sufficiency at the end). -In {\tt CRACK} all intermediate equations generated are checked to see -whether they can be integrated at least once directly by an integration -module. - -\subsection{Integrating exact PDEs} -The technical term `exact' is adapted for PDEs from exterior calculus and -is a small abuse of language but it is useful to characterize the kind of PDEs -under consideration. - -The purpose of the integration module in {\tt CRACK} is to decide -whether a given differential -expression $D$ which involves unknown functions $f^i(x^j),\;\; 1\leq i\leq m$ -of independent variables $x^j, 1\leq j\leq n$ -is a total derivative of another expression $I$ -w.r.t. any variable $x^k, 1\leq k\leq n$ -\[ D(x^i,\; f^j,\; f^j,_p,\; f^j,_{pq}, \ldots) - = \frac{d I(x^i,\; f^j,\; f^j,_p,\; f^j,_{pq}, \ldots)}{d x^k} \] -and to invert the total derivative i.e. to find $I.$ The index $k$ is -reserved in the following for the integration variable $x^k.$ Because -the appropriate constant or function of integration which depends on -all variables except $x^k$ is added to $I,$ a replacement of $0 = D$ -by $0 = I$ in a system of equations is no loss of generality. - -Of course there -always exists a function $I$ with a total derivative equal to $D$ but -the question is whether for \underline{arbitrary} $f^i$ the integral -$I$ is functionally dependent only on the $f^i$ and their derivatives, -and not on integrals of $f^i.$ \\ -\underline{Preconditions:} \\ -$D$ is a polynomial in the $f^i$ and their derivatives. The number of -functions and variables is free. -For deciding the existence of $I$ only, the explicit occurrence of the -variables $x^i$ is arbitrary. In order to actually -calculate $I$ explicitly, $D$ must have the property that all terms in $D$ -must either contain an unknown function of $x^k$ or -must be formally integrable w.r.t. $x^k.$ -That means if $I$ exists then -only a special explicit occurrence of $x^k$ can prevent the -calculation of $I$ -and furthermore only in those terms which do not contain -any unknown function of $x^k.$ -If such terms occur in $D$ and $I$ exists then $I$ can still be expressed -as a polynomial in the $f^i, f^i,_j, \ldots$ and terms containing -indefinite integrals with integrands explicit in $x^k.$ \\ -\underline{Algorithm:} \\ -Successive partial integration of the term with the highest -$x^k$-derivative of any $f^i.$ By that the -differential order w.r.t. $x^k$ is reduced -successively. This procedure is always applicable because steps involve only -differentiations and the polynomial -integration $(\int h^n\frac{\partial h}{\partial x}dx = -h^{n+1}/(n+1))$ where $h$ is a partial derivative of some function -$f^i.$ For a more detailed description see \cite{WoInt}.\\ -\underline{Stop:} \\ -Iteration stops if no term with any $x^k$-derivative of any $f^i$ is left. -If in the remaining un-integrated terms any $f^i(x^k)$ itself occurs, -then $I$ is not expressible with $f^i$ and its derivatives only. In -case no $f^i(x^k)$ occurs then any remaining terms can contain $x^k$ only -explicitly. Whether they can be integrated depends on their formal -integrability. For their integration the REDUCE integrator is applied. \\ -\underline{Example :} \\ -We apply the above algorithm to -\begin{equation} -D := 2f,_yg' + 2f,_{xy}g + gg'^3 + xg'^4 + 3xgg'^2g'' = 0 -\label{D} -\end{equation} -with $f = f(x,y), \, g = g(x), \, '\equiv d/dx.$ -Starting with terms containing $g$ -and at first with the highest derivative $g,_{xx},$ the steps are -\[ -\begin{array}{rcccl} -\int 3xgg,_x^2g,_{xx} dx -& = & \int d(xgg,_x^3) - & - & \int \left( \partial_x(xg) g,_x^3\right) dx \\ \\ -& = & xgg,_x^3 & - & \int g,_x^3(g + xg,_x) dx, -\end{array} \] -\[ I := I + xgg,_x^3 \] -\[ D := D - g,_x^3(g + xg,_x) \] -The new terms $- g,_x^3(g + xg,_x)$ are of lower order than $g,_{xx}$ -and so in the expression $D$ the maximal order of $x$-derivatives -of $g$ is lowered. The conditions that $D$ is exact are the following. -\begin{itemize} -\item The leading derivative must occur linearly before each partial -integration step. -\item After the partial integration of the terms with first order -$x$-derivatives of $f$ the remaining $D$ must not contain $f$ -or other derivatives of $f$, because such terms cannot -be integrated w.r.t.\ $x$ without specifying $f$. -\end{itemize} -The result of $x$- and $y$-integration in the above example is -(remember $g=g(x)$) -\begin{equation} -0 = 2fg + xygg,_x^3 + c_1(x) + c_2(y) \; \; (=I). \nonumber -\end{equation} -{\tt CRACK} can now eliminate $f$ and substitute -for it in all other equations. -\underline{Generalization:} \\ -If after applying the above basic algorithm, terms are left which contain -functions of $x^k$ but each of these functions depends only on a subset of -all $x^i, 1\leq i\leq n,$ then a generalized version of the above algorithm -can still provide a formal expression for the integral $I$ -(see \cite{WoInt}). The price consists of -additional differential conditions, but they are equations in less variables -than occur in the integrated equation. Integrating for example -\begin{equation} -\tilde{D} = D + g^2(y^2 + x\sin y + x^2e^y) \label{Dnew} -\end{equation} -by introducing as few -new functions and additional conditions as possible gives as the integral -$\tilde{I}$ -\begin{eqnarray*} -\tilde{I} & = & 2fg + xygg,_{x}^{3} + c_1(x) + c_2(y) \\ - & & + \frac{1}{3}y^3c_3'' - \cos y(xc_3'' - c_3) -+ e^y(x^2c_3'' - 2xc_3' + 2c_3) -\end{eqnarray*} -with $c_3 = c_3(x), \, '\equiv d/dx$ and the single additional -condition $g^2 = c_3'''.$ -The integration of the new terms of (\ref{Dnew}) is -achieved by partial integration again. For example -\begin{eqnarray*} -\int g^2x^2 dx & = & x^2\int g^2 dx - \int (2x\!\int g^2 dx) dx \\ -& = & x^2\int g^2 dx - 2x\int\!\!\int g^2 dx -+ 2 \int\!\!\int\!\!\int g^2 dx \\ -& = & x^2c_3'' - 2xc_3' + 2c_3 -\end{eqnarray*} -\underline{Characterization:} \\ -This algorithm is a decision algorithm which does not involve any -heuristic. It is fast because time and memory requirements grow only -linearly with the number of terms in $D$ and with the order of -the highest derivative. -After integration the new equation is still a polynomial -in $f^i$ and in the new constant or function of integration,. -Therefore the algorithms for bringing the system into standard form can still -be applied to the PDE-system -after the equation $D = 0$ is replaced by $I = 0.$ - -The complexity of algorithms for bringing a PDE-system into a standard -form depends nonlinearly on the order of these equations because of -the nonlinear increase of the number of different leading derivatives -and by that the number of equations generated intermediately by such -an algorithm. It therefore in general pays off to integrate equations (with -linear expenses) during such a standard form algorithm. The increase -in the number of unknown constants/functions through integration does -not play a role for standard form algorithms because these functions -have less variables and do not increase the number of possible leading -derivatives and therefore not the number of equations to be maintained -during execution of the standard form algorithm. - -If an $f^i,$ which depends on all variables, can be eliminated after an -integration, then depending on its length -it is in general helpful to substitute $f^i$ in other equations and -to reduce the number of equations and functions by one. This is especially -profitable if the replaced expression is short and -contains only functions of less variables than $f^i.$ -\underline{Test:} \\ -The corresponding test input is -\begin{verbatim} -depend f,x,y; -depend g,x; -crack({2*df(f,y)*df(g,x)+2*df(f,x,y)*g+g*df(g,x)**3 - +x*df(g,x)**4+3*x*g*df(g,x)**2*df(g,x,2) - +g**2*(y**2+x*sin y+x**2*e**y)}, - {f,g},{}); -\end{verbatim} -The meaning of the REDUCE command {\tt depend} is to declare that $f$ -depends in an unknown way on $x$ and $y$. For more details on the -algorithm see \cite{WoInt}, for an introduction to REDUCE see \cite{WM}. - -\subsection{Direct separation of PDEs} -As a result of repeated integrations the functions in the -remaining equations have less and less variables. It therefore may happen -that after a substitution an equation results where at least one variable -occurs only explicitly and not as an argument of an unknown function. -Consequently all coefficients of linearly independent expressions in this -variable can be set to zero individually. \\ - -{\em Example:} \\ -$f = f(x,y), \;\; g = g(x), \;\; x,y,z$ are independent variables. -The equation is -\begin{equation} -0 = f,_y + z(f^2+g,_x) + z^2(g,_x+yg^2) \label{sep} -\end{equation} -$x$-separation? $\rightarrow$ no \\ -$y$-separation? $\rightarrow$ no \\ -$z$-separation? $\rightarrow$ yes: $0 \,=\, f,_y \,=\, f^2+g,_x \,=\, -g,_x+yg^2$ \\ -$y$-separation? $\rightarrow$ yes: $0 = g,_x = g^2\;\;$ -(from the third equation from the $z$-separation) - -If $z^2$ had been replaced in (\ref{sep}) by a third -function $h(z)$ then direct separation would not have been possible. -The situation changes if $h$ is a parametric function which is -assumed to be independently given and which should not be -calculated, i.e.\ $f$ and $g$ should be calculated for any -arbitrary given $h(z)$. Then the same separation could have been -done with an extra treatment of the special case $h,_{zz} = 0,$ -i.e.\ $h$ linear in $z$. This different treatment of unknown functions -makes it necessary to input explicitly the functions to be -calculated as the second argument to {\tt CRACK}. The input -in this case would be -\begin{verbatim} -depend f,x,y; -depend g,x; -depend h,z; -crack({df(f,y)+z*f**2+(z+h)*df(g,x)+h*y*g**2},{f,g},{z}); -\end{verbatim} -The third parameter for {\tt CRACK} is necessary to make clear that -in addition to the variables of $f$ and $g$, $z$ is also an independent -variable. - -If the flag {\tt independence\_} is not {\tt nil} then {\tt CRACK} will -stop if linear independence of the explicit expressions of the -separation variable (in the example $1,z,z^2$) is not clear and ask -interactively whether separation should be done or not. - -\subsection{Indirect separation of PDEs} -For the above direct separation a precondition is that at least one -variable occurs only explicitly or as an argument of parametric -functions. The situation where each variable is an argument of at least -one function but no function contains all independent variables of an -equation needs a more elaborate treatment. - -The steps are these -\begin{itemize} - \item A variable $x_a$ is chosen which occurs in as few functions as possible. - This variable will be separated directly later which - requires that all unknown functions $f_i$ containing $x_a$ are to be - eliminated. Therefore, as long as $F:=\{f_i\}$ is not empty do the following: - \begin{itemize} - \item Choose the function $f_i(y_p)$ in $F$ with the smallest number of - variables $y_p$ and with $z_{ij}$ as those variables on which $f_i$ does - not depend. - \item Identify all different products $P_{ik}$ of powers of - $f_i$-derivatives and of $f_i$ in the equation. - Determine the $z_{ij}$-dependent factors $C_{ik}$ of the coefficients - of $P_{ik}$. - \item Choose a $z_{ij}$ and for each $C_{il}$ ($i$ fixed, $l=1,\ldots)$: - \begin{itemize} - \item divide by $C_{il}$ the equation and all the $C_{im}$ with $m>l,$ - \item differentiate the equation and the $C_{im}$ w.r.t.\ $z_{ij}$ - \end{itemize} - \end{itemize} - \item The resulting equation no longer contains any unknown function of $x_a$ - and can be separated w.r.t.\ $x_a$ directly. The - equations arising can be integrated, inverting the sequence of differentiation - and division, by - \begin{itemize} - \item multiplying them and the $C_{im}$ with $m1$ for dynamical symmetries -%(only in case of one ODE for one unknown function) -\item If {\tt lp} is $nil$ then the standard ansatz for $\xi^i, \eta^\alpha$ -is taken which is -\begin{itemize} -\item for point symmetries ({\tt od}=0) $\xi^i = \xi^i(x^j,u^\beta), - u^\alpha = u^\alpha(x^j,u^\beta)$ -\item for contact symmetries ({\tt od}=1) - $ \xi^i := \Omega,_{u,_i}, \;\;\; - \eta := u,_i\Omega,_{u_i} \; - \; \Omega, \;\;\; - \Omega:=\Omega(x^i, u, u,_j)$ -%\item for dynamical symmetries ({\tt od}$>1$) \\ -% $ \xi := \Omega,_{u'}, \;\;\; -% \eta := u'\Omega,_{u'} \; - \; \Omega, \;\;\; -% \Omega:=\Omega(x, u, u',\ldots, u^{({\tt od}-1)})$ -% where {\tt od} must be less than the order of the ODE. -\end{itemize} - - -If {\tt lp} is not $nil$ then {\tt lp} is the ansatz for -$\xi^i, \eta^\alpha$ and must have the form -\begin{itemize} - \item for point symmetries - {\tt \{xi\_\mbox{$x1$} = ..., ..., eta\_\mbox{$u1$} = ..., ...\}} - where {\tt xi\_, eta\_} - are fixed and $x1, \ldots, u1$ are to be replaced by the actual names - of the variables and functions. - \item otherwise {\tt spot\_ = ...} where the expression on the right hand - side is the ansatz for the Symmetry-POTential $\Omega.$ -\end{itemize} - -\item {\tt fl} is the list of free functions in the ansatz -in case {\tt lp} is not $nil.$ -\end{itemize} - -The conditions for the symmetry generators $\xi, \eta$ to provide -infinitesimal transformations -which leave (\ref{k97}) form-invariant to order $O(\varepsilon^2)$ are -formulated by the program {\tt LIEPDE} to be -\begin{eqnarray} -0 & = & \frac{1}{2}x^3\eta,_{yy} - x^3\xi,_{xy} - x^2\xi,_y - 2y\xi,_y - \label{con1} \\ -0 & = & 12y^2\xi,_y - x^4\xi,_{xx} - x^3\xi,_x - 2xy\xi,_x - + 2x^4\eta,_{xy} + x^2\xi + 6y\xi - 2x\eta \\ -0 & = & 2y^2\xi - xy^2\xi,_x - \frac{1}{8}x^5\eta,_{xx} - + \frac{1}{8}x^4\eta,_x - + \frac{1}{4}x^2y\eta,_x + \frac{1}{2}xy^2\eta,_y - - xy\eta \\ -0 & = & \xi,_{yy}. \label{con2} -\end{eqnarray} -{\tt LIEPDE} then calls {\tt CRACK} to solve this system. - -First (\ref{con2}) is integrated to $0 = \xi + c_1y + c_2$ -with new functions $c_1(x), c_2(x).$ -Then $\xi$ is substituted into the other three equations. Now (\ref{con1}) -can be integrated to -\[ 0 = x^3\eta + x^3y^2c_1' - x^3yc_3 - x^3c_4 + x^2y^2c_1 - + \frac{2}{3}y^3c_1 \] -with new functions $c_3(x), c_4(x)$ and $\eta$ can be substituted. -Because the functions $c_1,\ldots,c_4$ are functions of $x$ only, -a separation of the remaining two equations w.r.t.\ the independent -variable $y$ becomes possible which yields 5 and 4 equations. One of -them is $c_1=0$. -After setting $c_1$ to zero, the exact second order ODE -$0 = xc_4'' + 3c_4'$ can be integrated once and -the resulting first order ODE can be solved by -{\tt ODESOLVE} \cite{Mal} to give $c_4 = x^2c_6 - c_5/2$ -with constants $c_5, c_6$. From another equation $c_3$ can be eliminated -and substituted: $c_3 = c_2' - 3c_2/x$. The last function $c_2(x)$ is -solved by {\tt ODESOLVE} from $0 = x^2c_2'' - xc_2' + c_2$ to give -$c_2 = x(c_8\log x + c_7)$. Because now only constants are involved in -the remaining two equations, {\tt CRACK} separates them w.r.t.\ $x$ to obtain 4 -conditions which are solved to give $c_5 = 0$ and $c_6 = - c_8$, -finally obtaining two symmetries (for $c_7 = 0, \, c_8 = -1$ and -$c_7 = -1, \, c_8 = 0$): -\[ -\begin{array}{rclrcl} - \xi_1 & = & x\log x,\hspace{0.5in} & \eta_1 & = & 2y\log x + x^2 - y \\ - \xi_2 & = & x, & \eta_2 & = & 2y . -\end{array} \] -Applying Lie's algorithm by hand, the general solution of (\ref{k97}) -is \cite{Ka} -\[ y = \left\{ \begin{array}{l} - x^2(1 + c_9\tan(c_9\log x + c_{10})) \\ - x^2(1 - c_9\tanh(c_9\log x + c_{10})) \\ - x^2(1 - c_9\coth(c_9\log x + c_{10})) - \end{array} - \right. \] -with constant $c_9, c_{10}$. - -If symmetries of a PDE or of a system of equations shall be determined then -{\tt LIEPDE} does this iteratively by formulating some of the conditions and -solving them by calling {\tt CRACK} to simplify the formulation of the -remaining conditions. If a system of DEs is investigated then the conditions -following from the form-invariance of each single equation are investigated -successively. If a PDE is investigated then conditions which result from -setting to zero the coefficients of the highest derivatives of $y$ are -investigated first. For more details on this iteration see \cite{Alex}, -\cite{Step} and \cite{LIEPDE}. - -A more difficult system of PDEs are the Karpman equations \cite{Karp} -which play a role in plasma physics. In their real form, which is used to -determine symmetries, they are (\cite{Cham}) -\[\rho,_t+w_1\rho,_z+\frac{1}{2}\left[s_1(2\rho,_x\phi,_x+2\rho,_y\phi,_y - +\rho\phi,_{xx}+\rho\phi,_{yy})+ - s_2(2\rho,_z\phi,_z+\rho\phi,_{zz})\right] = 0\] -\[\phi,_t+w_1\phi,_z-\frac{1}{2}\left[s_1\left(\frac{\rho,_{xx}}{\rho} - +\frac{\rho,_{yy}}{\rho}-\phi,_x^2-\phi,_y^2\right)+ - s_2\left(\frac{\rho,_{zz}}{\rho}-\phi,_z^2\right)\right]+a_1\nu = 0\] -\[\nu,_{tt}-(w_2)^2(\nu,_{xx}+\nu,_{yy}+\nu,_{zz})- -2a_2\rho(\rho,_{xx}+\rho,_{yy}+\rho,_{zz})-2a_2(\rho,_x^2+\rho,_y^2+\rho,_z^2) = 0\] -with the three functions $\rho,\phi,\nu$ of four variables $t,x,y,z$ and -with constant parameters $a_i,s_i,w_i.$ - -At first, preliminary symmetry conditions are -derived and solved successively -for each of the three equations. -The solution -of the preliminary conditions for the -first equation -requires 31 integrations and states that all $\xi^i$ are -functions of $t,x,y,z$ only. -The preliminary conditions of the second equation do not provide new -constraints. -The result from the preliminary conditions for the third equation -is that $\nu$ is a function of $t,x,y,z$ only. This needs 4 -integrations. -After 7.1/0.1 sec the full conditions for the first equation are derived -which to solve requires further 77 integrations. -The remaining full conditions for the second equation -to solve requires 6 integrations. Finally, -the full conditions for the last equation are -solved with three more integrations. - -The general solution for the symmetry generators then reads -\[ \begin{array}{rclrcl} - \xi^x & = & - y c_1 + c_2 \;\;\;\;\; & \eta^r & = & 0 \\ - \xi^y & = & x c_1 + c_3 & \eta^\phi & = & a_1 c_6 t^2 + a_1 c_7 t + c_8 \\ - \xi^z & = & c_4 & \eta^v & = & - c_6 t - c_7 \\ - \xi^t & = & c_5 & & & -\end{array} -\] -with constants $c_1, \ldots, c_8.$ The corresponding 8 symmetry generators are -\begin{eqnarray*} - X_1 = \partial_x & \;\;\;\;\;\;\;\;\;\; & X_5 = y\partial_x - x\partial_y \\ - X_2 = \partial_y & & X_6 = \partial_\phi \\ - X_3 = \partial_z & & X_7 = a_1t\partial_\phi - \partial_\nu \\ - X_4 = \partial_t & & X_8 = a_1t^2\partial_\phi - 2t\partial_\nu. -\end{eqnarray*} - -The total time in a test run with {\tt lisp(print\_:=nil);} was -260/3.2 seconds on a PC486 with 33 MHz and 4MB RAM, -i.e. less than 5 min. -For comparison, the same calculation reported in \cite{Cham}, also split -into 6 parts but with integrations done by hand, took more than 2 hours CPU -on a VAX 8600 to formulate and simplify the symmetry conditions using the -program {\tt SYMMGRP.MAX} written in MACSYMA. -The corresponding input for {\tt LIEPDE} is -\begin{verbatim} -depend r,x,y,z,tt; -depend f,x,y,z,tt; -depend v,x,y,z,tt; - -de := {{df(r,tt)+w1*df(r,z) - + s1*(df(r,x)*df(f,x)+df(r,y)*df(f,y)+r*df(f,x,2)/2+r*df(f,y,2)/2) - + s2*(df(r,z)*df(f,z)+r*df(f,z,2)/2), - - df(f,tt)+w1*df(f,z) - - (s1*(df(r,x,2)/r+df(r,y,2)/r-df(f,x)**2-df(f,y)**2) + - s2*(df(r,z,2)/r-df(f,z)**2))/2 + a1*v, - - df(v,tt,2)-w2**2*(df(v,x,2)+df(v,y,2)+df(v,z,2)) - - 2*a2*r*(df(r,x,2)+df(r,y,2)+df(r,z,2)) - - 2*a2*(df(r,x)**2+df(r,y)**2+df(r,z)**2)}, - - {r,f,v}, {x,y,z,tt}}; -mo := {0, nil, nil}; -LIEPDE(de,mo); -\end{verbatim} - -\subsection{Determining integrating factors} -Another way to solve or simplify nonlinear DEs is to determine first -integrals by finding integrating factors. For the equation (6.37) of -\cite{Ka} (which has no point symmetry) -\begin{equation} -0 = y'' + y'(2y + F(x)) + F(x)y^2 - H(x) \label{k37} -\end{equation} -for $y(x)$ and parametric functions $F, H$ of $x$ the input -consists of -\begin{verbatim} -depend f,x; -depend h,x; -depend y,x; -de := {df(y,x,2) = -(2*y+f)*df(y,x)-f*y**2+h, y, x}; -mo := {0,{},2}; -FIRINT(de,mo); -\end{verbatim} -The arguments to {\tt FIRINT} are similar to those of {\tt LIEPDE}\@. -Here {\tt mo = \{fi,fl,dg\}} specifies an ansatz for the first integral. - - For {\tt fi=0} the ansatz for the first integral is determined by -{\tt dg}: The first integral is assumed to be a -polynomial of degree {\tt dg} in $y^{(n-1)}$ (with $n$ as the order of the ODE) -and with arbitrary functions of $x, y,\ldots,y^{(n-2)}$ as coefficients. -In this case -{\tt fl} has no meaning and is set to \{\}. -For {\tt fi}$\neq${\tt 0, fi} is the ansatz for the first integral and -{\tt fl} is a list of -unknown functions in the ansatz, which are to be solved for. In this case -{\tt dg} has no meaning. - - The above example determines first integrals which are at most quadratic -in $y'$ for equation (6.37) in \cite{Ka}. -{\tt FIRINT} starts with the ansatz -\begin{equation} -{\rm const.} = h_2(x,y)y'^2 + h_1(x,y)y' + h_0(x,y) \label{fians} -\end{equation} -and formulates the determining system by total differentiation of -(\ref{fians}), identification of $y''$ with $y''$ in (\ref{k37}) and -direct separation of $y',$ to produce -\begin{eqnarray*} -0 & = & h_2,_y \\ -0 & = & (H - F y^2)h_1 + h_0,_x \\ -0 & = & h_1,_x + h_2,x - (2F + 4y)h_2 \\ -0 & = & 2(H - Fy^2)h_2 - (F - 2y)h_1 + h_0,y + h_1,x. -\end{eqnarray*} -It then calls {\tt CRACK} which provides the solution for $h_0,h_1,h_2.$ -The first integral is -\begin{equation} -\mbox{const.} = \left( \frac{dy}{dx}+y^2 \right) e^{\int \!F\,dx} - -\int He^{\int \!F\,dx} dx -\end{equation} -which is linear in $y'$. Many other nonlinear ODEs in \cite{Ka} have quadratic -first integrals. - -\subsection{Determining a Lagrangian for a given 2nd order ODE} -The knowledge of a Lagrangian $L$ for a given set of differential -equations may be useful in solving and understanding these equations. -If $L$ is known it is easier to determine symmetries, conserved -quantities and singular points. An equivalent variational principle -could also be useful for a more efficient numerical solution. -This problem is known as the inverse problem of variational calculus. -For example, the first transcendental Painlev\'{e} equation -\begin{equation} - y'' = 6y^2 + x \label{pain} -\end{equation} -has no point symmetries but proves to have a Lagrangian with the -structure -\begin{equation} - L = u(x,y)(y')^2 + v(x,y). \label{lagr} -\end{equation} -(The other 5 transcendental Painlev\'{e} equations have a Lagrangian -of this structure as well.) -A program {\tt LAGRAN} formulates the conditions for $u$ and $v$ (a first -order PDE-system). The call is -\begin{verbatim} -depend f,x; depend y,x; -de := {df(y,x,2) = 6*y**2 + x, y, x}; -mo := {0,{}}; -LAGRAN(de,mo); -\end{verbatim} - -If a system of ODEs or a PDE with at least two variables is given, -then the existence of an equivalent Lagrangian $L$ is not guaranteed. -Only in the case of -a single 2nd order ODE, which is treated by the program {\tt LAGRAN}, -must a Lagrangian which is locally equivalent to the ODE -exist. As a consequence the determination of $L$ for a second order -ODE is in general not simpler than the solution of the ODE itself. -Therefore the structure of -$L$ must be specified, which is done through (\ref{lagr}). - - In the call of {\tt LAGRAN} the second argument {\tt mo=\{lg,fl\}} allows -input of an ansatz for the Lagrangian. -For {\tt lg=0} the default ansatz for the first integral is as given in -(\ref{lagr}). -For {\tt lg$\neq$0, lg} is the ansatz for the Lagrangian and {\tt fl} is a -list of unknown functions in the ansatz which are to be solved. -For equation (\ref{pain}) the resulting equivalent Lagrangian is -\[ L = y'^2 + xy + 4y^3. \] -Because the first order system for $u$ and $v$ is normally not too -difficult, more complicated problems can also be solved, such as the -determination of $L$ for the 6'th transcendental Painlev\'{e} equation -\begin{eqnarray} - y'' = & \frac{1}{2}\left(\frac{1}{y}+\frac{1}{y-1}+\frac{1}{y-x}\right) y'^2 -- \left(\frac{1}{x}+\frac{1}{x-1}+\frac{1}{y-x}\right)y' \nonumber \\ -& + \frac{y(y-1)(y-x)}{x^2(x-1)^2}\left(a+\frac{bx}{y^2}+\frac{c(x-1)}{(y-1)^2} -+\frac{dx(x-1)}{(y-x)^2}\right) -\end{eqnarray} -for which $L$ turns out to be -\[ -\begin{array}{rcll} -L & = & 1/[xy(x-y)(x+1)(x-1)(y-1)] \cdot [(x+1)(x-1)^2x^2y'^2 \\ - & & - 2a(xy+x+y)(x-y)(y-1)y + 2b(x+y+1)(x-y)(y-1)x \\ - & & + 2c(x+y)(x-y)(x-1)y - 2d(x-1)(y+1)(y-1)xy ]. -\end{array} \] - -\subsection{A factorization ansatz for a given ODE} -A further possible way to integrate an $n$'th order ODE is to decompose it -into two ODEs of order $k$ and $n-k$. If one specifies the structure of the -$k$'th order ODE and demands that these ODEs can be solved successively then -this leads to a system of PDEs in the variables -$x, y, \ldots, y^{k-1}$ with a good chance of solution. - -To solve the ODE (6.122) in \cite{Ka} -\begin{equation} -0 = yy'' - y'^2 + F(x)yy' + Q(x)y^2 \label{6.122} -\end{equation} -the input would be -\begin{verbatim} -depend f,x; -depend q,x; -depend y,x; -de := {df(y,x,2) = df(y,x)**2/y - f*df(y,x) - y*q, y, x}; -mo := {2,{}}; -DECOMP(de,mo); -\end{verbatim} -In contrast to {\tt FIRINT}, {\tt LAGRAN} the ODE could here -be in the implicit form $0 = \ldots \;$ as well. - -The second argument {\tt mo = \{as,fl\}} specifies an ansatz for the $k$'th -order ODE. If {\tt as} is an integer between 1 and 4 inclusive -then a default ansatz -is taken and {\tt fl} (the list of further unknown functions) is \{\}. -The 4 ans\"atze for \verb+as+ $\in$ [1,4] are -\begin{eqnarray} -y' & = & a(x)\,b(y) \nonumber \\ -y' & = & a(x)\,y + b(x) \label{d2} \\ -y' & = & a(x)\,y^n + b(x)\,y \nonumber \\ -y' & = & a(x)\,y^2 + b(x)\,y + c(x) \nonumber -\end{eqnarray} - - For {\tt as}$\not\in$[1,4], {\tt as} itself is the ansatz for the $k$'th -order ODE with $y^{(k)}$ eliminated on the left side and {\tt fl} is -a list of unknown functions in the ansatz, which are to be solved for. - -The program {\tt DECOMP} formulates the determining system, in the above -example -\begin{eqnarray*} -0 & = & b^2 \\ -0 & = & - F(x)b - b' + ab \\ -0 & = & - F(x)a - Q(x) - a' -\end{eqnarray*} -and calls {\tt CRACK} to solve it. Because the result -\begin{eqnarray*} -a(x) & = & \left(c_1 - \int Qe^{-\int F dx} dx\right)e^{-\int F dx} \\ -b(x) & = & 0 -\end{eqnarray*} -contains $n-k = 1$ constant(s) of integration, this factorization ansatz -does not restrict the solution space of (\ref{6.122}) -and because of (\ref{d2}) the general solution is -\[y = c_2e^{\int \left[\left(c_1 - \int Qe^{-\int F dx} dx\right)e^{-\int F dx} -\right] dx}.\] - -\subsection{General remarks on complexity} -In general, PDE-systems are easier to solve, the fewer arbitrary functions of -fewer variables are contained in the general solution. This in turn -is the case if more and more equations have to be satisfied for less functions, -i.e. the more restrictive is the PDE-system. -Having more equations to solve for a given number of functions -improves the -chance of finding an integrable one among them and provides -more possibilities to combine them and find a quick way to solve -them. For example, it is usually more difficult to find all -point symmetries of a very simple ODE with many point symmetries -than to show that an ODE that is possibly more difficult -to solve has no point symmetry. -An appropriate strategy could therefore be to start an -investigation with a very restrictive ansatz and later to try -less restrictive ones. For example, an ODE could be investigated at first -with respect to point symmetries and if none is found then one -could look for contact and then for dynamical symmetries. - -Experience shows that nonlinear systems may lead to an -explosion in the length of generated equations much quicker -than linear equations -even if they have more independent variables or are of higher order. -For solving ODEs one should therefore investigate infinitesimal -symmetries or integrating factors first which provide linear systems -and only later consider the factorization into two ODEs of lower order. - -\subsection{Acknowledgement} -We want to thank especially Francis Wright and Herbert Melenk for -continuous help in respect with special features and bugs of REDUCE. - -\newpage -\begin{thebibliography}{99} -\bibitem{Riq} C. Riquier, Les syst\`{e}mes d'\'{e}quations aux d\'{e}riv\'{e}es -partielles, Gauthier--Villars, Paris (1910). -\bibitem{Th} J. Thomas, Differential Systems, AMS, Colloquium -publications, v. 21, N.Y. (1937). -\bibitem{Ja} M. Janet, Le\c{c}ons sur les syst\`{e}mes d'\'{e}quations aux -d\'{e}riv\'{e}es, Gauthier--Villars, Paris (1929). -\bibitem{Topu} V.L. Topunov, Reducing Systems of Linear Differential -Equations to a Passive Form, Acta Appl. Math. 16 (1989) 191--206. -\bibitem{Alex} A.V. Bocharov and M.L. Bronstein, Efficiently -Implementing Two Methods of the Geometrical Theory of Differential -Equations: An Experience in Algorithm and Software Design, Acta. Appl. -Math. 16 (1989) 143--166. -\bibitem{Reid1} G.J. Reid, A triangularization algorithm which -determines the Lie symmetry algebra of any system of PDEs, J.Phys. A: -Math. Gen. 23 (1990) L853-L859. -\bibitem{FS} F. Schwarz, Automatically Determining Symmetries of Partial -Differential Equations, Computing 34, (1985) 91-106. -\bibitem{Fush} W.I. Fushchich and V.V. Kornyak, Computer Algebra -Application for Determining Lie and Lie--B\"{a}cklund Symmetries of -Differential Equations, J. Symb. Comp. 7 (1989) 611--619. -\bibitem{Ka} E. Kamke, Differentialgleichungen, L\"{o}sungsmethoden -und L\"{o}sungen, Band 1, Gew\"{o}hnliche Differentialgleichungen, -Chelsea Publishing Company, New York, 1959. -\bibitem{Wo} T. Wolf, An Analytic Algorithm for Decoupling and Integrating -systems of Nonlinear Partial Differential Equations, J. Comp. Phys., -no. 3, 60 (1985) 437-446 and, Zur analytischen Untersuchung und exakten -L\"{o}sung von Differentialgleichungen mit Computeralgebrasystemen, -Dissertation B, Jena (1989). -\bibitem{WoInt} T. Wolf, The Symbolic Integration of Exact PDEs, -preprint, submitted to J.\ Symb.\ Comp. (1991). -\bibitem{WM} M.A.H. MacCallum, F.J. Wright, Algebraic Computing with REDUCE, -Clarendon Press, Oxford (1991). -\bibitem{Mal} M.A.H. MacCallum, An Ordinary Differential Equation -Solver for REDUCE, Proc. ISAAC'88, Springer Lect. Notes in Comp Sci. -358, 196--205. -\bibitem{Step} H. Stephani, Differential equations, Their solution using -symmetries, Cambridge University Press (1989). -\bibitem{LIEPDE} T. Wolf, An efficiency improved program {\tt LIEPDE} -for determining Lie-symmetries of PDEs, Proceedings of the workshop on -Modern group theory methods in Acireale (Sicily) Nov. (1992) -\bibitem{Karp} V.I. Karpman, Phys. Lett. A 136, 216 (1989) -\bibitem{Cham} B. Champagne, W. Hereman and P. Winternitz, The computer - calculation of Lie point symmetries of large systems of differential - equation, Comp. Phys. Comm. 66, 319-340 (1991) - -\end{thebibliography} - -\end{document} +% This is a LaTeX file +\documentstyle[12pt]{article} + +%Sets size of page and margins +\oddsidemargin 10mm \evensidemargin 10mm +\topmargin 0pt \headheight 0pt \headsep 0pt +\footheight 14pt \footskip 40pt +\textheight 23cm \textwidth 15cm +%\textheight 15cm \textwidth 10cm + +%spaces lines at one and a half spacing +%\def\baselinestretch{1.5} + +%\parskip = \baselineskip + +%Defines capital R for the reals, ... +%\font\Edth=msym10 +%\def\Integer{\hbox{\Edth Z}} +%\def\Rational{\hbox{\Edth Q}} +%\def\Real{\hbox{\Edth R}} +%\def\Complex{\hbox{\Edth C}} + +\title{The Computer Algebra Package {\tt CRACK} for Investigating PDEs} +\author{Thomas Wolf \\ + School of Mathematical Sciences \\ + Queen Mary and Westfield College \\ + University of London \\ + London E1 4NS \\ + T.Wolf@maths.qmw.ac.uk +\\ \\ +Andreas Brand \\ Institut f\"{u}r +Informatik \\ Friedrich Schiller Universit\"{a}t Jena \\ 07740 Jena +\\ Germany \\ maa@hpux.rz.uni-jena.de +} + +\begin{document} +\maketitle +\tableofcontents +\section{The purpose of {\tt CRACK}} +The package {\tt CRACK} attempts the solution of an overdetermined +system of ordinary or partial differential +equations (ODEs/PDEs) with at most polynomial nonlinearities. +Under `normal circumstances' the number of DEs which describe physical +processes matches the number of unknown functions which are involved. +Moreover none of those equations can be solved or integrated and +integrability conditions yield only identities. Though the package +{\tt CRACK} applied to solve such `difficult' systems +directly will not be of much help usually, it is possible to +investigate them indirectly by +studying analytic properties which would be useful for their +solution. Such `simpler' overdetermined PDEs also result from +investigating properties of ODEs and problems in differential geometry. +The property of overdetermination (by which we only mean the fact +that there are more equations than unknown functions) is not a +prerequisite for applying the package but it simplifies the problem +and it is usually necessary for success in solving or simplifying the +system. + +The following examples are quite different in nature. They demonstrate +typical applications of {\tt CRACK} and give an impression of its efficiency. +In principle it makes no difference to investigate more general +symmetries, more general coordinate transformations and so on, except that the +computational complexity may grow very rapidly for more general +ans\"atze, especially for nonlinear problems, such that a solution +becomes practically impossible. + +The following overview makes suggestions for possible +applications; the mathematics of the applications and of the +algorithms which are applied in {\tt CRACK} are described only +superficially. These applications are only examples. The user will usually +have to write own procedures to formulate his problem in form of +an overdetermined system of PDEs which is then solved or simplified with +{\tt CRACK}. + +\begin{enumerate} + \item + DEs as well as differential geometric objects, like a metric which + describes infinitesimal distances in a manifold, can have + infinitesimal symmetries, i.e.\ there exist transformations of dependent + and independent variables, which leave the DE or metric + form-invariant. According to a theory of Sophus Lie such + symmetries of an ODE can be used to integrate the + ODE and symmetries of a PDE can be used to decrease the number + of independent variables. + + The determining conditions for the generators of this + symmetry are given by a system of linear PDEs. + +\item + Other ans\"atze, e.g.\ for finding +\begin{itemize} +\item integrating factors of DEs, or +\item a variational principle, i.e.\ a Lagrangian which is equivalent + to a given ODE, or +\item a factorization ansatz which transforms a given $n$-th order + ODE into two ODEs of order $k$ and $n-k,$ +\end{itemize} + lead to PDE-systems for the remaining free functions with good + prospects for solution. +\item + The ability of {\tt CRACK} to decouple systems of DEs with at most polynomial + nonlinearity can be used to perform very general transformations of + undetermined functions. If, for example, an equation +\begin{equation} + 0 = D_1(x, f) \label{df} +\end{equation} + for a function $f(x)$ is given with $D_1$ as a differential +expression in $x$ and $f$, and a further function $g$ of $x$ +is related to $f$ through a differential relation +\begin{equation} + 0 = D_2(x, g, f), \label{dg} +\end{equation} +then, to obtain an equation equivalent to (\ref{df}) for the function $g,$ +the system (\ref{df},\ref{dg}) could be decoupled w.r.t.\ $f$ to +obtain an equation +\[ 0 = D_3(x, g) \] +which contains only $g$. + + Such generalized transformations can in principle also be done for more +than one equation of the form (\ref{df}), more old and new functions and +variables, and more relations of the form (\ref{dg}). + +\item + If a PDE or `well defined' system is too complicated to be solved in + general, and one has some idea of the dependence of one of the + functions which are to be calculated (e.g. $f$) on at least one + variable (e.g. $x$), then one could try an ansatz for $f$ which + involves $x$ (and possibly other variables) + only explicitly and furthermore only unknown functions + that are independent of $x$. Also other + ans\"atze are possible where no variable occurs explicitly but all new + functions involve only a subset of all variables. This approach + includes separations such as the well known product ansatz $f(r, + \theta, \varphi) = R(r)Y(\theta, \varphi)$ to solve the Laplace + equation $\triangle f = 0$ in spherical coordinates. After such a + substitution the resulting system is simplified and can be solved + usually, because the + number of functions of all independent variables is decreased and is + now less than the number of equations. + +\item + A difficult DE-system is simplified usually if further conditions + in the form of differential equations are added, + because then the resulting system is not necessarily in involution + and integrability conditions can be used to lower the order or to + solve it. +\end{enumerate} + +To explain the input to {\tt CRACK}, which corresponds to examples +given in the final two sections, the way to call {\tt CRACK} is described next. + +\section{How to apply {\tt CRACK}} +\subsection{The call} +{\tt CRACK} is written in the symbolic mode of REDUCE 3.4 and is loaded by +{\tt load CRACK;}. Then {\tt CRACK} is called by +\begin{tabbing} + {\tt CRACK}(\=\{{\it equ}$_1$, {\it equ}$_2$, \ldots , {\it equ}$_m$\}, \\ + \>\{{\it ineq}$_1$, {\it ineq}$_2$, \ldots , {\it ineq}$_n$\}, \\ + \>\{{\it fun}$_1$, {\it fun}$_2$, \ldots , {\it fun}$_p$\}, \\ + \>\{{\it var}$_1$, {\it var}$_2$, \ldots , {\it var}$_q$\}); +\end{tabbing} + $m,n,p,q$ are arbitrary. +\begin{itemize} +\item +The {\it equ}$_i$ are identically vanishing partial differential expressions, +i.e.\ +they represent equations $0 = {\it equ}_i$, which are to be solved for the +functions ${\it fun}_j$ as far as possible, thereby drawing only necessary +conclusions and not restricting the general solution. +\item +The {\it ineq}$_i$ are expressions which must not vanish identically for +any solution to be determined, i.e. only such solutions are computed for which +none of the {\it ineq}$_i$ vanishes identically in all independent variables. +\item +The dependence of the (scalar) functions ${\it fun}_j$ on possibly a number of +variables is assumed to have been defined with DEPEND rather than +declaring these functions +as operators. Their arguments may themselves only be independent variables +and not expressions. +\item +The functions ${\it fun}_j$ and their derivatives may only occur polynomially. +Other unknown functions in ${\it equ}_i$ may be represented as operators. +\item +The ${\it var}_k$ are further independent variables, which are not +already arguments +of any of the ${\it fun}_j$. If there are none then the third argument is +the empty list \{\}. +\item +The dependence of the ${\it equ}_i$ on the independent variables and on +constants and functions other than ${\it fun}_j$ is arbitrary. +\end{itemize} + +\subsection{The result} +The result is a list of solutions +\[ \{{\it sol}_1, \ldots \} \] +where each solution is a list of 3 lists: +\begin{tabbing} + \{\=\{${\it con}_1, \; {\it con}_2, \ldots , \; {\it con}_q$\}, \\ + \>\{${\it fun}_a={\it ex}_a, \;\; +{\it fun}_b={\it ex}_b, \ldots , \;\; {\it fun}_p={\it ex}_p$\},\= \\ + \>\{${\it fun}_c, \;\; {\it fun}_d, \ldots , \;\; {\it fun}_r$\} \>\} +\end{tabbing} +with integer $a, b, c, d, p, q, r.$ +If {\tt CRACK} finds a contradiction as e.g. $0=1$ then there exists no +solution and it returns the empty list \{\}. +The empty list is also returned if no solution exists +which does not violate the inequalities +{\it ineq}$_i \neq 0.$ +For example, in the case of a linear system as input, there is +at most one solution ${\it sol}_1$. + +The expressions ${\it con}_i$ (if there are any), are the +remaining necessary and sufficient conditions for the functions +${\it fun}_c,\ldots,{\it fun}_r$ in the third list. Those +functions can be original functions from the equations to be +solved (of the second argument of the call of {\tt CRACK}) or new +functions or constants which arose from integrations. +The dependence of new functions on variables is declared with {\tt DEPEND} +and to visualize this dependence the algebraic mode function +${\tt FARGS({\it fun}_i)}$ can be used. +If there are no ${\it con}_i$ then all equations are solved and the +functions in the third list are unconstrained. + +The second list contains +equations ${\it fun}_i={\it ex}_i$ where each ${\it fun}_i$ is an +original function and ${\it ex}_i$ is the computed expression +for ${\it fun}_i$. + +\subsection{Flags} +Possible flags which can be changed in symbolic mode +after {\tt CRACK} has been loaded are (initial values in brackets): +\begin{description} +\item[{\tt cont\_ :}] if t then if the maximal number of terms of an expression + is greater then {\tt fcteval\_} or {\tt odesolve\_} then + the user is asked + whether or not the expression is to be substituted or integrated + with {\tt ODESOLVE} respectively. (default: {\tt nil}) +\item[{\tt decouple\_ :}] maximal number of decoupling attempts for a + function (default: 2) +\item[{\tt factorize\_ :}] If an equation can be factored with more than one + factor + containing unknown functions then independent investigations + start. In each investigation exactly one of these factors is set + to zero. If + many equations can be factorized then this may lead to a large + number of individual investigations. {\tt factorize\_} is the + maximal number + of factorizations. If the starting system is linear then + an attempt at factorization would be unsuccessful, i.e. + {\tt factorize\_:=0} prevents this unnecessary + attempt. (default: 4) +\item[{\tt fcteval\_ :}] if a function has been computed from an equation and + is to + be substituted in other equations then {\tt fcteval\_} is the + upper limit for the number of terms of the equated expression + for which substitution is done. (default: 100) +\item[{\tt fname\_ :}] the name to be used for new constants and functions + which result from integrations (default: {\tt c}) +\item[{\tt genint\_ :}] generalized integration disabled/enabled + (default: {\tt nil}) +\item[{\tt logoprint\_ :}] If t then printing of a standard message whenever + {\tt CRACK} is called (default: {\tt t}) +\item[{\tt independence\_ :}] If t then the user will be asked during + separation whether expressions are considered to + be linear independent or not. This should be set true if + in a previous run the assumption of linear independence made by + {\tt CRACK} automatically was false. (default: {\tt nil}) +\item[{\tt odesolve\_ :}] the maximal number of terms of expressions which + are to be + investigated with {\tt ODESOLVE}. (default: $100$) +\item[{\tt print\_ :}] If nil then there is no output during calculation + otherwise {\tt print\_} is the maximal number of terms + of equations which are to be output. (default: 8) +\item[{\tt sp\_cases :}] After a factorization factors are dropped + if they do not contain functions which are to be solved. An + exceptional case is if a factor contains other (parametric) + functions or constants. Then a corresponding message is given + at the first appearance of each factor. These factors are + stored in a list {\tt special\_cases}. If {\tt sp\_cases} + is not {\tt nil} then such factors are not dropped. + (default: {\tt nil}) +\item[{\tt time\_ :}] If t then printing the time necessary for the last + {\tt CRACK} run (default: {\tt t}) +\item[{\tt tr\_gensep :}] to trace of the generalized separation + (default: nil) +\end{description} + +\subsection{Help} +Parts of this text are provided after typing + +{\tt crackhp();} + +The authors are grateful for critical comments +on the interface, efficiency and computational errors. + +\section{Contents of the {\tt CRACK} package} +The package {\tt CRACK} contains modules for decoupling PDEs, integrating +exact PDEs, separating PDEs, solving DEs containing functions of only +a subset of all variables and solving standard ODEs (of Bernoulli or +Euler type, linear, homogeneous and separable ODEs). These facilities +will be described briefly together with examples. + +\subsection{Decoupling} +The decoupling module differentiates equations and combines them algebraically +to obtain if possible decoupled and simplified equations of lower order. +How this could work is demonstrated in the following example. +The integrability condition for the system +\[ \begin{array}{cccl} +f = f(x,y), \; \; & f,_{x} & = & 1 \\ + & f,_{y} & = & (f-x-1/y)x - 1/y^2 +\end{array} \] +provides an algebraic condition for the function $f$ +which turns out not only to be necessary but also sufficient to solve both +equations: +\begin{eqnarray*} + 0 = f,_{xy} - f,_{yx} & = & - xf,_x - f + 2x + 1/y \\ + & = & - f + x + 1/y \; \; \; \; \; \; + \mbox{(with $f,_x$ from above)} +\end{eqnarray*} +\[ \rightarrow f = x + 1/y. \] +A general algorithm to bring a system of PDEs into a standard form +where all integrability conditions are satisfied by applying +a finite number of additions, multiplications and differentiations +is based on the general theory of involutive systems \cite{Riq,Th,Ja}. +Essential to this theory is a total ordering of partial derivatives +which allows assignment to each PDE of a {\em Leading Derivative} +(LD) according to a chosen ordering of functions +and derivatives. Examples for possible orderings are +\begin{itemize} +\item lex.\ order of functions $>$ lex.\ order of variables +\item lex.\ order of functions $>$ total differential order $>$ lex.\ + order of variables +\item total order $>$ lex.\ order of functions $>$ lex.\ order of variables +\end{itemize} +or mixtures of them by giving weights to individual functions and variables. +Above, the `$>$' indicate ``before'' in priority of criteria. The principle +is then to +\begin{itemize} +\item take two equations at a time and differentiate them as often as +necessary to get equal LDs, +\item regard these two equations as algebraic equations in +the common LD and calculate the remainder w.r.t.\ the LD, i.e.\ to +generate an equation without the LD by the Euclidean algorithm, and +\item add this equation to the system. +\end{itemize} +Usually pairs of equations are taken first, such that only one must be +differentiated. If in such a generation step one of both equations is not +differentiated then it is called a +simplification step and this equation will be replaced by the new equation. +The algorithm ends if each combination of two equations yields only equations +which simplify to an identity modulo the other equations. +A more detailed description is given e.g. in \cite{Alex,Reid1}. + +In {\tt CRACK}, a reduced version of this algorithm has so far been +implemented, which applies the first of the above orderings with +lexicographical ordering of functions having the highest +priority. This is done to get decoupled equations, i.e.\ a system with +a ``triangular dependence'' of the equations on the functions, +which is usually easier to solve +successively (starting with the equation containing the fewest +functions) than are coupled DEs. To save memory not all equations +are stored but new equations replace in general older ones. +Details of the algorithm used +in {\tt CRACK} are given in \cite{Wo}. +Programs implementing the standard algorithm are described e.g. in +\cite{FS,Alex,Fush} and \cite{Reid1}. + +The possible variations of orderings or even the switch between +them open possibilities for future optimization. + +{\em Example:} +Applying the decoupling module alone without factorization and integration +to the two equations +\[ \begin{array}{rclcl} + D_1 & := & f + f,_{yy}f,_x & = & 0 \\ \\ + D_2 & := & f,_y + f,_x^2 & = & 0 +\end{array} \] +for $f(x,y)$, using the lexicographic ordering of variables $y>x>1,$ +the steps would be +\begin{tabbing} +$D_1:=$\=$D_1-D_{2y}f_x=f-2f_x^2f_{yx}$ \\ + \> $\rightarrow$ a second 1st order eqn. in $y$\\ \\ +$D_1:=$\>$D_1+2f_x^2D_{2x}=f+4f_x^3f_{xx} \rightarrow$ first ODE \\ + \> to get a second ODE we need an extra equation $D_3:$ \\ \\ +$D_3:=$\>$4f_x^3D_{2xx}-D_{1y}=8f_{xx}^2f_x^3+8f_{xxx}f_x^4-12f_x^2f_{xx}f_{xy} +-f_y$ \\ \\ +$D_3:=$\>$D_3+12f_x^2f_{xx}D_{2x}=32f_{xx}^2f_x^3+8f_{xxx}f_x^4-f_y$ +\\ \\ +$D_2:=$\>$D_2+D_3=32f_{xx}^2f_x^3+8f_{xxx}f_x^4+f_x^2 \rightarrow$ +second ODE \\ \\ +$D_2:=$\>$2f_xD_{1x}-D_2=-8f_{xx}^2f_x^3+f_x^2$ \\ \\ +$D_2:=$\>$D_2+2f_{xx}D_1=2ff_{xx}+f_x^2$ \\ \\ +$D_2:=$\>$D_1f-2f_x^3D_2=f^2-2f_x^5$ \\ \\ +$D_1:=$\>$2D_{2x}+5f_xD_1=9ff_x$ \\ \\ +$D_2:=$\>$2f_x^4D_1+9fD_2=9f^3 \rightarrow f=0$ is necessary and \\ + \> as a test shows also sufficient, \\ \\ +$D_1:=$\>$D_{2x}-3fD_2=0 \rightarrow$ end +\end{tabbing} +Here $D_1:=\ldots$ means that the old expression for $D_1$ is replaced +by the result of the calculation of the right side. As the indices +show the calculation can be done by storing only 3 equations at a time, +which is the purpose of the chosen total ordering of derivatives. If +we have $n$ independent variables and $k$ equations at the beginning, +then the calculation can be done by storing not more than $k+n-1$ +equations at a time (plus the original $k$ equations to test results for +sufficiency at the end). +In {\tt CRACK} all intermediate equations generated are checked to see +whether they can be integrated at least once directly by an integration +module. + +\subsection{Integrating exact PDEs} +The technical term `exact' is adapted for PDEs from exterior calculus and +is a small abuse of language but it is useful to characterize the kind of PDEs +under consideration. + +The purpose of the integration module in {\tt CRACK} is to decide +whether a given differential +expression $D$ which involves unknown functions $f^i(x^j),\;\; 1\leq i\leq m$ +of independent variables $x^j, 1\leq j\leq n$ +is a total derivative of another expression $I$ +w.r.t. any variable $x^k, 1\leq k\leq n$ +\[ D(x^i,\; f^j,\; f^j,_p,\; f^j,_{pq}, \ldots) + = \frac{d I(x^i,\; f^j,\; f^j,_p,\; f^j,_{pq}, \ldots)}{d x^k} \] +and to invert the total derivative i.e. to find $I.$ The index $k$ is +reserved in the following for the integration variable $x^k.$ Because +the appropriate constant or function of integration which depends on +all variables except $x^k$ is added to $I,$ a replacement of $0 = D$ +by $0 = I$ in a system of equations is no loss of generality. + +Of course there +always exists a function $I$ with a total derivative equal to $D$ but +the question is whether for \underline{arbitrary} $f^i$ the integral +$I$ is functionally dependent only on the $f^i$ and their derivatives, +and not on integrals of $f^i.$ \\ +\underline{Preconditions:} \\ +$D$ is a polynomial in the $f^i$ and their derivatives. The number of +functions and variables is free. +For deciding the existence of $I$ only, the explicit occurrence of the +variables $x^i$ is arbitrary. In order to actually +calculate $I$ explicitly, $D$ must have the property that all terms in $D$ +must either contain an unknown function of $x^k$ or +must be formally integrable w.r.t. $x^k.$ +That means if $I$ exists then +only a special explicit occurrence of $x^k$ can prevent the +calculation of $I$ +and furthermore only in those terms which do not contain +any unknown function of $x^k.$ +If such terms occur in $D$ and $I$ exists then $I$ can still be expressed +as a polynomial in the $f^i, f^i,_j, \ldots$ and terms containing +indefinite integrals with integrands explicit in $x^k.$ \\ +\underline{Algorithm:} \\ +Successive partial integration of the term with the highest +$x^k$-derivative of any $f^i.$ By that the +differential order w.r.t. $x^k$ is reduced +successively. This procedure is always applicable because steps involve only +differentiations and the polynomial +integration $(\int h^n\frac{\partial h}{\partial x}dx = +h^{n+1}/(n+1))$ where $h$ is a partial derivative of some function +$f^i.$ For a more detailed description see \cite{WoInt}.\\ +\underline{Stop:} \\ +Iteration stops if no term with any $x^k$-derivative of any $f^i$ is left. +If in the remaining un-integrated terms any $f^i(x^k)$ itself occurs, +then $I$ is not expressible with $f^i$ and its derivatives only. In +case no $f^i(x^k)$ occurs then any remaining terms can contain $x^k$ only +explicitly. Whether they can be integrated depends on their formal +integrability. For their integration the REDUCE integrator is applied. \\ +\underline{Example :} \\ +We apply the above algorithm to +\begin{equation} +D := 2f,_yg' + 2f,_{xy}g + gg'^3 + xg'^4 + 3xgg'^2g'' = 0 +\label{D} +\end{equation} +with $f = f(x,y), \, g = g(x), \, '\equiv d/dx.$ +Starting with terms containing $g$ +and at first with the highest derivative $g,_{xx},$ the steps are +\[ +\begin{array}{rcccl} +\int 3xgg,_x^2g,_{xx} dx +& = & \int d(xgg,_x^3) + & - & \int \left( \partial_x(xg) g,_x^3\right) dx \\ \\ +& = & xgg,_x^3 & - & \int g,_x^3(g + xg,_x) dx, +\end{array} \] +\[ I := I + xgg,_x^3 \] +\[ D := D - g,_x^3(g + xg,_x) \] +The new terms $- g,_x^3(g + xg,_x)$ are of lower order than $g,_{xx}$ +and so in the expression $D$ the maximal order of $x$-derivatives +of $g$ is lowered. The conditions that $D$ is exact are the following. +\begin{itemize} +\item The leading derivative must occur linearly before each partial +integration step. +\item After the partial integration of the terms with first order +$x$-derivatives of $f$ the remaining $D$ must not contain $f$ +or other derivatives of $f$, because such terms cannot +be integrated w.r.t.\ $x$ without specifying $f$. +\end{itemize} +The result of $x$- and $y$-integration in the above example is +(remember $g=g(x)$) +\begin{equation} +0 = 2fg + xygg,_x^3 + c_1(x) + c_2(y) \; \; (=I). \nonumber +\end{equation} +{\tt CRACK} can now eliminate $f$ and substitute +for it in all other equations. +\underline{Generalization:} \\ +If after applying the above basic algorithm, terms are left which contain +functions of $x^k$ but each of these functions depends only on a subset of +all $x^i, 1\leq i\leq n,$ then a generalized version of the above algorithm +can still provide a formal expression for the integral $I$ +(see \cite{WoInt}). The price consists of +additional differential conditions, but they are equations in less variables +than occur in the integrated equation. Integrating for example +\begin{equation} +\tilde{D} = D + g^2(y^2 + x\sin y + x^2e^y) \label{Dnew} +\end{equation} +by introducing as few +new functions and additional conditions as possible gives as the integral +$\tilde{I}$ +\begin{eqnarray*} +\tilde{I} & = & 2fg + xygg,_{x}^{3} + c_1(x) + c_2(y) \\ + & & + \frac{1}{3}y^3c_3'' - \cos y(xc_3'' - c_3) ++ e^y(x^2c_3'' - 2xc_3' + 2c_3) +\end{eqnarray*} +with $c_3 = c_3(x), \, '\equiv d/dx$ and the single additional +condition $g^2 = c_3'''.$ +The integration of the new terms of (\ref{Dnew}) is +achieved by partial integration again. For example +\begin{eqnarray*} +\int g^2x^2 dx & = & x^2\int g^2 dx - \int (2x\!\int g^2 dx) dx \\ +& = & x^2\int g^2 dx - 2x\int\!\!\int g^2 dx ++ 2 \int\!\!\int\!\!\int g^2 dx \\ +& = & x^2c_3'' - 2xc_3' + 2c_3 +\end{eqnarray*} +\underline{Characterization:} \\ +This algorithm is a decision algorithm which does not involve any +heuristic. It is fast because time and memory requirements grow only +linearly with the number of terms in $D$ and with the order of +the highest derivative. +After integration the new equation is still a polynomial +in $f^i$ and in the new constant or function of integration,. +Therefore the algorithms for bringing the system into standard form can still +be applied to the PDE-system +after the equation $D = 0$ is replaced by $I = 0.$ + +The complexity of algorithms for bringing a PDE-system into a standard +form depends nonlinearly on the order of these equations because of +the nonlinear increase of the number of different leading derivatives +and by that the number of equations generated intermediately by such +an algorithm. It therefore in general pays off to integrate equations (with +linear expenses) during such a standard form algorithm. The increase +in the number of unknown constants/functions through integration does +not play a role for standard form algorithms because these functions +have less variables and do not increase the number of possible leading +derivatives and therefore not the number of equations to be maintained +during execution of the standard form algorithm. + +If an $f^i,$ which depends on all variables, can be eliminated after an +integration, then depending on its length +it is in general helpful to substitute $f^i$ in other equations and +to reduce the number of equations and functions by one. This is especially +profitable if the replaced expression is short and +contains only functions of less variables than $f^i.$ +\underline{Test:} \\ +The corresponding test input is +\begin{verbatim} +depend f,x,y; +depend g,x; +crack({2*df(f,y)*df(g,x)+2*df(f,x,y)*g+g*df(g,x)**3 + +x*df(g,x)**4+3*x*g*df(g,x)**2*df(g,x,2) + +g**2*(y**2+x*sin y+x**2*e**y)}, + {f,g},{}); +\end{verbatim} +The meaning of the REDUCE command {\tt depend} is to declare that $f$ +depends in an unknown way on $x$ and $y$. For more details on the +algorithm see \cite{WoInt}, for an introduction to REDUCE see \cite{WM}. + +\subsection{Direct separation of PDEs} +As a result of repeated integrations the functions in the +remaining equations have less and less variables. It therefore may happen +that after a substitution an equation results where at least one variable +occurs only explicitly and not as an argument of an unknown function. +Consequently all coefficients of linearly independent expressions in this +variable can be set to zero individually. \\ + +{\em Example:} \\ +$f = f(x,y), \;\; g = g(x), \;\; x,y,z$ are independent variables. +The equation is +\begin{equation} +0 = f,_y + z(f^2+g,_x) + z^2(g,_x+yg^2) \label{sep} +\end{equation} +$x$-separation? $\rightarrow$ no \\ +$y$-separation? $\rightarrow$ no \\ +$z$-separation? $\rightarrow$ yes: $0 \,=\, f,_y \,=\, f^2+g,_x \,=\, +g,_x+yg^2$ \\ +$y$-separation? $\rightarrow$ yes: $0 = g,_x = g^2\;\;$ +(from the third equation from the $z$-separation) + +If $z^2$ had been replaced in (\ref{sep}) by a third +function $h(z)$ then direct separation would not have been possible. +The situation changes if $h$ is a parametric function which is +assumed to be independently given and which should not be +calculated, i.e.\ $f$ and $g$ should be calculated for any +arbitrary given $h(z)$. Then the same separation could have been +done with an extra treatment of the special case $h,_{zz} = 0,$ +i.e.\ $h$ linear in $z$. This different treatment of unknown functions +makes it necessary to input explicitly the functions to be +calculated as the second argument to {\tt CRACK}. The input +in this case would be +\begin{verbatim} +depend f,x,y; +depend g,x; +depend h,z; +crack({df(f,y)+z*f**2+(z+h)*df(g,x)+h*y*g**2},{f,g},{z}); +\end{verbatim} +The third parameter for {\tt CRACK} is necessary to make clear that +in addition to the variables of $f$ and $g$, $z$ is also an independent +variable. + +If the flag {\tt independence\_} is not {\tt nil} then {\tt CRACK} will +stop if linear independence of the explicit expressions of the +separation variable (in the example $1,z,z^2$) is not clear and ask +interactively whether separation should be done or not. + +\subsection{Indirect separation of PDEs} +For the above direct separation a precondition is that at least one +variable occurs only explicitly or as an argument of parametric +functions. The situation where each variable is an argument of at least +one function but no function contains all independent variables of an +equation needs a more elaborate treatment. + +The steps are these +\begin{itemize} + \item A variable $x_a$ is chosen which occurs in as few functions as possible. + This variable will be separated directly later which + requires that all unknown functions $f_i$ containing $x_a$ are to be + eliminated. Therefore, as long as $F:=\{f_i\}$ is not empty do the following: + \begin{itemize} + \item Choose the function $f_i(y_p)$ in $F$ with the smallest number of + variables $y_p$ and with $z_{ij}$ as those variables on which $f_i$ does + not depend. + \item Identify all different products $P_{ik}$ of powers of + $f_i$-derivatives and of $f_i$ in the equation. + Determine the $z_{ij}$-dependent factors $C_{ik}$ of the coefficients + of $P_{ik}$. + \item Choose a $z_{ij}$ and for each $C_{il}$ ($i$ fixed, $l=1,\ldots)$: + \begin{itemize} + \item divide by $C_{il}$ the equation and all the $C_{im}$ with $m>l,$ + \item differentiate the equation and the $C_{im}$ w.r.t.\ $z_{ij}$ + \end{itemize} + \end{itemize} + \item The resulting equation no longer contains any unknown function of $x_a$ + and can be separated w.r.t.\ $x_a$ directly. The + equations arising can be integrated, inverting the sequence of differentiation + and division, by + \begin{itemize} + \item multiplying them and the $C_{im}$ with $m1$ for dynamical symmetries +%(only in case of one ODE for one unknown function) +\item If {\tt lp} is $nil$ then the standard ansatz for $\xi^i, \eta^\alpha$ +is taken which is +\begin{itemize} +\item for point symmetries ({\tt od}=0) $\xi^i = \xi^i(x^j,u^\beta), + u^\alpha = u^\alpha(x^j,u^\beta)$ +\item for contact symmetries ({\tt od}=1) + $ \xi^i := \Omega,_{u,_i}, \;\;\; + \eta := u,_i\Omega,_{u_i} \; - \; \Omega, \;\;\; + \Omega:=\Omega(x^i, u, u,_j)$ +%\item for dynamical symmetries ({\tt od}$>1$) \\ +% $ \xi := \Omega,_{u'}, \;\;\; +% \eta := u'\Omega,_{u'} \; - \; \Omega, \;\;\; +% \Omega:=\Omega(x, u, u',\ldots, u^{({\tt od}-1)})$ +% where {\tt od} must be less than the order of the ODE. +\end{itemize} + + +If {\tt lp} is not $nil$ then {\tt lp} is the ansatz for +$\xi^i, \eta^\alpha$ and must have the form +\begin{itemize} + \item for point symmetries + {\tt \{xi\_\mbox{$x1$} = ..., ..., eta\_\mbox{$u1$} = ..., ...\}} + where {\tt xi\_, eta\_} + are fixed and $x1, \ldots, u1$ are to be replaced by the actual names + of the variables and functions. + \item otherwise {\tt spot\_ = ...} where the expression on the right hand + side is the ansatz for the Symmetry-POTential $\Omega.$ +\end{itemize} + +\item {\tt fl} is the list of free functions in the ansatz +in case {\tt lp} is not $nil.$ +\end{itemize} + +The conditions for the symmetry generators $\xi, \eta$ to provide +infinitesimal transformations +which leave (\ref{k97}) form-invariant to order $O(\varepsilon^2)$ are +formulated by the program {\tt LIEPDE} to be +\begin{eqnarray} +0 & = & \frac{1}{2}x^3\eta,_{yy} - x^3\xi,_{xy} - x^2\xi,_y - 2y\xi,_y + \label{con1} \\ +0 & = & 12y^2\xi,_y - x^4\xi,_{xx} - x^3\xi,_x - 2xy\xi,_x + + 2x^4\eta,_{xy} + x^2\xi + 6y\xi - 2x\eta \\ +0 & = & 2y^2\xi - xy^2\xi,_x - \frac{1}{8}x^5\eta,_{xx} + + \frac{1}{8}x^4\eta,_x + + \frac{1}{4}x^2y\eta,_x + \frac{1}{2}xy^2\eta,_y + - xy\eta \\ +0 & = & \xi,_{yy}. \label{con2} +\end{eqnarray} +{\tt LIEPDE} then calls {\tt CRACK} to solve this system. + +First (\ref{con2}) is integrated to $0 = \xi + c_1y + c_2$ +with new functions $c_1(x), c_2(x).$ +Then $\xi$ is substituted into the other three equations. Now (\ref{con1}) +can be integrated to +\[ 0 = x^3\eta + x^3y^2c_1' - x^3yc_3 - x^3c_4 + x^2y^2c_1 + + \frac{2}{3}y^3c_1 \] +with new functions $c_3(x), c_4(x)$ and $\eta$ can be substituted. +Because the functions $c_1,\ldots,c_4$ are functions of $x$ only, +a separation of the remaining two equations w.r.t.\ the independent +variable $y$ becomes possible which yields 5 and 4 equations. One of +them is $c_1=0$. +After setting $c_1$ to zero, the exact second order ODE +$0 = xc_4'' + 3c_4'$ can be integrated once and +the resulting first order ODE can be solved by +{\tt ODESOLVE} \cite{Mal} to give $c_4 = x^2c_6 - c_5/2$ +with constants $c_5, c_6$. From another equation $c_3$ can be eliminated +and substituted: $c_3 = c_2' - 3c_2/x$. The last function $c_2(x)$ is +solved by {\tt ODESOLVE} from $0 = x^2c_2'' - xc_2' + c_2$ to give +$c_2 = x(c_8\log x + c_7)$. Because now only constants are involved in +the remaining two equations, {\tt CRACK} separates them w.r.t.\ $x$ to obtain 4 +conditions which are solved to give $c_5 = 0$ and $c_6 = - c_8$, +finally obtaining two symmetries (for $c_7 = 0, \, c_8 = -1$ and +$c_7 = -1, \, c_8 = 0$): +\[ +\begin{array}{rclrcl} + \xi_1 & = & x\log x,\hspace{0.5in} & \eta_1 & = & 2y\log x + x^2 - y \\ + \xi_2 & = & x, & \eta_2 & = & 2y . +\end{array} \] +Applying Lie's algorithm by hand, the general solution of (\ref{k97}) +is \cite{Ka} +\[ y = \left\{ \begin{array}{l} + x^2(1 + c_9\tan(c_9\log x + c_{10})) \\ + x^2(1 - c_9\tanh(c_9\log x + c_{10})) \\ + x^2(1 - c_9\coth(c_9\log x + c_{10})) + \end{array} + \right. \] +with constant $c_9, c_{10}$. + +If symmetries of a PDE or of a system of equations shall be determined then +{\tt LIEPDE} does this iteratively by formulating some of the conditions and +solving them by calling {\tt CRACK} to simplify the formulation of the +remaining conditions. If a system of DEs is investigated then the conditions +following from the form-invariance of each single equation are investigated +successively. If a PDE is investigated then conditions which result from +setting to zero the coefficients of the highest derivatives of $y$ are +investigated first. For more details on this iteration see \cite{Alex}, +\cite{Step} and \cite{LIEPDE}. + +A more difficult system of PDEs are the Karpman equations \cite{Karp} +which play a role in plasma physics. In their real form, which is used to +determine symmetries, they are (\cite{Cham}) +\[\rho,_t+w_1\rho,_z+\frac{1}{2}\left[s_1(2\rho,_x\phi,_x+2\rho,_y\phi,_y + +\rho\phi,_{xx}+\rho\phi,_{yy})+ + s_2(2\rho,_z\phi,_z+\rho\phi,_{zz})\right] = 0\] +\[\phi,_t+w_1\phi,_z-\frac{1}{2}\left[s_1\left(\frac{\rho,_{xx}}{\rho} + +\frac{\rho,_{yy}}{\rho}-\phi,_x^2-\phi,_y^2\right)+ + s_2\left(\frac{\rho,_{zz}}{\rho}-\phi,_z^2\right)\right]+a_1\nu = 0\] +\[\nu,_{tt}-(w_2)^2(\nu,_{xx}+\nu,_{yy}+\nu,_{zz})- +2a_2\rho(\rho,_{xx}+\rho,_{yy}+\rho,_{zz})-2a_2(\rho,_x^2+\rho,_y^2+\rho,_z^2) = 0\] +with the three functions $\rho,\phi,\nu$ of four variables $t,x,y,z$ and +with constant parameters $a_i,s_i,w_i.$ + +At first, preliminary symmetry conditions are +derived and solved successively +for each of the three equations. +The solution +of the preliminary conditions for the +first equation +requires 31 integrations and states that all $\xi^i$ are +functions of $t,x,y,z$ only. +The preliminary conditions of the second equation do not provide new +constraints. +The result from the preliminary conditions for the third equation +is that $\nu$ is a function of $t,x,y,z$ only. This needs 4 +integrations. +After 7.1/0.1 sec the full conditions for the first equation are derived +which to solve requires further 77 integrations. +The remaining full conditions for the second equation +to solve requires 6 integrations. Finally, +the full conditions for the last equation are +solved with three more integrations. + +The general solution for the symmetry generators then reads +\[ \begin{array}{rclrcl} + \xi^x & = & - y c_1 + c_2 \;\;\;\;\; & \eta^r & = & 0 \\ + \xi^y & = & x c_1 + c_3 & \eta^\phi & = & a_1 c_6 t^2 + a_1 c_7 t + c_8 \\ + \xi^z & = & c_4 & \eta^v & = & - c_6 t - c_7 \\ + \xi^t & = & c_5 & & & +\end{array} +\] +with constants $c_1, \ldots, c_8.$ The corresponding 8 symmetry generators are +\begin{eqnarray*} + X_1 = \partial_x & \;\;\;\;\;\;\;\;\;\; & X_5 = y\partial_x - x\partial_y \\ + X_2 = \partial_y & & X_6 = \partial_\phi \\ + X_3 = \partial_z & & X_7 = a_1t\partial_\phi - \partial_\nu \\ + X_4 = \partial_t & & X_8 = a_1t^2\partial_\phi - 2t\partial_\nu. +\end{eqnarray*} + +The total time in a test run with {\tt lisp(print\_:=nil);} was +260/3.2 seconds on a PC486 with 33 MHz and 4MB RAM, +i.e. less than 5 min. +For comparison, the same calculation reported in \cite{Cham}, also split +into 6 parts but with integrations done by hand, took more than 2 hours CPU +on a VAX 8600 to formulate and simplify the symmetry conditions using the +program {\tt SYMMGRP.MAX} written in MACSYMA. +The corresponding input for {\tt LIEPDE} is +\begin{verbatim} +depend r,x,y,z,tt; +depend f,x,y,z,tt; +depend v,x,y,z,tt; + +de := {{df(r,tt)+w1*df(r,z) + + s1*(df(r,x)*df(f,x)+df(r,y)*df(f,y)+r*df(f,x,2)/2+r*df(f,y,2)/2) + + s2*(df(r,z)*df(f,z)+r*df(f,z,2)/2), + + df(f,tt)+w1*df(f,z) + - (s1*(df(r,x,2)/r+df(r,y,2)/r-df(f,x)**2-df(f,y)**2) + + s2*(df(r,z,2)/r-df(f,z)**2))/2 + a1*v, + + df(v,tt,2)-w2**2*(df(v,x,2)+df(v,y,2)+df(v,z,2)) + - 2*a2*r*(df(r,x,2)+df(r,y,2)+df(r,z,2)) + - 2*a2*(df(r,x)**2+df(r,y)**2+df(r,z)**2)}, + + {r,f,v}, {x,y,z,tt}}; +mo := {0, nil, nil}; +LIEPDE(de,mo); +\end{verbatim} + +\subsection{Determining integrating factors} +Another way to solve or simplify nonlinear DEs is to determine first +integrals by finding integrating factors. For the equation (6.37) of +\cite{Ka} (which has no point symmetry) +\begin{equation} +0 = y'' + y'(2y + F(x)) + F(x)y^2 - H(x) \label{k37} +\end{equation} +for $y(x)$ and parametric functions $F, H$ of $x$ the input +consists of +\begin{verbatim} +depend f,x; +depend h,x; +depend y,x; +de := {df(y,x,2) = -(2*y+f)*df(y,x)-f*y**2+h, y, x}; +mo := {0,{},2}; +FIRINT(de,mo); +\end{verbatim} +The arguments to {\tt FIRINT} are similar to those of {\tt LIEPDE}\@. +Here {\tt mo = \{fi,fl,dg\}} specifies an ansatz for the first integral. + + For {\tt fi=0} the ansatz for the first integral is determined by +{\tt dg}: The first integral is assumed to be a +polynomial of degree {\tt dg} in $y^{(n-1)}$ (with $n$ as the order of the ODE) +and with arbitrary functions of $x, y,\ldots,y^{(n-2)}$ as coefficients. +In this case +{\tt fl} has no meaning and is set to \{\}. +For {\tt fi}$\neq${\tt 0, fi} is the ansatz for the first integral and +{\tt fl} is a list of +unknown functions in the ansatz, which are to be solved for. In this case +{\tt dg} has no meaning. + + The above example determines first integrals which are at most quadratic +in $y'$ for equation (6.37) in \cite{Ka}. +{\tt FIRINT} starts with the ansatz +\begin{equation} +{\rm const.} = h_2(x,y)y'^2 + h_1(x,y)y' + h_0(x,y) \label{fians} +\end{equation} +and formulates the determining system by total differentiation of +(\ref{fians}), identification of $y''$ with $y''$ in (\ref{k37}) and +direct separation of $y',$ to produce +\begin{eqnarray*} +0 & = & h_2,_y \\ +0 & = & (H - F y^2)h_1 + h_0,_x \\ +0 & = & h_1,_x + h_2,x - (2F + 4y)h_2 \\ +0 & = & 2(H - Fy^2)h_2 - (F - 2y)h_1 + h_0,y + h_1,x. +\end{eqnarray*} +It then calls {\tt CRACK} which provides the solution for $h_0,h_1,h_2.$ +The first integral is +\begin{equation} +\mbox{const.} = \left( \frac{dy}{dx}+y^2 \right) e^{\int \!F\,dx} - +\int He^{\int \!F\,dx} dx +\end{equation} +which is linear in $y'$. Many other nonlinear ODEs in \cite{Ka} have quadratic +first integrals. + +\subsection{Determining a Lagrangian for a given 2nd order ODE} +The knowledge of a Lagrangian $L$ for a given set of differential +equations may be useful in solving and understanding these equations. +If $L$ is known it is easier to determine symmetries, conserved +quantities and singular points. An equivalent variational principle +could also be useful for a more efficient numerical solution. +This problem is known as the inverse problem of variational calculus. +For example, the first transcendental Painlev\'{e} equation +\begin{equation} + y'' = 6y^2 + x \label{pain} +\end{equation} +has no point symmetries but proves to have a Lagrangian with the +structure +\begin{equation} + L = u(x,y)(y')^2 + v(x,y). \label{lagr} +\end{equation} +(The other 5 transcendental Painlev\'{e} equations have a Lagrangian +of this structure as well.) +A program {\tt LAGRAN} formulates the conditions for $u$ and $v$ (a first +order PDE-system). The call is +\begin{verbatim} +depend f,x; depend y,x; +de := {df(y,x,2) = 6*y**2 + x, y, x}; +mo := {0,{}}; +LAGRAN(de,mo); +\end{verbatim} + +If a system of ODEs or a PDE with at least two variables is given, +then the existence of an equivalent Lagrangian $L$ is not guaranteed. +Only in the case of +a single 2nd order ODE, which is treated by the program {\tt LAGRAN}, +must a Lagrangian which is locally equivalent to the ODE +exist. As a consequence the determination of $L$ for a second order +ODE is in general not simpler than the solution of the ODE itself. +Therefore the structure of +$L$ must be specified, which is done through (\ref{lagr}). + + In the call of {\tt LAGRAN} the second argument {\tt mo=\{lg,fl\}} allows +input of an ansatz for the Lagrangian. +For {\tt lg=0} the default ansatz for the first integral is as given in +(\ref{lagr}). +For {\tt lg$\neq$0, lg} is the ansatz for the Lagrangian and {\tt fl} is a +list of unknown functions in the ansatz which are to be solved. +For equation (\ref{pain}) the resulting equivalent Lagrangian is +\[ L = y'^2 + xy + 4y^3. \] +Because the first order system for $u$ and $v$ is normally not too +difficult, more complicated problems can also be solved, such as the +determination of $L$ for the 6'th transcendental Painlev\'{e} equation +\begin{eqnarray} + y'' = & \frac{1}{2}\left(\frac{1}{y}+\frac{1}{y-1}+\frac{1}{y-x}\right) y'^2 +- \left(\frac{1}{x}+\frac{1}{x-1}+\frac{1}{y-x}\right)y' \nonumber \\ +& + \frac{y(y-1)(y-x)}{x^2(x-1)^2}\left(a+\frac{bx}{y^2}+\frac{c(x-1)}{(y-1)^2} ++\frac{dx(x-1)}{(y-x)^2}\right) +\end{eqnarray} +for which $L$ turns out to be +\[ +\begin{array}{rcll} +L & = & 1/[xy(x-y)(x+1)(x-1)(y-1)] \cdot [(x+1)(x-1)^2x^2y'^2 \\ + & & - 2a(xy+x+y)(x-y)(y-1)y + 2b(x+y+1)(x-y)(y-1)x \\ + & & + 2c(x+y)(x-y)(x-1)y - 2d(x-1)(y+1)(y-1)xy ]. +\end{array} \] + +\subsection{A factorization ansatz for a given ODE} +A further possible way to integrate an $n$'th order ODE is to decompose it +into two ODEs of order $k$ and $n-k$. If one specifies the structure of the +$k$'th order ODE and demands that these ODEs can be solved successively then +this leads to a system of PDEs in the variables +$x, y, \ldots, y^{k-1}$ with a good chance of solution. + +To solve the ODE (6.122) in \cite{Ka} +\begin{equation} +0 = yy'' - y'^2 + F(x)yy' + Q(x)y^2 \label{6.122} +\end{equation} +the input would be +\begin{verbatim} +depend f,x; +depend q,x; +depend y,x; +de := {df(y,x,2) = df(y,x)**2/y - f*df(y,x) - y*q, y, x}; +mo := {2,{}}; +DECOMP(de,mo); +\end{verbatim} +In contrast to {\tt FIRINT}, {\tt LAGRAN} the ODE could here +be in the implicit form $0 = \ldots \;$ as well. + +The second argument {\tt mo = \{as,fl\}} specifies an ansatz for the $k$'th +order ODE. If {\tt as} is an integer between 1 and 4 inclusive +then a default ansatz +is taken and {\tt fl} (the list of further unknown functions) is \{\}. +The 4 ans\"atze for \verb+as+ $\in$ [1,4] are +\begin{eqnarray} +y' & = & a(x)\,b(y) \nonumber \\ +y' & = & a(x)\,y + b(x) \label{d2} \\ +y' & = & a(x)\,y^n + b(x)\,y \nonumber \\ +y' & = & a(x)\,y^2 + b(x)\,y + c(x) \nonumber +\end{eqnarray} + + For {\tt as}$\not\in$[1,4], {\tt as} itself is the ansatz for the $k$'th +order ODE with $y^{(k)}$ eliminated on the left side and {\tt fl} is +a list of unknown functions in the ansatz, which are to be solved for. + +The program {\tt DECOMP} formulates the determining system, in the above +example +\begin{eqnarray*} +0 & = & b^2 \\ +0 & = & - F(x)b - b' + ab \\ +0 & = & - F(x)a - Q(x) - a' +\end{eqnarray*} +and calls {\tt CRACK} to solve it. Because the result +\begin{eqnarray*} +a(x) & = & \left(c_1 - \int Qe^{-\int F dx} dx\right)e^{-\int F dx} \\ +b(x) & = & 0 +\end{eqnarray*} +contains $n-k = 1$ constant(s) of integration, this factorization ansatz +does not restrict the solution space of (\ref{6.122}) +and because of (\ref{d2}) the general solution is +\[y = c_2e^{\int \left[\left(c_1 - \int Qe^{-\int F dx} dx\right)e^{-\int F dx} +\right] dx}.\] + +\subsection{General remarks on complexity} +In general, PDE-systems are easier to solve, the fewer arbitrary functions of +fewer variables are contained in the general solution. This in turn +is the case if more and more equations have to be satisfied for less functions, +i.e. the more restrictive is the PDE-system. +Having more equations to solve for a given number of functions +improves the +chance of finding an integrable one among them and provides +more possibilities to combine them and find a quick way to solve +them. For example, it is usually more difficult to find all +point symmetries of a very simple ODE with many point symmetries +than to show that an ODE that is possibly more difficult +to solve has no point symmetry. +An appropriate strategy could therefore be to start an +investigation with a very restrictive ansatz and later to try +less restrictive ones. For example, an ODE could be investigated at first +with respect to point symmetries and if none is found then one +could look for contact and then for dynamical symmetries. + +Experience shows that nonlinear systems may lead to an +explosion in the length of generated equations much quicker +than linear equations +even if they have more independent variables or are of higher order. +For solving ODEs one should therefore investigate infinitesimal +symmetries or integrating factors first which provide linear systems +and only later consider the factorization into two ODEs of lower order. + +\subsection{Acknowledgement} +We want to thank especially Francis Wright and Herbert Melenk for +continuous help in respect with special features and bugs of REDUCE. + +\newpage +\begin{thebibliography}{99} +\bibitem{Riq} C. Riquier, Les syst\`{e}mes d'\'{e}quations aux d\'{e}riv\'{e}es +partielles, Gauthier--Villars, Paris (1910). +\bibitem{Th} J. Thomas, Differential Systems, AMS, Colloquium +publications, v. 21, N.Y. (1937). +\bibitem{Ja} M. Janet, Le\c{c}ons sur les syst\`{e}mes d'\'{e}quations aux +d\'{e}riv\'{e}es, Gauthier--Villars, Paris (1929). +\bibitem{Topu} V.L. Topunov, Reducing Systems of Linear Differential +Equations to a Passive Form, Acta Appl. Math. 16 (1989) 191--206. +\bibitem{Alex} A.V. Bocharov and M.L. Bronstein, Efficiently +Implementing Two Methods of the Geometrical Theory of Differential +Equations: An Experience in Algorithm and Software Design, Acta. Appl. +Math. 16 (1989) 143--166. +\bibitem{Reid1} G.J. Reid, A triangularization algorithm which +determines the Lie symmetry algebra of any system of PDEs, J.Phys. A: +Math. Gen. 23 (1990) L853-L859. +\bibitem{FS} F. Schwarz, Automatically Determining Symmetries of Partial +Differential Equations, Computing 34, (1985) 91-106. +\bibitem{Fush} W.I. Fushchich and V.V. Kornyak, Computer Algebra +Application for Determining Lie and Lie--B\"{a}cklund Symmetries of +Differential Equations, J. Symb. Comp. 7 (1989) 611--619. +\bibitem{Ka} E. Kamke, Differentialgleichungen, L\"{o}sungsmethoden +und L\"{o}sungen, Band 1, Gew\"{o}hnliche Differentialgleichungen, +Chelsea Publishing Company, New York, 1959. +\bibitem{Wo} T. Wolf, An Analytic Algorithm for Decoupling and Integrating +systems of Nonlinear Partial Differential Equations, J. Comp. Phys., +no. 3, 60 (1985) 437-446 and, Zur analytischen Untersuchung und exakten +L\"{o}sung von Differentialgleichungen mit Computeralgebrasystemen, +Dissertation B, Jena (1989). +\bibitem{WoInt} T. Wolf, The Symbolic Integration of Exact PDEs, +preprint, submitted to J.\ Symb.\ Comp. (1991). +\bibitem{WM} M.A.H. MacCallum, F.J. Wright, Algebraic Computing with REDUCE, +Clarendon Press, Oxford (1991). +\bibitem{Mal} M.A.H. MacCallum, An Ordinary Differential Equation +Solver for REDUCE, Proc. ISAAC'88, Springer Lect. Notes in Comp Sci. +358, 196--205. +\bibitem{Step} H. Stephani, Differential equations, Their solution using +symmetries, Cambridge University Press (1989). +\bibitem{LIEPDE} T. Wolf, An efficiency improved program {\tt LIEPDE} +for determining Lie-symmetries of PDEs, Proceedings of the workshop on +Modern group theory methods in Acireale (Sicily) Nov. (1992) +\bibitem{Karp} V.I. Karpman, Phys. Lett. A 136, 216 (1989) +\bibitem{Cham} B. Champagne, W. Hereman and P. Winternitz, The computer + calculation of Lie point symmetries of large systems of differential + equation, Comp. Phys. Comm. 66, 319-340 (1991) + +\end{thebibliography} + +\end{document} Index: r36/doc/CVIT.TEX ================================================================== --- r36/doc/CVIT.TEX +++ r36/doc/CVIT.TEX @@ -1,421 +1,421 @@ -\documentstyle[11pt,reduce]{article} -\title{CVIT - Program for fast calculation of Dirac's $\gamma$-matrices -traces} -\date{(Version: 1.2. Release: March, 11, 1990)} -\author{V. Ilyin, A. Kryukov, A. Rodionov and A. Taranov \\ -Institute for Nuclear Physics \\ -Moscow State University \\ -Moscow, 119899 USSR \\ -Phone 939-58-92 \\ -Telex 411483 MGU SU \\ -Fax (011)7095-939-01-26} - -\begin{document} -\maketitle -\section*{Abstract} - -In modern high energy physics the calculation of Feynman diagrams are -still very important. One of the difficulties of these calculations -are trace calculations. So the calculation of traces of Dirac's -$\gamma$-matrices were one of first task of computer algebra systems. -All available algorithms are based on the fact that gamma-matrices -constitute a basis of a Clifford algebra: -\begin{verbatim} - {Gm,Gn} = 2gmn. -\end{verbatim} - -We present the implementation of an alternative algorithm based on -treating of gamma-matrices as 3-j symbols (details may be found in -[1,2]). - -The program consists of 5 modules described below. - -\newpage -\begin{verbatim} - - MODULES CROSS REFERENCES - +--------+ - | REDUCE | - |________| |ISIMP1 - ISIMP2| +-----------------------+ - +--->-----| RED_TO_CVIT_INTERFACE | - |_______________________| - CALC_SPUR| |REPLACE_BY_VECTOR - | |REPLACE_BY_VECTORP - | |GAMMA5P - ^ V - +--------------+ - | CVITMAPPING | - |______________| - ^ - |PRE-CALC-MAP - |CALC_MAP_TAR - |CALC_DENTAR - | - +-------------+ - | INTERFIERZ | - |_____________| - | |MK-NUMR - | |STRAND-ALG-TOP - | ^ - MAP-TO-STRAND| +------------+ - INCIDENT1| | EVAL-MAPS | - | |____________| - ^ |DELETEZ1 - | |CONTRACT-STRAND - +----------------+ |COLOR-STRAND - | MAP-TO-STRAND |---->---+ - |________________| - - - Requires of REDUCE version: 3.2, 3.3. - -\end{verbatim} - - -\section*{Module RED\_TO\_CVIT\_INTERFACE} - -\begin{center} -Author: A.P.Kryukov \\ -Purpose:interface REDUCE and CVIT package -\end{center} - -RED\_TO\_CVIT\_INTERFACE module is intended for connection of REDUCE -with main module of CVIT package. The main idea is to preserve -standard REDUCE syntax for high energy calculations. For realization -of this we redefine {\ SYMBOLIC PROCEDURE ISIMP1} from HEPhys module of -REDUCE system. - -After loading CVIT package user may use switch CVIT which is {\tt ON} by -default. If switch CVIT is {\tt OFF} then calculations of Diracs matrices -traces are performed using standard REDUCE facilities. If CVIT switch -is {\tt ON} then CVIT package will be active. - -{\tt RED\_TO\_CVIT\_INTERFACE} module performs some primitive simplification -and control input data independently. For example it remove $G_mG_m$, -check parity of the number of Dirac matrices in each trace {\em etc}. -There is one principal restriction concerning G5-matrix. There are no -closed form for trace in non-integer dimension case when trace include -G5-matrix. The next restriction is that if the space-time dimension -is integer then it must be even (2,4,6,...). If these and other -restrictions are violated then the user get corresponding error -message. List of messages is included. - -\begin{center} -\begin{verbatim} - LIST OF IMPORTED FUNCTIONS -------------------------------------------------- - Function From module -------------------------------------------------- - ISIMP2 HEPhys - CALC_SPUR CVITMAPPING -------------------------------------------------- -\end{verbatim} - -\begin{verbatim} - LIST OF EXPORTED FUNCTION -------------------------------------------------- - Function To module -------------------------------------------------- - ISIMP1 HEPhys (redefine) - REPLACE_BY_VECTOR EVAL_MAP - REPLACE_BY_VECTORP EVAL__MAP - GAMMA5P CVITMAPPING, EVAL_MAP -------------------------------------------------- -\end{verbatim} -\end{center} - - - -\section*{Module CVITMAPPING} - -\begin{center} -Author: A.Ya.Rodionov \\ -Purpose: graphs reduction -\end{center} - -CVITMAPPING module is intended for diagrams calculation according to -Cvitanovic - Kennedy algorithm. The top function of this module -CALC\_SPUR is called from RED\_TO\_CVIT\_INTERFACE interface module. -The main idea of the algorithm consists in diagram simplification -according to rules (1.9') and (1.14) from [1]. The input data - trace -of Diracs gamma matrices (G-matrices) has a form of a list of -identifiers lists with cyclic order. Some of identifiers may be -identical. In this case we assume summation over dummy indices. So -trace Sp(GbGr).Sp(GwGbGcGwGcGr) is represented as list ((b r) (w b c w -c r)). - -The first step is to transform the input data to ``map'' structure and -then to reduce the map to a ``simple'' one. This transformation is made -by function TRANSFORM\_MAP\_ (top function). Transformation is made in -three steps. At the first step the input data are transformed to the -internal form - a map (by function PREPARE\_MAP\_). At the second step -a map is subjected to Fierz transformations (1.14) (function -MK\_SIMPLE\_MAP\_). At this step of optimization can be maid (if -switch CVITOP is on) by function MK\_FIRZ\_OP. In this case Fierzing -starts with linked vertices with minimal distance (number of vertices) -between them. After Fierz transformations map is further reduced by -vertex simplification routine MK\_SIMPLE\_VERTEX using (1.9'). -Vertices reduced to primitive ones, that is to vertices with three or -less edges. This is the last (third) step in transformation from -input to internal data. - -The next step is optional. If switch CVITBTR is on factorisation of -bubble (function FIND\_BUBBLES1) and triangle (function -FIND\_TRIANGLES1) submaps is made. This factorisation is very -efficient for ``wheel'' diagrams and unnecessary for ``lattice'' diagrams. -Factorisation is made recursively by substituting composed edges for -bubbles and composed vertices for triangles. So check (function -SORT\_ATLAS) must be done to test possibility of future marking -procedure. If the check fails then a new attempt to reorganize atlas -(so we call complicated structure witch consists of MAP, COEFFicient -and DENOMinator) is made. This cause backtracking (but very seldom). -Backtracking can be traced by turning on switch CVITRACE. FIND\_BUBLTR -is the top function of this program's branch. - -Then atlases must be prepared (top function WORLD\_FROM\_ATLAS) for -final algebraic calculations. The resulted object called ``world'' -consists of edges names list (EDGELIST), their marking variants -(VARIANTS) and WORLD1 structure. WORLD1 structure differs from WORLD -structure in one point. It contains MAP2 structure instead of MAP -structure. MAP2 is very complicated structure and consist of VARIANTS, -marking plan and GSTRAND. (GSTRAND constructed by PRE!-CALC!-MAP\_ -from INTERFIERZ module.) By marking we understand marking of edges -with numbers according to Cvitanovic - Kennedy algorithm. - -The last step is performed by function CALC\_WORLD. At this step -algebraic calculations are done. Two functions CALC\_MAP\_TAR and -CALC\_DENTAR from INTERFIERZ module make algebraic expressions in the -prefix form. This expressions are further simplified by function -{\tt REVAL}. This is the REDUCE system general function for algebraic -expressions simplification. {\tt REVAL} and {\tt SIMP!*} are the only REDUCE -functions used in this module. - -There are also some functions for printing several internal -structures: PRINT\_ATLAS, PRINT\_VERTEX, PRINT\_EDGE, PRINT\_COEFF, -PRINT\_DENOM. This functions can be used for debugging. - -If an error occur in module CVITMAPPING the error message ``ERROR IN -MAP CREATING ROUTINES'' is displayed. Error has number 55. The switch -CVITERROR allows to give full information about error: name of -function where error occurs and names and values of function's -arguments. If CVITERROR switch is on and backtracking fails message -about error in SORT\_ATLAS function is printed. The result of -computation however will be correct because in this case factorized -structure is not used. This happens extremely seldom. - - -\begin{verbatim} - List of imported function -------------------------------------------------- - function from module -------------------------------------------------- - REVAL REDUCE - SIMP!* REDUCE - CALC_MAP_TAR INTERFIERZ - CALC_DENTAR INTERFIERZ - PRE!-CALC!-MAP_ INTERFIERZ - GAMMA5P RED_TO_CVIT_INTERFACE -------------------------------------------------- -\end{verbatim} - -\begin{verbatim} - List of exported function -------------------------------------------------- - function to module -------------------------------------------------- - CALC_SPUR REDUCE - CVIT interface -------------------------------------------------- -\end{verbatim} - -\begin{verbatim} - Data structure - WORLD ::= (EDGELIST,VARIANTS,WORLD1) - WORLD1 ::= (MAP2,COEFF,DENOM) - MAP2 ::= (MAPS,VARIANTS,PLAN) - MAPS ::= (EDGEPAIR . GSTRAND) - MAP1 ::= (EDGEPAIR . MAP) - MAP ::= list of VERTICES (unordered) - EDGEPAIR ::= (OLDEDGELIST . NEWEDGELIST) - COEFF ::= list of WORLDS (unordered) - ATLAS ::= (MAP,COEFF,DENOM) - GSTRAND ::= (STRAND*,MAP,TADPOLES,DELTAS) - VERTEX ::= list of EDGEs (with cyclic order) - EDGE ::= (NAME,PROPERTY,TYPE) - NAME ::= ATOM - PROPERTY ::= (FIRSTPAIR . SECONDPAIR) - TYPE ::= T or NIL - ------------------------------------------------ - *Define in module MAP!-TO!-STRAND. - -\end{verbatim} - -\section*{Modules INTERFIERZ, EVAL\_MAPS, AND MAP-TO-STRAND.} - -\begin{center} -Author: A.Taranov \\ -Purpose: evaluate single Map -\end{center} - -Module INTERFIERZ exports to module CVITMAPPING three functions: -PRE-CALC-MAP\_, CALC-MAP\_TAR, CALC-DENTAR. - -Function PRE-CALC-MAP\_ is used for preliminary processing of a map. It -returns a list of the form (STRAND NEWMAP TADEPOLES DELTAS) where -STRAND is strand structure described in MAP-TO-STRAND module. NEWMAP -is a map structure without ``tadepoles'' and ``deltas''. ``Tadepole'' is a -loop connected with map with only one line (edge). ``Delta'' is a single -line disconnected from a map. TADEPOLES is a list of ``tadepole'' -submaps. DELTAS is a list (CONS E1 E2) where E1 and E2 are - -Function CALC\_MAP\_TAR takes a list of the same form as returned by -PRE-CALC-MAP\_, a-list, of the form (... edge . weight ... ) and -returns a prefix form of algebraic expression corresponding to the map -numerator. - -Function CALC-DENTAR returns a prefix form of algebraic expression -corresponding to the map denominator. - -Module EVAL-MAP exports to module INTERFIERZ functions MK-NUMR and -STRAND-ALG-TOP. - -Function MK-NUMR returns a prefix form for some combinatorial -coefficient (Pohgammer symbol). - -Function STRAND-ALG-TOP performs an actual computation of a prefix -form of algebraic expression corresponding to the map numerator. This -computation is based on a ``strand'' structure constructed from the -``map'' structure. - -Module MAP-TO-STRAND exports functions MAP-TO-STRAND, INCIDENT1 to -module INTERFIERZ and functions DELETEZ1, CONTRACT-STRAND, -COLOR-STRAND to module EVAL-MAPS. - -Function INCIDENT1 is a selector in ``strand'' structure. DELETEZ1 -performs auxiliary optimization of ``strand''. MAP-TO-STRAND transforms -``map'' to ``strand'' structure. The latter is describe in program -module. - -CONTRACT-STRAND do strand vertex simplifications of ``strand'' and -COLOR-STRAND finishes strand generation. - -\begin{verbatim} - - Description of STRAND data structure. - STRAND ::= - VERTEX ::= . ( ) - ROAD ::= . NUMBER - NAME ::=NUMBER -\end{verbatim} - - -\subsection*{ LIST OF MESSAGES} - -\begin{itemize} - -\item{CALC\_SPUR: $<$vecdim$>$ IS NOT EVEN SPACE-TIME DIMENSION} - The dimension of space-time $<$vecdim$ $is integer but not -even. Only even numeric dimensions are allowed. - -\item{NOSPUR NOT YET IMPLEMENTED} - Attempt to calculate trace when NOSPUR switch is on. This facility -is not implemented now. - -\item{G5 INVALID FOR VECDIM NEQ 4} - Attempt to calculate trace with gamma5-matrix for space-time -dimension not equal to 4. - -\item{CALC\_SPUR: $<$expr$>$ HAS NON-UNIT DENOMINATOR} -The has non-unit denominator. - -\item{THREE INDICES HAVE NAME $<$name$>$} - There are three indices with equal names in evaluated expression. - -\end{itemize} - -\begin{verbatim} - List of switches ------------------------------------------------------------- - switch default comment ------------------------------------------------------------- - CVIT ON If it is on then use Kennedy- - Cvitanovic algorithm else use - standard facilities. - CVITOP OFF Fierz optimization switch - CVITBTR ON Bubbles and triangles - factorisation switch - CVITRACE OFF Backtracking tracing switch ------------------------------------------------------------- -\end{verbatim} - - -\begin{verbatim} - Functions cross references*. - -CALC_SPUR - | - +-->SIMP!* (REDUCE) - | - +-->CALC_SPUR0 - | - |--->TRANSFORM_MAP_ - | | - | |--->MK_SIMPLE_VERTEX - | +--->MK_SIMPLE_MAP_ - | | - | +--->MK_SIMPLE_MAP_1 - | | - | +--->MK_FIERS_OP - | - |--->WORLD_FROM_ATLAS - | | - | +--->CONSTR_WORLDS - | | - | +---->MK_WORLD1 - | | - | +--->MAP_2_FROM_MAP_1 - | | - | |--->MARK_EDGES - | +--->MAP_1_TO_STRAND - | | - | +-->PRE!-CALC!-MAP_ - | (INTERFIRZ) - | - |--->CALC_WORLD - | | - | |--->CALC!-MAP_TAR (INTERFIRZ) - | |--->CALC!-DENTAR (INTERFIRZ) - | +--->REVAL (REDUCE) - | - +--->FIND_BUBLTR - | - +--->FIND_BUBLTR0 - | - |--->SORT_ATLAS - +--->FIND_BUBLTR1 - | - |--->FIND_BUBLES1 - +--->FIND_TRIANGLES1 -*Unmarked functions are from CVITMPPING module. - -\end{verbatim} - - -\section*{References} - -\begin{itemize} - -\item{1.} -Ilyin V.A., Kryukov A.P., Rodionov A.Ya., Taranov A.Yu. -Fast algorithm for calculation of Diracs gamma-matrices -traces. SIGSAM Bull., 1989, v.23, no.4, pp.15-24. - -\item{2.} -Kennedy A.D. Phys.Rev., 1982, D26, p.1936. -\end{itemize} - -\section*{Keywords} - -REDUCE, GAMMA-MATRIX, TRACE, SPACE-TIME DIMENSION, HIGH ENERGY PHYSICS. - -\end{document} +\documentstyle[11pt,reduce]{article} +\title{CVIT - Program for fast calculation of Dirac's $\gamma$-matrices +traces} +\date{(Version: 1.2. Release: March, 11, 1990)} +\author{V. Ilyin, A. Kryukov, A. Rodionov and A. Taranov \\ +Institute for Nuclear Physics \\ +Moscow State University \\ +Moscow, 119899 USSR \\ +Phone 939-58-92 \\ +Telex 411483 MGU SU \\ +Fax (011)7095-939-01-26} + +\begin{document} +\maketitle +\section*{Abstract} + +In modern high energy physics the calculation of Feynman diagrams are +still very important. One of the difficulties of these calculations +are trace calculations. So the calculation of traces of Dirac's +$\gamma$-matrices were one of first task of computer algebra systems. +All available algorithms are based on the fact that gamma-matrices +constitute a basis of a Clifford algebra: +\begin{verbatim} + {Gm,Gn} = 2gmn. +\end{verbatim} + +We present the implementation of an alternative algorithm based on +treating of gamma-matrices as 3-j symbols (details may be found in +[1,2]). + +The program consists of 5 modules described below. + +\newpage +\begin{verbatim} + + MODULES CROSS REFERENCES + +--------+ + | REDUCE | + |________| |ISIMP1 + ISIMP2| +-----------------------+ + +--->-----| RED_TO_CVIT_INTERFACE | + |_______________________| + CALC_SPUR| |REPLACE_BY_VECTOR + | |REPLACE_BY_VECTORP + | |GAMMA5P + ^ V + +--------------+ + | CVITMAPPING | + |______________| + ^ + |PRE-CALC-MAP + |CALC_MAP_TAR + |CALC_DENTAR + | + +-------------+ + | INTERFIERZ | + |_____________| + | |MK-NUMR + | |STRAND-ALG-TOP + | ^ + MAP-TO-STRAND| +------------+ + INCIDENT1| | EVAL-MAPS | + | |____________| + ^ |DELETEZ1 + | |CONTRACT-STRAND + +----------------+ |COLOR-STRAND + | MAP-TO-STRAND |---->---+ + |________________| + + + Requires of REDUCE version: 3.2, 3.3. + +\end{verbatim} + + +\section*{Module RED\_TO\_CVIT\_INTERFACE} + +\begin{center} +Author: A.P.Kryukov \\ +Purpose:interface REDUCE and CVIT package +\end{center} + +RED\_TO\_CVIT\_INTERFACE module is intended for connection of REDUCE +with main module of CVIT package. The main idea is to preserve +standard REDUCE syntax for high energy calculations. For realization +of this we redefine {\ SYMBOLIC PROCEDURE ISIMP1} from HEPhys module of +REDUCE system. + +After loading CVIT package user may use switch CVIT which is {\tt ON} by +default. If switch CVIT is {\tt OFF} then calculations of Diracs matrices +traces are performed using standard REDUCE facilities. If CVIT switch +is {\tt ON} then CVIT package will be active. + +{\tt RED\_TO\_CVIT\_INTERFACE} module performs some primitive simplification +and control input data independently. For example it remove $G_mG_m$, +check parity of the number of Dirac matrices in each trace {\em etc}. +There is one principal restriction concerning G5-matrix. There are no +closed form for trace in non-integer dimension case when trace include +G5-matrix. The next restriction is that if the space-time dimension +is integer then it must be even (2,4,6,...). If these and other +restrictions are violated then the user get corresponding error +message. List of messages is included. + +\begin{center} +\begin{verbatim} + LIST OF IMPORTED FUNCTIONS +------------------------------------------------- + Function From module +------------------------------------------------- + ISIMP2 HEPhys + CALC_SPUR CVITMAPPING +------------------------------------------------- +\end{verbatim} + +\begin{verbatim} + LIST OF EXPORTED FUNCTION +------------------------------------------------- + Function To module +------------------------------------------------- + ISIMP1 HEPhys (redefine) + REPLACE_BY_VECTOR EVAL_MAP + REPLACE_BY_VECTORP EVAL__MAP + GAMMA5P CVITMAPPING, EVAL_MAP +------------------------------------------------- +\end{verbatim} +\end{center} + + + +\section*{Module CVITMAPPING} + +\begin{center} +Author: A.Ya.Rodionov \\ +Purpose: graphs reduction +\end{center} + +CVITMAPPING module is intended for diagrams calculation according to +Cvitanovic - Kennedy algorithm. The top function of this module +CALC\_SPUR is called from RED\_TO\_CVIT\_INTERFACE interface module. +The main idea of the algorithm consists in diagram simplification +according to rules (1.9') and (1.14) from [1]. The input data - trace +of Diracs gamma matrices (G-matrices) has a form of a list of +identifiers lists with cyclic order. Some of identifiers may be +identical. In this case we assume summation over dummy indices. So +trace Sp(GbGr).Sp(GwGbGcGwGcGr) is represented as list ((b r) (w b c w +c r)). + +The first step is to transform the input data to ``map'' structure and +then to reduce the map to a ``simple'' one. This transformation is made +by function TRANSFORM\_MAP\_ (top function). Transformation is made in +three steps. At the first step the input data are transformed to the +internal form - a map (by function PREPARE\_MAP\_). At the second step +a map is subjected to Fierz transformations (1.14) (function +MK\_SIMPLE\_MAP\_). At this step of optimization can be maid (if +switch CVITOP is on) by function MK\_FIRZ\_OP. In this case Fierzing +starts with linked vertices with minimal distance (number of vertices) +between them. After Fierz transformations map is further reduced by +vertex simplification routine MK\_SIMPLE\_VERTEX using (1.9'). +Vertices reduced to primitive ones, that is to vertices with three or +less edges. This is the last (third) step in transformation from +input to internal data. + +The next step is optional. If switch CVITBTR is on factorisation of +bubble (function FIND\_BUBBLES1) and triangle (function +FIND\_TRIANGLES1) submaps is made. This factorisation is very +efficient for ``wheel'' diagrams and unnecessary for ``lattice'' diagrams. +Factorisation is made recursively by substituting composed edges for +bubbles and composed vertices for triangles. So check (function +SORT\_ATLAS) must be done to test possibility of future marking +procedure. If the check fails then a new attempt to reorganize atlas +(so we call complicated structure witch consists of MAP, COEFFicient +and DENOMinator) is made. This cause backtracking (but very seldom). +Backtracking can be traced by turning on switch CVITRACE. FIND\_BUBLTR +is the top function of this program's branch. + +Then atlases must be prepared (top function WORLD\_FROM\_ATLAS) for +final algebraic calculations. The resulted object called ``world'' +consists of edges names list (EDGELIST), their marking variants +(VARIANTS) and WORLD1 structure. WORLD1 structure differs from WORLD +structure in one point. It contains MAP2 structure instead of MAP +structure. MAP2 is very complicated structure and consist of VARIANTS, +marking plan and GSTRAND. (GSTRAND constructed by PRE!-CALC!-MAP\_ +from INTERFIERZ module.) By marking we understand marking of edges +with numbers according to Cvitanovic - Kennedy algorithm. + +The last step is performed by function CALC\_WORLD. At this step +algebraic calculations are done. Two functions CALC\_MAP\_TAR and +CALC\_DENTAR from INTERFIERZ module make algebraic expressions in the +prefix form. This expressions are further simplified by function +{\tt REVAL}. This is the REDUCE system general function for algebraic +expressions simplification. {\tt REVAL} and {\tt SIMP!*} are the only REDUCE +functions used in this module. + +There are also some functions for printing several internal +structures: PRINT\_ATLAS, PRINT\_VERTEX, PRINT\_EDGE, PRINT\_COEFF, +PRINT\_DENOM. This functions can be used for debugging. + +If an error occur in module CVITMAPPING the error message ``ERROR IN +MAP CREATING ROUTINES'' is displayed. Error has number 55. The switch +CVITERROR allows to give full information about error: name of +function where error occurs and names and values of function's +arguments. If CVITERROR switch is on and backtracking fails message +about error in SORT\_ATLAS function is printed. The result of +computation however will be correct because in this case factorized +structure is not used. This happens extremely seldom. + + +\begin{verbatim} + List of imported function +------------------------------------------------- + function from module +------------------------------------------------- + REVAL REDUCE + SIMP!* REDUCE + CALC_MAP_TAR INTERFIERZ + CALC_DENTAR INTERFIERZ + PRE!-CALC!-MAP_ INTERFIERZ + GAMMA5P RED_TO_CVIT_INTERFACE +------------------------------------------------- +\end{verbatim} + +\begin{verbatim} + List of exported function +------------------------------------------------- + function to module +------------------------------------------------- + CALC_SPUR REDUCE - CVIT interface +------------------------------------------------- +\end{verbatim} + +\begin{verbatim} + Data structure + WORLD ::= (EDGELIST,VARIANTS,WORLD1) + WORLD1 ::= (MAP2,COEFF,DENOM) + MAP2 ::= (MAPS,VARIANTS,PLAN) + MAPS ::= (EDGEPAIR . GSTRAND) + MAP1 ::= (EDGEPAIR . MAP) + MAP ::= list of VERTICES (unordered) + EDGEPAIR ::= (OLDEDGELIST . NEWEDGELIST) + COEFF ::= list of WORLDS (unordered) + ATLAS ::= (MAP,COEFF,DENOM) + GSTRAND ::= (STRAND*,MAP,TADPOLES,DELTAS) + VERTEX ::= list of EDGEs (with cyclic order) + EDGE ::= (NAME,PROPERTY,TYPE) + NAME ::= ATOM + PROPERTY ::= (FIRSTPAIR . SECONDPAIR) + TYPE ::= T or NIL + ------------------------------------------------ + *Define in module MAP!-TO!-STRAND. + +\end{verbatim} + +\section*{Modules INTERFIERZ, EVAL\_MAPS, AND MAP-TO-STRAND.} + +\begin{center} +Author: A.Taranov \\ +Purpose: evaluate single Map +\end{center} + +Module INTERFIERZ exports to module CVITMAPPING three functions: +PRE-CALC-MAP\_, CALC-MAP\_TAR, CALC-DENTAR. + +Function PRE-CALC-MAP\_ is used for preliminary processing of a map. It +returns a list of the form (STRAND NEWMAP TADEPOLES DELTAS) where +STRAND is strand structure described in MAP-TO-STRAND module. NEWMAP +is a map structure without ``tadepoles'' and ``deltas''. ``Tadepole'' is a +loop connected with map with only one line (edge). ``Delta'' is a single +line disconnected from a map. TADEPOLES is a list of ``tadepole'' +submaps. DELTAS is a list (CONS E1 E2) where E1 and E2 are + +Function CALC\_MAP\_TAR takes a list of the same form as returned by +PRE-CALC-MAP\_, a-list, of the form (... edge . weight ... ) and +returns a prefix form of algebraic expression corresponding to the map +numerator. + +Function CALC-DENTAR returns a prefix form of algebraic expression +corresponding to the map denominator. + +Module EVAL-MAP exports to module INTERFIERZ functions MK-NUMR and +STRAND-ALG-TOP. + +Function MK-NUMR returns a prefix form for some combinatorial +coefficient (Pohgammer symbol). + +Function STRAND-ALG-TOP performs an actual computation of a prefix +form of algebraic expression corresponding to the map numerator. This +computation is based on a ``strand'' structure constructed from the +``map'' structure. + +Module MAP-TO-STRAND exports functions MAP-TO-STRAND, INCIDENT1 to +module INTERFIERZ and functions DELETEZ1, CONTRACT-STRAND, +COLOR-STRAND to module EVAL-MAPS. + +Function INCIDENT1 is a selector in ``strand'' structure. DELETEZ1 +performs auxiliary optimization of ``strand''. MAP-TO-STRAND transforms +``map'' to ``strand'' structure. The latter is describe in program +module. + +CONTRACT-STRAND do strand vertex simplifications of ``strand'' and +COLOR-STRAND finishes strand generation. + +\begin{verbatim} + + Description of STRAND data structure. + STRAND ::= + VERTEX ::= . ( ) + ROAD ::= . NUMBER + NAME ::=NUMBER +\end{verbatim} + + +\subsection*{ LIST OF MESSAGES} + +\begin{itemize} + +\item{CALC\_SPUR: $<$vecdim$>$ IS NOT EVEN SPACE-TIME DIMENSION} + The dimension of space-time $<$vecdim$ $is integer but not +even. Only even numeric dimensions are allowed. + +\item{NOSPUR NOT YET IMPLEMENTED} + Attempt to calculate trace when NOSPUR switch is on. This facility +is not implemented now. + +\item{G5 INVALID FOR VECDIM NEQ 4} + Attempt to calculate trace with gamma5-matrix for space-time +dimension not equal to 4. + +\item{CALC\_SPUR: $<$expr$>$ HAS NON-UNIT DENOMINATOR} +The has non-unit denominator. + +\item{THREE INDICES HAVE NAME $<$name$>$} + There are three indices with equal names in evaluated expression. + +\end{itemize} + +\begin{verbatim} + List of switches +------------------------------------------------------------ + switch default comment +------------------------------------------------------------ + CVIT ON If it is on then use Kennedy- + Cvitanovic algorithm else use + standard facilities. + CVITOP OFF Fierz optimization switch + CVITBTR ON Bubbles and triangles + factorisation switch + CVITRACE OFF Backtracking tracing switch +------------------------------------------------------------ +\end{verbatim} + + +\begin{verbatim} + Functions cross references*. + +CALC_SPUR + | + +-->SIMP!* (REDUCE) + | + +-->CALC_SPUR0 + | + |--->TRANSFORM_MAP_ + | | + | |--->MK_SIMPLE_VERTEX + | +--->MK_SIMPLE_MAP_ + | | + | +--->MK_SIMPLE_MAP_1 + | | + | +--->MK_FIERS_OP + | + |--->WORLD_FROM_ATLAS + | | + | +--->CONSTR_WORLDS + | | + | +---->MK_WORLD1 + | | + | +--->MAP_2_FROM_MAP_1 + | | + | |--->MARK_EDGES + | +--->MAP_1_TO_STRAND + | | + | +-->PRE!-CALC!-MAP_ + | (INTERFIRZ) + | + |--->CALC_WORLD + | | + | |--->CALC!-MAP_TAR (INTERFIRZ) + | |--->CALC!-DENTAR (INTERFIRZ) + | +--->REVAL (REDUCE) + | + +--->FIND_BUBLTR + | + +--->FIND_BUBLTR0 + | + |--->SORT_ATLAS + +--->FIND_BUBLTR1 + | + |--->FIND_BUBLES1 + +--->FIND_TRIANGLES1 +*Unmarked functions are from CVITMPPING module. + +\end{verbatim} + + +\section*{References} + +\begin{itemize} + +\item{1.} +Ilyin V.A., Kryukov A.P., Rodionov A.Ya., Taranov A.Yu. +Fast algorithm for calculation of Diracs gamma-matrices +traces. SIGSAM Bull., 1989, v.23, no.4, pp.15-24. + +\item{2.} +Kennedy A.D. Phys.Rev., 1982, D26, p.1936. +\end{itemize} + +\section*{Keywords} + +REDUCE, GAMMA-MATRIX, TRACE, SPACE-TIME DIMENSION, HIGH ENERGY PHYSICS. + +\end{document} Index: r36/doc/DEFINT.TEX ================================================================== --- r36/doc/DEFINT.TEX +++ r36/doc/DEFINT.TEX @@ -1,500 +1,500 @@ -\documentstyle[11pt,reduce]{article} -\date{July 1994} -\title{A Definite Integration Interface for REDUCE} -\author{Kerry Gaskell \\ -Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin\\ -Heilbronner Strasse 10 \\ -D--10711 Berlin -- Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -E--mail: neun@zib-berlin.de\footnotemark[1]} - -\begin{document} -\maketitle -\footnotetext[1]{This definite integration interface was written -during my one year placement at ZIB. Any comments and/or -problems should therefore be directed to Winfried Neun at -neun@sc.zib-berlin.de.} - -\section{Introduction} -This documentation describes part of \REDUCE's definite -integration package that is able to calculate the definite integrals of -many functions, including several special functions. There are other -parts of this package, such as Stan Kameny's code for contour integration, -that are not included here. The integration process described here is not -the more normal approach of initially calculating the indefinite integral, -but is instead the rather unusual idea of representing each function as a -Meijer G-function (a formal definition of the Meijer G-function can be -found in \cite {Prudnikov}), and then calculating the integral by using -the following Meijer G integration formula. - -\begin{displaymath} -\int_{0}^{\infty} x^{\alpha-1} G^{s t}_{u v} -\left( \sigma x \ \Bigg\vert \ {( c_u) \atop (d_v)} \right) -G^{m n}_{p q} \left( \omega x^{l/k} \ \Bigg\vert \ {(a_p) \atop (b_q)} -\right) dx = k G^{i j}_{k l} \left( \xi \ \Bigg\vert \ -{(g_k) \atop (h_l)} \right) \hspace{5mm} (1) -\end{displaymath} - -The resulting Meijer G-function is then retransformed, either directly -or via a hypergeometric function simplification, to give -the answer. A more detailed account of this theory can be found in -\cite {Adamchik:90}. - -\section{Integration between zero and infinity} - -As an example, if one wishes to calculate the following integral - -\begin{displaymath} -\int_{0}^{\infty} x^{-1} e^{-x} sin(x) \, dx -\end{displaymath} - -then initially the correct Meijer G-functions are found, via a -pattern matching -process, and are substituted into (1) to give - -\begin{displaymath} -\sqrt{\pi} \int_{0}^{\infty} x^{-1} G^{1 0}_{0 1} \left(x -\ \Bigg\vert \ -{. \atop 0}\right) G^{1 0}_{0 2}\left(\frac{x^{2}}{4} -\ \Bigg\vert \ {. \; . \atop \frac{1}{2} \; 0} \right) dx -\end{displaymath} - -The cases for validity of the integral are then checked. If these -are found to be satisfactory then the formula is calculated and we -obtain the following Meijer G-function - -\begin{displaymath} -G^{1 2}_{2 2} \left(1 \ \Bigg\vert \ {\frac{1}{2} \; 1 \atop -\frac{1}{2} \; 0} \right) -\end{displaymath} - -This is reduced to the following hypergeometric function - -\begin{math} -\hspace{50mm} _2F_1 (\frac{1}{2},1;\frac{3}{2};-1 ) -\end{math} - -which is then calculated to give the correct answer of - -\begin{displaymath} -\frac{\pi}{4} -\end{displaymath} - -The above formula (1) is also true for the integration of a single -Meijer G-function by replacing the second Meijer G-function -with a trivial Meijer G-function. - -A list of numerous particular Meijer G-functions is available in -\cite {Prudnikov}. - -\section{Integration over other ranges} - -Although the description so far has been limited to the computation of -definite integrals between 0 and infinity, it can also be extended to -calculate integrals between 0 and some specific upper bound, and -by further extension, integrals between any two bounds. One approach is -to use the Heaviside function, i.e. - -\begin{displaymath} -\int_{0}^{\infty} x^{2} e^{-x} H(1-x)\,dx = \int_{0}^{1} x^{2} e^{-x}dx -\end{displaymath} - -Another approach, again not involving the normal indefinite integration -process, again uses Meijer G-functions, this time by means of the -following formula - -\begin{displaymath} -\int_{0}^{y} x^{\alpha-1} G^{m n}_{p q} -\left( \sigma x \ \Bigg\vert \ {( a_u) \atop (b_v)} \right) dx=% -y^{\alpha}\,G^{m \; n+1}_{p+1 \; q+1} \left( \sigma y \ \Bigg\vert \ -{( a_1..a_n,1-\alpha,a_{n+1}..a_p) -\atop (b_1..b_m,-\alpha,b_{m+1}..b_q)} \right) (2) -\end{displaymath} - -For a more detailed look at the theory behind this see -\cite{Adamchik:90}. - -For example, if one wishes to calculate the following integral - -\begin{displaymath} -\int_{0}^{y} sin(2 \sqrt{x}) \, dx -\end{displaymath} - -then initially the correct Meijer G-function is found, by a pattern -matching process, and is substituted -into (2) to give - -\begin{displaymath} -\int_{0}^{y} G^{1 0}_{0 2}\left(x -\ \Bigg\vert \ {. \; . \atop \frac{1}{2} \; 0} \right) dx -\end{displaymath} - -which then in turn gives - -\begin{displaymath} -y \; G^{1 1}_{1 3}\left(y \ \Bigg\vert \ {0 \atop -\frac{1}{2} -\!1 \; 0} \right) dx -\end{displaymath} - -and returns the result - -\begin{displaymath} -\frac{\sqrt{\pi} \, J_{3/2}(2 \, \sqrt{\,y}) \, y}{y^{1/4}} -\end{displaymath} - -\section{Using the definite integration package} -To use this package, you must first load it by the command -\begin{verbatim} -load_package defint; -\end{verbatim} -Definite integration is then possible using the \verb+int+ -command with the syntax: -\begin{verbatim} - INT(EXPRN:algebraic,VAR:kernel,LOW:algebraic,UP:algebraic) - :algebraic. -\end{verbatim} -where LOW and UP are the lower and upper bounds respectively for -the definite integration of EXPRN with respect to VAR. - -\subsection{Examples} - -\begin{displaymath} -\int_{0}^{\infty} e^{-x} dx -\end{displaymath} - - -\begin{verbatim} - int(e^(-x),x,0,infinity); - - 1 -\end{verbatim} - -\begin{displaymath} -\int_{0}^{\infty} x sin(1/x) \, dx -\end{displaymath} - -\begin{verbatim} - int(x*sin(1/x),x,0,infinity); - - 1 -INT(X*SIN(---),X,0,INFINITY) - X -\end{verbatim} - -\begin{displaymath} -\int_{0}^{\infty} x^2 cos(x) \, e^{-2x} dx -\end{displaymath} - -\begin{verbatim} - int(x^2*cos(x)*e^(-2*x),x,0,infinity); - - 4 - ----- - 125 -\end{verbatim} - -\begin{displaymath} -\int_{0}^{\infty} x e^{-1/2x} H(1-x) \,dx = \int_{0}^{1} x e^{-1/2x} dx -\end{displaymath} - -\begin{verbatim} - int(x*e^(-1/2x)*Heaviside(1-x),x,0,infinity); - - 2*(2*SQRT(E) - 3) - ------------------- - SQRT(E) -\end{verbatim} - -\begin{displaymath} -\int_{0}^{1} x \,log(1+x) \,dx -\end{displaymath} - -\begin{verbatim} - int(x*log(1+x),x,0,1); - - 1 - --- - 4 -\end{verbatim} - -\begin{displaymath} -\int_{0}^{y} cos(2x) \,dx -\end{displaymath} - -\begin{verbatim} - int(cos(2x),x,y,2y); - - SIN(4*Y) - SIN(2*Y) ---------------------- - 2 -\end{verbatim} - - -\section{Integral Transforms} - -A useful application of the definite integration package is in the -calculation of various integral transforms. The transforms -available are as follows: - -\begin{itemize} -\item Laplace transform -\item Hankel transform -\item Y-transform -\item K-transform -\item StruveH transform -\item Fourier sine transform -\item Fourier cosine transform -\end{itemize} - -\subsection{Laplace transform} - -The Laplace transform - -$\hspace{20 mm} f(s) = \cal L$ \{F(t)\} = -$\int_{0}^{\infty} e^{-st}F(t)\,dt$ - -can be calculated by using the \verb+laplace_transform+ command. - -This requires as parameters - -\begin{itemize} -\item the function to be integrated -\item the integration variable. -\end{itemize} - -For example - -$\hspace{56 mm} \cal L$ $\{e^{-at}\} \\$ -is entered as - -\begin{verbatim} - laplace_transform(e^(-a*x),x); -\end{verbatim} - -and returns the result - -\begin{displaymath} -\frac{1}{s+a} -\end{displaymath} - -\subsection{Hankel transform} - -The Hankel transform - -\begin{displaymath} -f(\omega) = \int_{0}^{\infty} F(t) \,J_{\nu}(2\sqrt{\omega t}) \,dt -\end{displaymath} - -can be calculated by using the \verb+hankel_transform+ command e.g. - -\begin{verbatim} - hankel_transform(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\subsection{Y-transform} - -The Y-transform - -\begin{displaymath} -f(\omega) = \int_{0}^{\infty} F(t) \,Y_{\nu}(2\sqrt{\omega t}) \,dt -\end{displaymath} - -can be calculated by using the \verb+Y_transform+ command e.g. - -\begin{verbatim} - Y_transform(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\subsection{K-transform} - -The K-transform - -\begin{displaymath} -f(\omega) = \int_{0}^{\infty} F(t) \,K_{\nu}(2\sqrt{\omega t}) \,dt -\end{displaymath} - -can be calculated by using the \verb+K_transform+ command e.g. - -\begin{verbatim} - K_transform(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\subsection{StruveH transform} - -The StruveH transform - -\begin{displaymath} -f(\omega) = \int_{0}^{\infty} F(t) \,StruveH(\nu,2\sqrt{\omega t}) \,dt -\end{displaymath} - -can be calculated by using the \verb+struveh_transform+ command e.g. - -\begin{verbatim} - struveh_transform(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\subsection{Fourier sine transform} - -The Fourier sine transform - -\begin{displaymath} -f(s) = \int_{0}^{\infty} F(t) \,sin (st) \,dt -\end{displaymath} - -can be calculated by using the \verb+fourier_sin+ command e.g. -\begin{verbatim} - fourier_sin(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\subsection{Fourier cosine transform} - -The Fourier cosine transform - -\begin{displaymath} -f(s) = \int_{0}^{\infty} F(t) \,cos (st) \,dt -\end{displaymath} - -can be calculated by using the \verb+fourier_cos+ command e.g. -\begin{verbatim} - fourier_cos(f(x),x); -\end{verbatim} - -This is used in the same way as the \verb+laplace_transform+ command. - -\section{Additional Meijer G-function Definitions} - -The relevant Meijer G representation for any function is found by a -pattern-matching process which is carried out on a list of Meijer -G-function definitions. This list, although extensive, can never hope -to be complete and therefore the user may wish to add more definitions. -Definitions can be added by adding the following lines: - -\begin{verbatim} - defint_choose(f(~x),~var => f1(n,x); - - symbolic putv(mellin!-transforms!*,n,' - (() (m n p q) (ai) (bj) (C) (var))); - -\end{verbatim} - where f(x) is the new function, i = 1..p, j=1..q, C = a constant, -%where i = 1..p, j=1..q, C = a constant, - var = variable, n = an indexing number. - -For example when considering $cos (x)$ we have - -\it Meijer G representation - -\begin{displaymath} -\sqrt{\pi} \,G^{1 0}_{0 2}\left(\frac{x^{2}}{4} \ \Bigg\vert -\ { . \; . \atop 0 \; \frac{1}{2}} \right) dx -\end{displaymath} - -\it Internal definite integration package representation - -\begin{verbatim} - defint_choose(cos(~x),~var) => f1(3,x); -\end{verbatim} - -\rm where 3 is the indexing number corresponding to the 3 -in the following formula - -\begin{verbatim} - symbolic putv(mellin!-transforms!*,3,' - (() (1 0 0 2) () (nil (quotient 1 2)) - (sqrt pi) (quotient (expt x 2) 4))); -\end{verbatim} - -or the more interesting example of $J_{n}(x)$: - -\it Meijer G representation - -\begin{displaymath} -G^{1 0}_{0 2} \left(\frac{x^{2}}{4} \ \Bigg\vert -\ {. \; . \atop \frac{n}{2} \; {\frac{-n}{2}}} \right) dx -\end{displaymath} - -\it Internal definite integration package representation - - -\begin{verbatim} - defint_choose(besselj(~n,~x),~var) => f1(50,x,n); - - symbolic putv(mellin!-transforms!*,50,' - ((n) (1 0 0 2) () ((quotient n 2) - (minus quotient n 2)) 1 - (quotient (expt x 2) 4))); -\end{verbatim} - -\section{The print\_conditions function} - -\rm The required conditions for the validity of the transform integrals -can be viewed using the following command: - -\begin{verbatim} - print_conditions(). -\end{verbatim} - -For example after calculating the following laplace transform - -\begin{verbatim} - laplace_transform(x^k,x); -\end{verbatim} - -using the \verb+print_conditions+ command would produce - -\begin{verbatim} - -repart(sum(ai) - sum(bj)) + 1/2 (q + 1 - p)>(q - p) repart(s) - - and ( - min(repart(bj)) f1(n,x); + + symbolic putv(mellin!-transforms!*,n,' + (() (m n p q) (ai) (bj) (C) (var))); + +\end{verbatim} + where f(x) is the new function, i = 1..p, j=1..q, C = a constant, +%where i = 1..p, j=1..q, C = a constant, + var = variable, n = an indexing number. + +For example when considering $cos (x)$ we have + +\it Meijer G representation - +\begin{displaymath} +\sqrt{\pi} \,G^{1 0}_{0 2}\left(\frac{x^{2}}{4} \ \Bigg\vert +\ { . \; . \atop 0 \; \frac{1}{2}} \right) dx +\end{displaymath} + +\it Internal definite integration package representation - +\begin{verbatim} + defint_choose(cos(~x),~var) => f1(3,x); +\end{verbatim} + +\rm where 3 is the indexing number corresponding to the 3 +in the following formula + +\begin{verbatim} + symbolic putv(mellin!-transforms!*,3,' + (() (1 0 0 2) () (nil (quotient 1 2)) + (sqrt pi) (quotient (expt x 2) 4))); +\end{verbatim} + +or the more interesting example of $J_{n}(x)$: + +\it Meijer G representation - +\begin{displaymath} +G^{1 0}_{0 2} \left(\frac{x^{2}}{4} \ \Bigg\vert +\ {. \; . \atop \frac{n}{2} \; {\frac{-n}{2}}} \right) dx +\end{displaymath} + +\it Internal definite integration package representation - + +\begin{verbatim} + defint_choose(besselj(~n,~x),~var) => f1(50,x,n); + + symbolic putv(mellin!-transforms!*,50,' + ((n) (1 0 0 2) () ((quotient n 2) + (minus quotient n 2)) 1 + (quotient (expt x 2) 4))); +\end{verbatim} + +\section{The print\_conditions function} + +\rm The required conditions for the validity of the transform integrals +can be viewed using the following command: + +\begin{verbatim} + print_conditions(). +\end{verbatim} + +For example after calculating the following laplace transform + +\begin{verbatim} + laplace_transform(x^k,x); +\end{verbatim} + +using the \verb+print_conditions+ command would produce + +\begin{verbatim} + +repart(sum(ai) - sum(bj)) + 1/2 (q + 1 - p)>(q - p) repart(s) + + and ( - min(repart(bj))=ram*(r+v). - - Finally this procedure RETURNS the complete result of the carry over of the - solution in the equation. - - This procedure cannot be used if the solution number solk is linked to a - condition. - - - -3) writing of different forms of results - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - - procedure standsol(solutions); - ============================== - - This procedure enables the simplified form of each solution to be obtained - from the list "solutions", {lcoeff,{...,{general_solution},....}} which is - one of the elements of the list returned by DESIR, or {lcoeff,sol} where - sol is the list returned by DELIRE. - - This procedure RETURNS a list of 3 elements : { lcoeff, solstand, solcond } - * lcoef = list of differential equation coefficients - * solstand = list of solutions written in standard form - * solcond = list of conditional solutions that have not been written in - standard form. This solutions remain in general form. - - This procedure has no meaning for "conditional" solutions. In case, a value - has to be given to the parameters, that can be done either by calling the - procedure SORPARAM that displays and returns these solutions in the - standard form, either by calling the procedure SOLPARAM which returns - these solutions in general form. - - procedure sorsol(sol); - ====================== - - This procedure is called by DESIR to write the solution sol, given in - general form, in standard form with enumeration of different conditions (if - there are any). - It can be used independently. - - - -4) Writing of solutions after the choice of parameters - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - - procedure sorparam(solutions,param); - ==================================== - - This is an interactive procedure which displays the solutions evaluated : - the value of parameters is requested. - * solutions : {lcoeff,{....,{general_solution},....}} - * param : list of parameters. - - It returns the list formed of 2 elements : - * list of evaluated coefficients of the equation - * list of standard solutions evaluated for the value of parameters. - - procedure solparam(solutions,param,valparam); - ============================================= - - This procedure evaluates the general solutions for the value of parameters - given by valparam and returns these solutions in general form. - * solutions : {lcoeff,{....,{general_solution},....}} - * param : list of parameters - * valparam : list of parameters values - - It returns the list formed of 2 elements : - * list of evaluated coefficients of the equation - * list of solutions in general form, evaluated for the value of - parameters. - - - -5) Transformations - ~~~~~~~~~~~~~~~ - - procedure changehom(lcoeff,x,secmember,id); - =========================================== - - Differentiation of an equation with right-hand side. - * lcoeff : list of coefficients of the equation - * x : variable - * secmember : right-hand side - * id : order of the differentiation. - - - It returns the list of coefficients of the differentiated equation. - It enables an equation with polynomial right-hand side to be transformed - into a homogeneous equation by differentiating id times, - id = degre(secmember) + 1. - - procedure changevar(lcoeff,x,v,fct); - ==================================== - - Changing of variable in the homogeneous equation defined by the list,lcoeff - of its coefficients : the old variable x and the new variable v are linked - by the relation x = fct(v). - - It returns the list of coefficients in respect to the variable v of the new - equation. - - examples of use : - --------------- - - translation enabling a rational singularity to be brought back to zero. - - x = 1/v brings the infinity to 0. - - procedure changefonc(lcoeff,x,q,fct); - ===================================== - - Changing of unknown function in the homogeneous equation defined by the - list lcoeff of its coefficients : - * lcoeff : list of coefficients of the initial equation - * x : variable - * q : new unknown function - * fct : y being the unknown function y = fct(q) - - It returns the list of coefficients of the new equation. - - example of use : - -------------- - this procedure enables the computation,in the neighbourhood of an irregular - singularity, of the "reduced" equation associated to one of the slopes (the - Newton polygon having a null slope of no null length). This equation gives - much informations on the associated divergent series. - - - -6) Optional writing of intermediary results - ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - - switch trdesir : when it is ON, at each step of the Newton algorithm, a - ======= - description of the Newton polygon is displayed (it is possible to follow - the break of slopes), and at each call of the FROBENIUS procedure ( case of - a null slope ) the corresponding indicial equation is displayed. - - By default, this switch is OFF. - - -6) LIMITATIONS - *********** - - -1) This DESIR version is limited to differential equations leading - to indicial equations of degree <= 3. To pass beyond this limit, a further - version written in the D5 environment of the computation with algebraic - numbers has to be used. - - -2) The computation of a basis of solutions for an equation depending on - parameters is assured only when the indicial equations are of degree <= 2. - - -7) IMPLEMENTATION - ************** - - This software uses the 3.3 version of REDUCE. - + + *************************************************************** + * * + * DESIR * + * ===== * + * * + * SOLUTIONS FORMELLES D'EQUATIONS DIFFERENTIELLES * + * * + * LINEAIRES ET HOMOGENES * + * * + * AU VOISINAGE DE POINTS SINGULIERS REGULIERS ET IRREGULIERS * + * * + *************************************************************** + + Differential linear homogenous Equation Solutions in the + neighbourhood of Irregular and Regular singular points + + Version 3.1 - Septembre 89 + + + Groupe de Calcul Formel de Grenoble + laboratoire TIM3 + + (C. Dicrescenzo, F. Richard-Jung, E. Tournier) + + E-mail: dicresc@afp.imag.fr + + +1) Introduction +2) Form of solutions +3) Interactive use +4) Direct use +5) Useful functions +6) Limitations +7) Implementation + + + +1) INTRODUCTION + ************ + + This software enables the basis of formal solutions to be computed for an + ordinary homogeneous differential equation with polynomial coefficients + over Q of any order, in the neighbourhood of zero ( regular or irregular + singular point, or ordinary point ). + Tools have been added to deal with equations with a polynomial right-hand + side, parameters and a singular point not to be found at zero. + + This software can be used in two ways : * direct ( DELIRE procedure ) + * interactive ( DESIR procedure) + + The basic procedure is the DELIRE procedure which enables the solutions of + a linear homogeneous differential equation to be computed in the neigh- + bourhood of zero. + + The DESIR procedure is a procedure without argument whereby DELIRE can be + called without preliminary treatment to the data, that is to say, in an + interactive autonomous way. This procedure also proposes some transfor- + mations on the initial equation. This allows one to start comfortably + with an equation which has a non zero singular point, a polynomial + right-hand side and parameters. + + This document is a succint user manual. For more details on the underlying + mathematics and the algorithms used, the reader can refer to : + + E. Tournier : Solutions formelles d'equations differentielles - Le + logiciel de calcul formel DESIR. + These d'Etat de l'Universite Joseph Fourier (Grenoble - avril 87). + + He will find more precision on use of parameters in : + + F. Richard-Jung : Representation graphique de solutions d'equations + differentielles dans le champ complexe. + These de l'Universite Louis Pasteur (Strasbourg - septembre 88). + + + +2) FORMS OF SOLUTIONS + ****************** + + We have tried to represent solutions in the simplest form possible. For + that, we have had to choose different forms according to the complexity + of the equation (parameters) and the later use we shall have of these + solutions. + + "general solution" = {......, { split_sol , cond },....} + ------------------ + + cond = list of conditions or empty list (if there is no condition) + that parameters have to verify such that split_sol is in the + basis of solutions. In fact, if there are parameters, basis of + solutions can have different expressions according to the values + of parameters. ( Note : if cond={}, the list "general solution" + has one element only. + + split_sol = { q , ram , polysol , r } + ( " split solution " enables precise information on the solution + to be obtained immediately ) + + The variable in the differential operator being x, solutions are expressed in + respect to a new variable xt, which is a fractional power of x, in the + following way : + + q : polynomial in 1/xt with complex coefficients + ram : xt = x**ram (1/ram is an integer) + polysol : polynomial in log(xt) with formal series in xt coefficients + r : root of a complex coefficient polynomial ("indicial + equation"). + + + qx r*ram + "standard solution" = e x polysolx + ----------------- + qx and polysolx are q and polysol expressions in which xt has been + replaced by x**ram + + N.B. : the form of these solutions is simplified according to the nature of + the point zero. + - si 0 is a regular singular point : the series appearing in polysol are + convergent, ram = 1 and q = 0. + - if 0 is a regular point, we also have : polysol is constant in log(xt) + (no logarithmic terms). + + + + +3) INTERACTIVE USE + *************** + + To call the procedure : desir(); + solution:=desir(); + + The DESIR procedure computes formal solutions of a linear homogeneous + differential equation in an interactive way. + In this equation the variable must be x. + --------- + The procedure requires the order and the coefficients of the equation, the + names of parameters if there are any, then if the user wants to transform + this equation and how ( for example to bring back a singular point to zero + - see procedures changehom, changevar, changefonc - ). + + This procedure DISPLAYS the solutions and RETURNS a list of general term + { lcoeff, {....,{ general_solution },....}}. The number of elements in + this list is linked to the number of transformations requested : + * lcoeff : list of coefficients of the differential equation + * general_solution : solution written in the general form + + + + +4) DIRECT USE + ********** + + procedure delire(x,k,grille,lcoeff,param); + ========================================== + + This procedure computes formal solutions of a linear homogeneous differen- + tial equation with polynomial coefficients over Q and of any order, in the + neighborhood of zero, regular or irregular singular point. In fact it + initializes the call of the NEWTON procedure that is a recursive procedure + (algorithm of NEWTON-RAMIS-MALGRANGE) + + x : variable + k : "number of desired terms". + For each formal series in xt appearing in polysol, + a_0+a_1 xt+a_2 xt**2+...+a_n xt**n+..., we compute the k+1 first + coefficients a_0, a_1,...a_k. + grille : the coefficients of the differential operator are polynomial in + x**grille (in general grille=1) + lcoeff : list of coefficients of the differential operator (in increasing + order of differentiation) + param : list of parameters + + This procedure RETURNS the list of general solutions. + ---- + + + +5) USEFUL FUNCTIONS + ***************** + + -1) Reading of equation coefficients + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + + procedure lectabcoef( ) ; + ========================; + + This procedure is called by DESIR to read the coefficients of an equation, + in increasing order of differentiation, but can be used independently. + ----------------------------------- + reading of n : order of the equation. + reading of parameters (only if a variable other than x appears in the + coefficients) + this procedure returns the list { lcoeff , param } made up of the list of + coefficients and the list of parameters (which can be empty). + + -2) verification of results + ~~~~~~~~~~~~~~~~~~~~~~~ + + procedure solvalide(solutions,solk,k); + =====================================; + + This procedure enables the validity of the solution number solk in the list + "solutions" to be verify. + solutions = {lcoeff,{....,{general_solution},....}} is any element of the + list returned by DESIR or is {lcoeff,sol} where sol is the list returned by + DELIRE. + qx r*ram + If we carry over the solution e x polysolx in the equation, the + qx r*ram + result has the form e x reste, where reste is a polynomial in + log(xt), with polynomial coefficients in xt. This procedure computes the + minimal valuation V of reste as polynomial in xt, using k "number of + desired terms" asked for at the call of DESIR or DELIRE, and DISPLAYS the + ram*(r+v) + "theoretical" size order of the regular part of the result : x . + On the other hand, this procedure carries over the solution in the equation + and DISPLAYS the significative term of the result. This is of the form : + qx a + e x polynomial(log(xt)), with a>=ram*(r+v). + + Finally this procedure RETURNS the complete result of the carry over of the + solution in the equation. + + This procedure cannot be used if the solution number solk is linked to a + condition. + + + -3) writing of different forms of results + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + + procedure standsol(solutions); + ============================== + + This procedure enables the simplified form of each solution to be obtained + from the list "solutions", {lcoeff,{...,{general_solution},....}} which is + one of the elements of the list returned by DESIR, or {lcoeff,sol} where + sol is the list returned by DELIRE. + + This procedure RETURNS a list of 3 elements : { lcoeff, solstand, solcond } + * lcoef = list of differential equation coefficients + * solstand = list of solutions written in standard form + * solcond = list of conditional solutions that have not been written in + standard form. This solutions remain in general form. + + This procedure has no meaning for "conditional" solutions. In case, a value + has to be given to the parameters, that can be done either by calling the + procedure SORPARAM that displays and returns these solutions in the + standard form, either by calling the procedure SOLPARAM which returns + these solutions in general form. + + procedure sorsol(sol); + ====================== + + This procedure is called by DESIR to write the solution sol, given in + general form, in standard form with enumeration of different conditions (if + there are any). + It can be used independently. + + + -4) Writing of solutions after the choice of parameters + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + + procedure sorparam(solutions,param); + ==================================== + + This is an interactive procedure which displays the solutions evaluated : + the value of parameters is requested. + * solutions : {lcoeff,{....,{general_solution},....}} + * param : list of parameters. + + It returns the list formed of 2 elements : + * list of evaluated coefficients of the equation + * list of standard solutions evaluated for the value of parameters. + + procedure solparam(solutions,param,valparam); + ============================================= + + This procedure evaluates the general solutions for the value of parameters + given by valparam and returns these solutions in general form. + * solutions : {lcoeff,{....,{general_solution},....}} + * param : list of parameters + * valparam : list of parameters values + + It returns the list formed of 2 elements : + * list of evaluated coefficients of the equation + * list of solutions in general form, evaluated for the value of + parameters. + + + -5) Transformations + ~~~~~~~~~~~~~~~ + + procedure changehom(lcoeff,x,secmember,id); + =========================================== + + Differentiation of an equation with right-hand side. + * lcoeff : list of coefficients of the equation + * x : variable + * secmember : right-hand side + * id : order of the differentiation. + + + It returns the list of coefficients of the differentiated equation. + It enables an equation with polynomial right-hand side to be transformed + into a homogeneous equation by differentiating id times, + id = degre(secmember) + 1. + + procedure changevar(lcoeff,x,v,fct); + ==================================== + + Changing of variable in the homogeneous equation defined by the list,lcoeff + of its coefficients : the old variable x and the new variable v are linked + by the relation x = fct(v). + + It returns the list of coefficients in respect to the variable v of the new + equation. + + examples of use : + --------------- + - translation enabling a rational singularity to be brought back to zero. + - x = 1/v brings the infinity to 0. + + procedure changefonc(lcoeff,x,q,fct); + ===================================== + + Changing of unknown function in the homogeneous equation defined by the + list lcoeff of its coefficients : + * lcoeff : list of coefficients of the initial equation + * x : variable + * q : new unknown function + * fct : y being the unknown function y = fct(q) + + It returns the list of coefficients of the new equation. + + example of use : + -------------- + this procedure enables the computation,in the neighbourhood of an irregular + singularity, of the "reduced" equation associated to one of the slopes (the + Newton polygon having a null slope of no null length). This equation gives + much informations on the associated divergent series. + + + -6) Optional writing of intermediary results + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + + switch trdesir : when it is ON, at each step of the Newton algorithm, a + ======= + description of the Newton polygon is displayed (it is possible to follow + the break of slopes), and at each call of the FROBENIUS procedure ( case of + a null slope ) the corresponding indicial equation is displayed. + + By default, this switch is OFF. + + +6) LIMITATIONS + *********** + + -1) This DESIR version is limited to differential equations leading + to indicial equations of degree <= 3. To pass beyond this limit, a further + version written in the D5 environment of the computation with algebraic + numbers has to be used. + + -2) The computation of a basis of solutions for an equation depending on + parameters is assured only when the indicial equations are of degree <= 2. + + +7) IMPLEMENTATION + ************** + + This software uses the 3.3 version of REDUCE. + Index: r36/doc/DFPART.TEX ================================================================== --- r36/doc/DFPART.TEX +++ r36/doc/DFPART.TEX @@ -1,263 +1,263 @@ -\documentstyle[11pt,reduce]{article} -\title{DFPART: A Package for Calculating with Derivatives of -Generic Functions} -\date{} -\author{ -H. Melenk \\[0.05in] -Konrad--Zuse--Zentrum \\ -f\"ur Informationstechnik Berlin \\ -Heilbronner Strasse 10 \\ -D--10711 Berlin Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -Email: melenk@sc.zib--berlin.de} - -\begin{document} -\maketitle - -\index{derivatives} -\index{partial derivatives} -\index{generic function} - -The package {\tt DFPART} supports computations with total and partial -derivatives of formal function objects. Such computations can -be useful in the context of differential equations or -power series expansions. - -\section{Generic Functions} - -A generic function is a symbol which represents a mathematical -function. The minimal information about a generic function -function is the number of its arguments. In order to facilitate -the programming and for a better readable output this package -assumes that the arguments of a generic function have default -names such as $f(x,y)$,$q(rho,phi)$. -A generic function is declared by prototype form in a statement - -\vspace{.1in} - {\tt GENERIC\_FUNCTION} $fname(arg_1,arg_2\cdots arg_n)$; -\vspace{.1in} - -\noindent -where $fname$ is the (new) name of a function and $arg_i$ are -symbols for its formal arguments. -In the following $fname$ is referred to as ``generic function", -$arg_1,arg_2\cdots arg_n$ as ``generic arguments" and -$fname(arg_1,arg_2\cdots arg_n)$ as ``generic form". -Examples: - -\begin{verbatim} - generic_function f(x,y); - generic_function g(z); -\end{verbatim} - - -After this declaration {\REDUCE} knows that -\begin{itemize} -\item there are formal partial derivatives $\frac{\partial f}{\partial x}$, -$\frac{\partial f}{\partial y}$ $\frac{\partial g}{\partial z}$ -and higher ones, while partial derivatives of $f$ and $g$ -with respect to other variables are assumed as zero, -\item expressions of the type $f()$, $g()$ are abbreviations for -$f(x,y)$, $g(z)$, -\item expressions of the type $f(u,v)$ are abbreviations for\\ -$sub(x=u,y=v,f(x,y))$ -\item a total derivative $\frac{d f(u,v)}{d w}$ has to be computed -as $\frac{\partial f}{\partial x} \frac{d u}{d w} + - \frac{\partial f}{\partial y} \frac{d v}{d w}$ -\end{itemize} - -\section{Partial Derivatives} - -The operator {\tt DFP} represents a partial derivative: - -\vspace{.1in} - {\tt DFP}($expr,{dfarg_1,dfarg_2\cdots dfarg_n}$); -\vspace{.1in} - -\noindent -where $expr$ is a function expression and $dfarg_i$ are -the differentiation variables. Examples: - -\begin{verbatim} - dfp(f(),{x,y}); -\end{verbatim} -means $\frac{\partial ^2 f}{\partial x \partial y}$ and -\begin{verbatim} - dfp(f(u,v),{x,y}); -\end{verbatim} -stands for $\frac{\partial ^2 f}{\partial x \partial y} (u,v)$. -For compatibility with the $DF$ operator the differentiation -variables need not be entered in list form; instead the syntax -of {\tt DF} can be used, where the function expression is followed -by the differentiation variables, eventually with repetition -numbers. Such forms are interenally converted to the above -form with a list as second parameter. - -The expression $expr$ can be a generic function -with or without arguments, or an arithmetic expression built -from generic functions and other algebraic parts. In the -second case the standard differentiation rules are applied -in order to reduce each derivative expressions to a minimal -form. - -When the switch {\tt NAT} is on partial derivatives of generic -functions are printed in standard index notation, that is -$f_{xy}$ for $\frac{\partial ^2 f}{\partial x \partial y}$ -and $f_{xy}(u,v)$ for $\frac{\partial ^2 f}{\partial x \partial y}(u,v)$. -Therefore single characters should be used for the arguments -whenever possible. Examples: - -\begin{verbatim} - - generic_function f(x,y); - generic_function g(y); - dfp(f(),x,2); - - F - XX - - dfp(f()*g(),x,2); - - F *G() - XX - - dfp(f()*g(),x,y); - - F *G() + F *G - XY X Y - -\end{verbatim} - -The difference between partial and total derivatives is -illustrated by the following example: - -\begin{verbatim} - generic_function h(x); - dfp(f(x,h(x))*g(h(x)),x); - - F (X,H(X))*G(H(X)) - X - - df(f(x,h(x))*g(h(x)),x); - - F (X,H(X))*G(H(X)) + F (X,H(X))*H (X)*G(H(X)) - X Y X - - + G (H(X))*H (X)*F(X,H(X)) - Y X -\end{verbatim} - -Cooperation of partial derivatives and Taylor series under -a differential side relation $\frac{dq}{dx}=f(x,q)$: - -\begin{verbatim} - load_package taylor; - operator q; - let df(q(~x),x) => f(x,q(x)); - taylor(q(x0+h),h,0,3); - - F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) - X Y 2 -Q(X0) + F(X0,Q(X0))*H + -----------------------------------------*H - 2 - -+ (F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) - XX XY - - + F (X0,Q(X0))*F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) - X Y YX - - 2 2 3 - + F (X0,Q(X0))*F(X0,Q(X0)) + F (X0,Q(X0)) *F(X0,Q(X0)))/6*H - YY Y - - 4 - + O(H ) - -\end{verbatim} - -Normally partial differentials are assumed as non-commutative - -\begin{verbatim} - dfp(f(),x,y)-dfp(f(),y,x); - - F - F - XY YX -\end{verbatim} - -However, a generic function can be declared to have globally -interchangeable partial derivatives using the declaration -{\tt DFP\_COMMUTE} -which takes the name of a generic function or a generic function -form as argument. For such a function differentiation variables are -rearranged corresponding to the sequence of the generic variables. - -\begin{verbatim} - generic_function q(x,y); - dfp_commute q(x,y); - dfp(q(),{x,y,y}) + dfp(q(),{y,x,y}) + dfp(q(),{y,y,x}); - - 3*Q - XYY -\end{verbatim} - -If only a part of the derivatives commute, this has to be -declared using the standard {\REDUCE} rule mechanism. Please -note that then the derivative variables must be written as -list. - -\section{Substitutions} - -When a generic form or a {\tt DFP} expression takes part in a -substitution the following steps are performed: -\begin{enumerate} -\item The substitutions are performed for the arguments. If the -argument list is empty the substitution is applied to the -generic arguments of the function; if these change, the resulting -forms are used as new actual arguments. -If the generic function itself is not affected by the substitution, -the process stops here. -\item If the function name or the generic function -form occurs as a left hand side in the substitution list, -it is replaced by the corresponding right hand side. -\item The new form is partially differentiated according to the -list of partial derivative variables. -\item The (eventually modified) actual parameters are substituted -into the form for their corresponding generic variables. -This substitution is done by name. -\end{enumerate} - -Examples: -\begin{verbatim} - generic_function f(x,y); - sub(y=10,f()); - - F(X,10) - - sub(y=10,dfp(f(),x,2)); - - - F (X,10) - XX - - sub(y=10,dfp(f(y,y),x,2)); - - F (10,10) - XX - - sub(f=x**3*y**3,dfp(f(),x,2)); - - 3 - 6*X*Y - - generic_function ff(y,z); - sub(f=ff,f(a,b)); - - FF(B,Z) -\end{verbatim} - -The dataset $dfpart.tst$ contains more examples, -including a complete application for computing the coefficient -equations for Runge-Kutta ODE solvers. - -\end{document} +\documentstyle[11pt,reduce]{article} +\title{DFPART: A Package for Calculating with Derivatives of +Generic Functions} +\date{} +\author{ +H. Melenk \\[0.05in] +Konrad--Zuse--Zentrum \\ +f\"ur Informationstechnik Berlin \\ +Heilbronner Strasse 10 \\ +D--10711 Berlin Wilmersdorf \\ +Federal Republic of Germany \\[0.05in] +Email: melenk@sc.zib--berlin.de} + +\begin{document} +\maketitle + +\index{derivatives} +\index{partial derivatives} +\index{generic function} + +The package {\tt DFPART} supports computations with total and partial +derivatives of formal function objects. Such computations can +be useful in the context of differential equations or +power series expansions. + +\section{Generic Functions} + +A generic function is a symbol which represents a mathematical +function. The minimal information about a generic function +function is the number of its arguments. In order to facilitate +the programming and for a better readable output this package +assumes that the arguments of a generic function have default +names such as $f(x,y)$,$q(rho,phi)$. +A generic function is declared by prototype form in a statement + +\vspace{.1in} + {\tt GENERIC\_FUNCTION} $fname(arg_1,arg_2\cdots arg_n)$; +\vspace{.1in} + +\noindent +where $fname$ is the (new) name of a function and $arg_i$ are +symbols for its formal arguments. +In the following $fname$ is referred to as ``generic function", +$arg_1,arg_2\cdots arg_n$ as ``generic arguments" and +$fname(arg_1,arg_2\cdots arg_n)$ as ``generic form". +Examples: + +\begin{verbatim} + generic_function f(x,y); + generic_function g(z); +\end{verbatim} + + +After this declaration {\REDUCE} knows that +\begin{itemize} +\item there are formal partial derivatives $\frac{\partial f}{\partial x}$, +$\frac{\partial f}{\partial y}$ $\frac{\partial g}{\partial z}$ +and higher ones, while partial derivatives of $f$ and $g$ +with respect to other variables are assumed as zero, +\item expressions of the type $f()$, $g()$ are abbreviations for +$f(x,y)$, $g(z)$, +\item expressions of the type $f(u,v)$ are abbreviations for\\ +$sub(x=u,y=v,f(x,y))$ +\item a total derivative $\frac{d f(u,v)}{d w}$ has to be computed +as $\frac{\partial f}{\partial x} \frac{d u}{d w} + + \frac{\partial f}{\partial y} \frac{d v}{d w}$ +\end{itemize} + +\section{Partial Derivatives} + +The operator {\tt DFP} represents a partial derivative: + +\vspace{.1in} + {\tt DFP}($expr,{dfarg_1,dfarg_2\cdots dfarg_n}$); +\vspace{.1in} + +\noindent +where $expr$ is a function expression and $dfarg_i$ are +the differentiation variables. Examples: + +\begin{verbatim} + dfp(f(),{x,y}); +\end{verbatim} +means $\frac{\partial ^2 f}{\partial x \partial y}$ and +\begin{verbatim} + dfp(f(u,v),{x,y}); +\end{verbatim} +stands for $\frac{\partial ^2 f}{\partial x \partial y} (u,v)$. +For compatibility with the $DF$ operator the differentiation +variables need not be entered in list form; instead the syntax +of {\tt DF} can be used, where the function expression is followed +by the differentiation variables, eventually with repetition +numbers. Such forms are interenally converted to the above +form with a list as second parameter. + +The expression $expr$ can be a generic function +with or without arguments, or an arithmetic expression built +from generic functions and other algebraic parts. In the +second case the standard differentiation rules are applied +in order to reduce each derivative expressions to a minimal +form. + +When the switch {\tt NAT} is on partial derivatives of generic +functions are printed in standard index notation, that is +$f_{xy}$ for $\frac{\partial ^2 f}{\partial x \partial y}$ +and $f_{xy}(u,v)$ for $\frac{\partial ^2 f}{\partial x \partial y}(u,v)$. +Therefore single characters should be used for the arguments +whenever possible. Examples: + +\begin{verbatim} + + generic_function f(x,y); + generic_function g(y); + dfp(f(),x,2); + + F + XX + + dfp(f()*g(),x,2); + + F *G() + XX + + dfp(f()*g(),x,y); + + F *G() + F *G + XY X Y + +\end{verbatim} + +The difference between partial and total derivatives is +illustrated by the following example: + +\begin{verbatim} + generic_function h(x); + dfp(f(x,h(x))*g(h(x)),x); + + F (X,H(X))*G(H(X)) + X + + df(f(x,h(x))*g(h(x)),x); + + F (X,H(X))*G(H(X)) + F (X,H(X))*H (X)*G(H(X)) + X Y X + + + G (H(X))*H (X)*F(X,H(X)) + Y X +\end{verbatim} + +Cooperation of partial derivatives and Taylor series under +a differential side relation $\frac{dq}{dx}=f(x,q)$: + +\begin{verbatim} + load_package taylor; + operator q; + let df(q(~x),x) => f(x,q(x)); + taylor(q(x0+h),h,0,3); + + F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) + X Y 2 +Q(X0) + F(X0,Q(X0))*H + -----------------------------------------*H + 2 + ++ (F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) + XX XY + + + F (X0,Q(X0))*F (X0,Q(X0)) + F (X0,Q(X0))*F(X0,Q(X0)) + X Y YX + + 2 2 3 + + F (X0,Q(X0))*F(X0,Q(X0)) + F (X0,Q(X0)) *F(X0,Q(X0)))/6*H + YY Y + + 4 + + O(H ) + +\end{verbatim} + +Normally partial differentials are assumed as non-commutative + +\begin{verbatim} + dfp(f(),x,y)-dfp(f(),y,x); + + F - F + XY YX +\end{verbatim} + +However, a generic function can be declared to have globally +interchangeable partial derivatives using the declaration +{\tt DFP\_COMMUTE} +which takes the name of a generic function or a generic function +form as argument. For such a function differentiation variables are +rearranged corresponding to the sequence of the generic variables. + +\begin{verbatim} + generic_function q(x,y); + dfp_commute q(x,y); + dfp(q(),{x,y,y}) + dfp(q(),{y,x,y}) + dfp(q(),{y,y,x}); + + 3*Q + XYY +\end{verbatim} + +If only a part of the derivatives commute, this has to be +declared using the standard {\REDUCE} rule mechanism. Please +note that then the derivative variables must be written as +list. + +\section{Substitutions} + +When a generic form or a {\tt DFP} expression takes part in a +substitution the following steps are performed: +\begin{enumerate} +\item The substitutions are performed for the arguments. If the +argument list is empty the substitution is applied to the +generic arguments of the function; if these change, the resulting +forms are used as new actual arguments. +If the generic function itself is not affected by the substitution, +the process stops here. +\item If the function name or the generic function +form occurs as a left hand side in the substitution list, +it is replaced by the corresponding right hand side. +\item The new form is partially differentiated according to the +list of partial derivative variables. +\item The (eventually modified) actual parameters are substituted +into the form for their corresponding generic variables. +This substitution is done by name. +\end{enumerate} + +Examples: +\begin{verbatim} + generic_function f(x,y); + sub(y=10,f()); + + F(X,10) + + sub(y=10,dfp(f(),x,2)); + + + F (X,10) + XX + + sub(y=10,dfp(f(y,y),x,2)); + + F (10,10) + XX + + sub(f=x**3*y**3,dfp(f(),x,2)); + + 3 + 6*X*Y + + generic_function ff(y,z); + sub(f=ff,f(a,b)); + + FF(B,Z) +\end{verbatim} + +The dataset $dfpart.tst$ contains more examples, +including a complete application for computing the coefficient +equations for Runge-Kutta ODE solvers. + +\end{document} Index: r36/doc/DUMMY.TEX ================================================================== --- r36/doc/DUMMY.TEX +++ r36/doc/DUMMY.TEX @@ -1,143 +1,143 @@ -\documentstyle[11pt,reduce]{article} -\newcommand{\nl}{\hfill\newline} -\newcommand{\bq}{\begin{quotation}} -\newcommand{\eq}{\end{quotation}} -\newcommand{\bi}{\begin{itemize}} -\newcommand{\ei}{\end{itemize}} -\date{} -\title{{\bf DUMMY}\\[3pt] -A package to find the canonical form of expressions involving -dummy variables\\[5pt] - \mbox{\hfill Version 1.0\hfil}} -\author{Alain Dresse \\ -Universit\'e Libre de Bruxelles \\ -Boulevard du Triomphe, CP 210/01 \\ -B--1050 BRUXELLES \\[3pt] -E--mail: adresse@ulb.ac.be} -\begin{document} -\maketitle -\index{DUMMY package} -\section{Introduction} -The proper use of dummy variables in computer algebra is difficult -because of the problem of simplifications. However, it is very important -to keep large expressions in a concise form and to manipulate them -efficiently. -The routines in the file allows to find the canonical form of expressions -involving dummy variables. In that way, the simplification of -polynomial expressions can be fully done. The indeterminates are general -operator objects endowed with as few properties as possible. In that way -the package may be used in a large spectrum of applications. - -In section 2, the convention for writing expressions is described and -the available declarations to distinguish between dummy and free variables -are explained. - -In section 3, the various declarations on the algebraic properties -of the operators as well as on their operational properties are -given. The use of the ready-to-use function {\tt canonuical} is illustrated. -In section 4, installation is explained. -\section{Dummy and Free Variables} -An expression of the type -$$ -\sum_{a=1}^{n} f(a) -$$ -for any $n$ is simply written as -$$ -f(a) -$$ -and $a$ is a {\em dummy} index. -If the previous expression is written as -$$ -\sum_{b=1}^{n} f(b) -$$ -$b$ is also a dummy index and, obviously we should be able to get the -equality -$$ -f(a)-f(b);\, \rightarrow 0 -$$ -To declare dummy variables, two declarations are available: -\begin{itemize} -\item{i.} -\begin{verbatim} - dummy_base ; -\end{verbatim} -where {\tt idp} is the name of any unassigned identifier. -\item{ii.} -\begin{verbatim} - dummy_names ,, ....; -\end{verbatim} -\end{itemize} -The first declares {\tt idp1,$\cdots$, idpn} as dummy variables i.e. -all variables of the form ``{\tt idxxx}'' where {\tt xxx} is a number -will be dummy variables, such as {\tt id1, id2, ... , id23}. -The second gives special names for dummy variables. -All other arguments are assumed to be {\tt free}.\\ -An example: -\begin{verbatim} - - dummy_base dv; ==> dv - - % dummy indices are dv1, dv2, dv3, ... - - dummy_names i,j,k; ==> t - - % dummy names are i,j,k. - -\end{verbatim} -When this is done, an expression like -\begin{verbatim} - op(dv1)*sin(dv2)*abs(x)*op(i)^3*op(dv2)$ -\end{verbatim} -is allowed. Notice that, dummy indices may not be repeated (it is not -limited to tensor calculus) or that they be repeated many times inside -the expression. -\section{Operators and Use of {\tt CANONICAL}} -All dummy variables are arguments of operators. These operators are -quite general, they may be element of an algebra, they may be tensors, -spinors, grassman variables, etc. $\ldots$ -By default they are assumed to be {\em commutative} and without symmetry -properties. Several commands allow to make variations about this default. - -First, the declarations {\tt NONCOM, SYMMETRIC and AN\-TI\-SYM\-ME\-TRIC} - may be used on the operators.\\ -Second, they may be declared anticommutative. -\begin{verbatim} - anticom ao1, ao2; -\end{verbatim} -Third, one may, declare partial symmetries for them thanks to the -declaration {\tt SYMTREE}. -Here is the corresponding declaration for the Riemann tensor -\begin{verbatim} - symtree (r, {!+, {!-, 1, 2}, {!-, 3, 4}}); -\end{verbatim} -The symbols !*, !+ and !- at the beginning of each list mean that -the operator has no symmetry, is symmetric and is antisymmetric with respect -to the indices inside the list. Notices that the indices are not designated -by their names but merely by their natural order of appearance. 1 means the -first written argument of {\tt r}, 2 its second argument etc. -In the example above r is symmetric with respect to interchange of the -pairs of indices 1,2 and 3,4 respectively. - -Notice that all the declarations here are valid whether the indices -are free or not. -It is then left to apply {CANONICAL} on any polynomial containing operators -to get its canonical representation. In that way full simplifications -are guaranteed. - -There are two limitations to the package. The first is that non-commuting -operators are assumed to commute with anticommuting ones. The second is -that it does not add anything to the problem of simplifications when -side relations (like Bianchi identities) are present. -\section{Installation} -The use of DUMMY requires that the package ASSIST version 2.2 be loaded. -It is also available in the \REDUCE\ library. Assuming that you got the -source files, use the script {\tt MKFASL} and do -\begin{verbatim} - mkfasl assist -\end{verbatim} -when done do -\begin{verbatim} - mkfasl dummy -\end{verbatim} -Finally, run the test file. -\end{document} +\documentstyle[11pt,reduce]{article} +\newcommand{\nl}{\hfill\newline} +\newcommand{\bq}{\begin{quotation}} +\newcommand{\eq}{\end{quotation}} +\newcommand{\bi}{\begin{itemize}} +\newcommand{\ei}{\end{itemize}} +\date{} +\title{{\bf DUMMY}\\[3pt] +A package to find the canonical form of expressions involving +dummy variables\\[5pt] + \mbox{\hfill Version 1.0\hfil}} +\author{Alain Dresse \\ +Universit\'e Libre de Bruxelles \\ +Boulevard du Triomphe, CP 210/01 \\ +B--1050 BRUXELLES \\[3pt] +E--mail: adresse@ulb.ac.be} +\begin{document} +\maketitle +\index{DUMMY package} +\section{Introduction} +The proper use of dummy variables in computer algebra is difficult +because of the problem of simplifications. However, it is very important +to keep large expressions in a concise form and to manipulate them +efficiently. +The routines in the file allows to find the canonical form of expressions +involving dummy variables. In that way, the simplification of +polynomial expressions can be fully done. The indeterminates are general +operator objects endowed with as few properties as possible. In that way +the package may be used in a large spectrum of applications. + +In section 2, the convention for writing expressions is described and +the available declarations to distinguish between dummy and free variables +are explained. + +In section 3, the various declarations on the algebraic properties +of the operators as well as on their operational properties are +given. The use of the ready-to-use function {\tt canonuical} is illustrated. +In section 4, installation is explained. +\section{Dummy and Free Variables} +An expression of the type +$$ +\sum_{a=1}^{n} f(a) +$$ +for any $n$ is simply written as +$$ +f(a) +$$ +and $a$ is a {\em dummy} index. +If the previous expression is written as +$$ +\sum_{b=1}^{n} f(b) +$$ +$b$ is also a dummy index and, obviously we should be able to get the +equality +$$ +f(a)-f(b);\, \rightarrow 0 +$$ +To declare dummy variables, two declarations are available: +\begin{itemize} +\item{i.} +\begin{verbatim} + dummy_base ; +\end{verbatim} +where {\tt idp} is the name of any unassigned identifier. +\item{ii.} +\begin{verbatim} + dummy_names ,, ....; +\end{verbatim} +\end{itemize} +The first declares {\tt idp1,$\cdots$, idpn} as dummy variables i.e. +all variables of the form ``{\tt idxxx}'' where {\tt xxx} is a number +will be dummy variables, such as {\tt id1, id2, ... , id23}. +The second gives special names for dummy variables. +All other arguments are assumed to be {\tt free}.\\ +An example: +\begin{verbatim} + + dummy_base dv; ==> dv + + % dummy indices are dv1, dv2, dv3, ... + + dummy_names i,j,k; ==> t + + % dummy names are i,j,k. + +\end{verbatim} +When this is done, an expression like +\begin{verbatim} + op(dv1)*sin(dv2)*abs(x)*op(i)^3*op(dv2)$ +\end{verbatim} +is allowed. Notice that, dummy indices may not be repeated (it is not +limited to tensor calculus) or that they be repeated many times inside +the expression. +\section{Operators and Use of {\tt CANONICAL}} +All dummy variables are arguments of operators. These operators are +quite general, they may be element of an algebra, they may be tensors, +spinors, grassman variables, etc. $\ldots$ +By default they are assumed to be {\em commutative} and without symmetry +properties. Several commands allow to make variations about this default. + +First, the declarations {\tt NONCOM, SYMMETRIC and AN\-TI\-SYM\-ME\-TRIC} + may be used on the operators.\\ +Second, they may be declared anticommutative. +\begin{verbatim} + anticom ao1, ao2; +\end{verbatim} +Third, one may, declare partial symmetries for them thanks to the +declaration {\tt SYMTREE}. +Here is the corresponding declaration for the Riemann tensor +\begin{verbatim} + symtree (r, {!+, {!-, 1, 2}, {!-, 3, 4}}); +\end{verbatim} +The symbols !*, !+ and !- at the beginning of each list mean that +the operator has no symmetry, is symmetric and is antisymmetric with respect +to the indices inside the list. Notices that the indices are not designated +by their names but merely by their natural order of appearance. 1 means the +first written argument of {\tt r}, 2 its second argument etc. +In the example above r is symmetric with respect to interchange of the +pairs of indices 1,2 and 3,4 respectively. + +Notice that all the declarations here are valid whether the indices +are free or not. +It is then left to apply {CANONICAL} on any polynomial containing operators +to get its canonical representation. In that way full simplifications +are guaranteed. + +There are two limitations to the package. The first is that non-commuting +operators are assumed to commute with anticommuting ones. The second is +that it does not add anything to the problem of simplifications when +side relations (like Bianchi identities) are present. +\section{Installation} +The use of DUMMY requires that the package ASSIST version 2.2 be loaded. +It is also available in the \REDUCE\ library. Assuming that you got the +source files, use the script {\tt MKFASL} and do +\begin{verbatim} + mkfasl assist +\end{verbatim} +when done do +\begin{verbatim} + mkfasl dummy +\end{verbatim} +Finally, run the test file. +\end{document} Index: r36/doc/EXCALC.TEX ================================================================== --- r36/doc/EXCALC.TEX +++ r36/doc/EXCALC.TEX @@ -1,1583 +1,1583 @@ -\documentstyle[11pt,reduce]{article} -\title{EXCALC: A System for Doing Calculations in the Calculus of Modern -Differential Geometry} -\author{Eberhard Schr\"{u}fer \\ -Institute SCAI.Alg \\ -German National Research Center for Information Technology (GMD) \\ -Schloss Birlinghoven \\ -D-53754 Sankt Augustin \\ -Germany \\[0.05in] -Email: schruefer@gmd.de} -\begin{document} -\maketitle - -\index{EXCALC package} - -\section*{Acknowledgments} - -This program was developed over several years. I would like to express -my deep gratitude to Dr. Anthony Hearn for his continuous interest in -this work, and especially for his hospitality and support during a -visit in 1984/85 at the RAND Corporation, where substantial progress -on this package could be achieved. The Heinrich Hertz-Stiftung -supported this visit. Many thanks are also due to Drs. F.W. Hehl, -University of Cologne, and J.D. McCrea, University College Dublin, for -their suggestions and work on testing this program. - -\section{Introduction} - -\index{differential geometry} -{\bf EXCALC} is designed for easy use by all who are familiar with the -calculus of Modern Differential Geometry. Its syntax is kept as close -as possible to standard textbook notations. Therefore, no great -experience in writing computer algebra programs is required. It is -almost possible to input to the computer the same as what would have -been written down for a hand-calculation. For example, the statement - -\begin{verbatim} - f*x^y + u _| (y^z^x) -\end{verbatim} - -\index{exterior calculus} -would be recognized by the program as a formula involving exterior -products and an inner product. The program is currently able to -handle scalar-valued exterior forms, vectors and operations between -them, as well as non-scalar valued forms (indexed forms). With this, -it should be an ideal tool for studying differential equations, -doing calculations in general relativity and field theories, or doing -such simple things as calculating the Laplacian of a tensor field for -an arbitrary given frame. With the increasing popularity of this -calculus, this program should have an application in almost any field -of physics and mathematics. - -Since the program is completely embedded in {\REDUCE}, all features and -facilities of {\REDUCE} are available in a calculation. Even for those -who are not quite comfortable in this calculus, there is a good chance -of learning it by just playing with the program. - -This is the last release of version 2. A much extended differential -geometry package (which includes complete symbolic index simplification, -tensors, mappings, bundles and others) is under development. - -Complaints and comments are appreciated and should be send to the author. -If the use of this program leads to a publication, this document should -be cited, and a copy of the article to the above address would be -welcome. - -\section{Declarations} - -Geometrical objects like exterior forms or vectors are introduced to the -system by declaration commands. The declarations can appear anywhere in -a program, but must, of course, be made prior to the use of the object. -Everything that has no declaration is treated as a constant; therefore -zero-forms must also be declared. - -An exterior form is introduced by\label{PFORM} \index{PFORM statement} -\index{exterior form ! declaration} - -\hspace*{2em} \k{PFORM} \s{declaration$_1$}, \s{declaration$_2$}, \ldots; - -where - -\begin{tabbing} -\s{declaration} ::= \s{name} $\mid$ \s{list of names}=\s{number} $\mid$ \s{identifier} $\mid$ \\ -\s{expression} \\ -\s{name} ::= \s{identifier} $\mid$ \s{identifier}(\s{arguments}) -\end{tabbing} - -For example - -\begin{verbatim} - pform u=k,v=4,f=0,w=dim-1; -\end{verbatim} - -declares {\tt U} to be an exterior form of degree {\tt K}, {\tt V} to be a -form of degree 4, {\tt F} to be a form of degree 0 (a function), and {\tt W} -to be a form of degree {\tt DIM}-1. - -If the exterior form should have indices, the declaration would be -\index{exterior form ! with indices} - -\begin{verbatim} - pform curv(a,b)=2,chris(a,b)=1; -\end{verbatim} - -The names of the indices are arbitrary. - -Exterior forms of the same degree can be grouped into lists to save typing. - -\begin{verbatim} - pform {x,y,z}=0,{rho(k,l),u,v(k)}=1; -\end{verbatim} - -The declaration of vectors is similar. The command {\tt TVECTOR}\label{TVECTOR} -takes a list of names. \index{TVECTOR command} \index{exterior form ! vector} - -\hspace*{2em} \k{TVECTOR} \s{name$_1$}, \s{name$_2$}, \ldots; - -For example, to declare {\tt X} as a vector and {\tt COMM} as a vector with -two indices, one would say - -\begin{verbatim} - tvector x,comm(a,b); -\end{verbatim} - -If a declaration of an already existing name is made, the old -declaration is removed, and the new one is taken. - -The exterior degree of a symbol or a general expression can be obtained -with the function \label{EXDEGREE} \index{EXDEGREE command} - -\hspace*{2em} \k{EXDEGREE} \s{expression}; - -Example: -\begin{verbatim} - exdegree(u + 3*chris(k,-k)); - - 1 -\end{verbatim} - - -\section{Exterior Multiplication} - -\index{"\^{} ! exterior multiplication} \index{exterior product} -Exterior multiplication between exterior forms is carried out with the -nary infix operator \^{ } (wedge)\label{wedge}. Factors are ordered -according to the usual ordering in {\REDUCE} using the commutation -rule for exterior products. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - pform u=1,v=1,w=k; - - u^v; - - U^V - - v^u; - - - U^V - - u^u; - - 0 - - w^u^v; - - K - ( - 1) *U^V^W - - (3*u-a*w)^(w+5*v)^u; - - A*(5*U^V^W - U^W^W) -\end{verbatim} - -It is possible to declare the dimension of the underlying space -by\label{SPACEDIM} \index{SPACEDIM command} \index{dimension} - -\hspace*{2em} \k{SPACEDIM} \s{number} $\mid$ \s{identifier}; - -If an exterior product has a degree higher than the dimension of the -space, it is replaced by 0: - -\begin{verbatim} - spacedim 4; - - pform u=2,v=3; - - u^v; - - 0 -\end{verbatim} - - -\section{Partial Differentiation} - -Partial differentiation is denoted by the operator {\tt @}\label{at}. Its -capability is the same as the {\REDUCE} {\tt DF} operator. -\index{"@ operator} \index{partial differentiation} -\index{differentiation ! partial} - -\example\index{EXCALC package ! example} - -\begin{verbatim} - @(sin x,x); - - COS(X) - - @(f,x); - - 0 -\end{verbatim} - -An identifier can be declared to be a function of certain variables. -\index{FDOMAIN command} -This is done with the command {\tt FDOMAIN}\label{FDOMAIN}. The -following would tell the partial differentiation operator that {\tt F} -is a function of the variables {\tt X} and {\tt Y} and that {\tt H} is -a function of {\tt X}. - -\begin{verbatim} - fdomain f=f(x,y),h=h(x); -\end{verbatim} - -Applying {\tt @} to {\tt F} and {\tt H} would result in - -\begin{verbatim} - @(x*f,x); - - F + X*@ F - X - - @(h,y); - - 0 -\end{verbatim} - -\index{tangent vector} -The partial derivative symbol can also be an operator with a single -argument. It then represents a natural base element of a tangent -vector\label{at1}. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - a*@ x + b*@ y; - - A*@ + B*@ - X Y -\end{verbatim} - -\section{Exterior Differentiation} -\index{exterior differentiation} -Exterior differentiation of exterior forms is carried out by the -operator {\tt d}\label{d}. Products are normally differentiated out, -{\em i.e.} - -\begin{verbatim} - pform x=0,y=k,z=m; - - d(x * y); - - X*d Y + d X^Y - - d(r*y); - - R*d Y - - d(x*y^z); - - K - ( - 1) *X*Y^d Z + X*d Y^Z + d X^Y^Z -\end{verbatim} - -This expansion can be suppressed by the command {\tt NOXPND D}\label{NOXPNDD}. -\index{NOXPND ! D} - -\begin{verbatim} - noxpnd d; - - d(y^z); - - d(Y^Z) -\end{verbatim} - -To obtain a canonical form for an exterior product when the expansion -is switched off, the operator {\tt D} is shifted to the right if it -appears in the leftmost place. - -\begin{verbatim} - d y ^ z; - - K - - ( - 1) *Y^d Z + d(Y^Z) -\end{verbatim} - -Expansion is performed again when the command {\tt XPND D}\label{XPNDD} -is executed. \index{XPND ! D} - -Functions which are implicitly defined by the {\tt FDOMAIN} command are -expanded into partial derivatives: - -\begin{verbatim} - pform x=0,y=0,z=0,f=0; - - fdomain f=f(x,y); - - d f; - - @ F*d X + @ F*d Y - X Y -\end{verbatim} - -If an argument of an implicitly defined function has further -dependencies the chain rule will be applied {\em e.g.} \index{chain rule} - - -\begin{verbatim} - fdomain y=y(z); - - d f; - - @ F*d X + @ F*@ Y*d Z - X Y Z -\end{verbatim} - -Expansion into partial derivatives can be inhibited by -{\tt NOXPND @}\label{NOXPNDA} -and enabled again by {\tt XPND @}\label{XPNDA}. -\index{NOXPND ! "@} \index{XPND ! "@} - -The operator is of course aware of the rules that a repeated -application always leads to zero and that there is no exterior form of -higher degree than the dimension of the space. - -\begin{verbatim} - d d x; - - 0 - - pform u=k; - spacedim k; - - d u; - - 0 -\end{verbatim} -\section{Inner Product} -\index{inner product ! exterior form} -The inner product between a vector and an exterior form is represented -by the diphthong \_$|$ \label{innerp} (underscore or-bar), which is the -notation of many textbooks. If the exterior form is an exterior -product, the inner product is carried through any factor. -\index{\_$\mid$ operator} - -\example\index{EXCALC package ! example} - -\begin{verbatim} - pform x=0,y=k,z=m; - - tvector u,v; - - u _| (x*y^z); - - K - X*(( - 1) *Y^U _| Z + U _| Y^Z) -\end{verbatim} - -In repeated applications of the inner product to the same exterior -form the vector arguments are ordered {\em e.g.} - -\begin{verbatim} - (u+x*v) _| (u _| (3*z)); - - - 3*U _| V _| Z -\end{verbatim} - -The duality of natural base elements is also known by the system, {\em i.e.} - -\begin{verbatim} - pform {x,y}=0; - - (a*@ x+b*@(y)) _| (3*d x-d y); - - 3*A - B -\end{verbatim} - -\section{Lie Derivative} - -\index{Lie Derivative} -The Lie derivative can be taken between a vector and an exterior form -or between two vectors. It is represented by the infix operator $|$\_ -\label{lie}. In the case of Lie differentiating, an exterior form by -a vector, the Lie derivative is expressed through inner products and -exterior differentiations, {\em i.e.} \index{$\mid$\_ operator} - -\begin{verbatim} - pform z=k; - - tvector u; - - u |_ z; - - U _| d Z + d(U _| Z) -\end{verbatim} - -If the arguments of the Lie derivative are vectors, the vectors are -ordered using the anticommutivity property, and functions (zero forms) -are differentiated out. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - tvector u,v; - - v |_ u; - - - U |_ V - - pform x=0,y=0; - - (x*u) |_ (y*v); - - - U*Y*V _| d X + V*X*U _| d Y + X*Y*U |_ V -\end{verbatim} - -\section{Hodge-* Duality Operator} - -\index{Hodge-* duality operator} \index{"\# ! Hodge-* operator} -The Hodge-*\label{hodge} duality operator maps an exterior form of degree -{\tt K} to an exterior form of degree {\tt N-K}, where {\tt N} is the -dimension of the space. The double application of the operator must -lead back to the original exterior form up to a factor. The following -example shows how the factor is chosen here - -\begin{verbatim} - spacedim n; - pform x=k; - - # # x; - - 2 - (K + K*N) - ( - 1) *X*SGN -\end{verbatim} -\pagebreak -\index{SGN ! indeterminate sign} \index{coframe} -The indeterminate SGN in the above example denotes the sign of the -determinant of the metric. It can be assigned a value or will be -automatically set if more of the metric structure is specified (via -COFRAME), {\em i.e.} it is then set to $g/|g|$, where $g$ is the -determinant of the metric. If the Hodge-* operator appears in an -exterior product of maximal degree as the leftmost factor, the Hodge-* -is shifted to the right according to - -\begin{verbatim} - pform {x,y}=k; - - # x ^ y; - - 2 - (K + K*N) - ( - 1) *X^# Y -\end{verbatim} - -More simplifications are performed if a coframe is defined. - - - -\section{Variational Derivative} - -\index{derivative ! variational} \index{variational derivative} -\ttindex{VARDF} -The function {\tt VARDF}\label{VARDF} returns as its value the -variation of a given Lagrangian n-form with respect to a specified -exterior form (a field of the Lagrangian). In the shared variable -\ttindex{BNDEQ"!*} -{\tt BNDEQ!*}, the expression is stored that has to yield zero if -integrated over the boundary. - -Syntax: - -\hspace*{2em} \k{VARDF}(\s{Lagrangian n-form},\s{exterior form}) - -\example\index{EXCALC package ! example} - -\begin{verbatim} - spacedim 4; - - pform l=4,a=1,j=3; - - l:=-1/2*d a ^ # d a - a^# j$ %Lagrangian of the e.m. field - - vardf(l,a); - - - (# J + d # d A) %Maxwell's equations - - bndeq!*; - - - 'A^# d A %Equation at the boundary -\end{verbatim} - -Restrictions: - -In the current implementation, the Lagrangian must be built up by the -fields and the operations {\tt d}, {\tt \#}, and {\tt @}. Variation -with respect to indexed quantities is currently not allowed. - -For the calculation of the conserved currents induced by symmetry -operators (vector fields), the function {\tt NOETHER}\label{NOETHER} -\index{NOETHER function} -is provided. It has the syntax: - -\hspace*{2em} -\k{NOETHER}(\s{Lagrangian n-form},\s{field},\s{symmetry generator}) - -\example\index{EXCALC package ! example} - -\begin{verbatim} - pform l=4,a=1,f=2; - - spacedim 4; - - l:= -1/2*d a^#d a; %Free Maxwell field; - - tvector x(k); %An unspecified generator; - - noether(l,a,x(-k)); - - ( - 2*d(X _|A)^# d A - (X _|d A)^# d A + d A^(X _|# d A))/2 - K K K -\end{verbatim} - -The above expression would be the canonical energy -momentum 3-forms of the Maxwell field, if X is interpreted -as a translation; - - - -\section{Handling of Indices} -\index{exterior form ! with indices} -Exterior forms and vectors may have indices. On input, the indices -are given as arguments of the object. A positive argument denotes a -superscript and a negative argument a subscript. On output, the -indexed quantity is displayed two dimensionally if {\tt NAT} is on. -\index{NAT flag} -Indices may be identifiers or numbers. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - pform om(k,l)=m,e(k)=1; - - e(k)^e(-l); - - K - E ^E - L - - om(4,-2); - - 4 - OM - 2 -\end{verbatim} - -In the current release, full simplification is performed only if an -index range is specified. It is hoped that this restriction can be -removed soon. If the index range (the values that the indices can -obtain) is specified, the given expression is evaluated for all -possible index values, and the summation convention is understood. - -\example\label{INDEXRANGE}\index{EXCALC package ! example} - -\begin{verbatim} - indexrange t,r,ph,z; - - pform e(k)=1,s(k,l)=2; - - w := e(k)*e(-k); - - T R PH Z - W := E *E + E *E + E *E + E *E - T R PH Z - - - s(k,l):=e(k)^e(l); - - T T - S := 0 - - R T T R - S := - E ^E - - PH T T PH - S := - E ^E - - . - . - . - -\end{verbatim} - -If the expression to be evaluated is not an assignment, the values of -the expression are displayed as an assignment to an indexed variable -with name {\tt NS}. This is done only on output, {\em i.e.} no actual -binding to the variable NS occurs. -\index{NS dummy variable} - -\begin{verbatim} - e(k)^e(l); - - T T - NS := 0 - - R T T R - NS := - E ^E - . - . - . -\end{verbatim} - -It should be noted, however, that the index positions on the variable -NS can sometimes not be uniquely determined by the system (because of -possible reorderings in the expression). Generally it is advisable to -use assignments to display complicated expressions. - -A range can also be assigned to individual index-names. For example, -the declaration - -\begin{verbatim} - indexrange {k,l}={x,y,z},{u,v,w}={1,2}; -\end{verbatim} - -would assign to the index identifiers k,l the range values x,y,z and -to the index identifiers u,v,w the range values 1,2. The use of an -index identifier not listed in previous indexrange statements has the -range of the union of all given index ranges. - -With the above example of an indexrange statement, the following -index evaluations would take place - -\begin{verbatim} - pform w n=0; - - w(k)*w(-k); - - X Y Z - W *W + W *W + W *W - X Y Z - - w(u)*w(-u); - - 1 2 - W *W + W *W - 1 2 - - w(r)*w(-r); - - 1 2 X Y Z - W *W + W *W + W *W + W *W + W *W - 1 2 X Y Z -\end{verbatim} - -In certain cases, one would like to inhibit the summation over -specified index names, or at all. For this the command - -\index{NOSUM command} -\hspace*{2em} \k{NOSUM} \s{indexname$_1$}, \ldots;\label{NOSUM} - -and the switch {\tt NOSUM} are \index{NOSUM switch} -available. The command {\tt NOSUM} has the effect that summation is -not performed over those indices which had been listed. The command -{\tt RENOSUM}\label{RENOSUM} enables summation again. The switch {\tt -NOSUM}, if on, inhibits any summation. \index{RENOSUM command} - -\label{INDEXSYMMETRIES} \index{INDEXSYMMETRIES command} -It is possible to declare symmetry properties for an indexed quantity by -the command {\tt INDEX\_SYMMETRIES}. A prototypical example is as -follows - -\begin{verbatim} - - index_symmetries u(k,l,m,n): symmetric in {k,l},{m,n} - antisymmetric in {{k,l},{m,n}}, - g(k,l),h(k,l): symmetric; - -\end{verbatim} - -It declares the object {\tt u} symmetric in the first two and last -two indices and antisymmetric with respect to commutation of the given -index pairs. If an object is completely symmetric or antisymmetric, -the indices need not to be given after the corresponding keyword as -shown above for {\tt g} and {\tt h}. - -If applicable, this command should -be issued, since great savings in memory and execution time result. -Only strict components are printed. - -The commands symmetric and antisymmetric of earlier releases have no -effect. - - -\section{Metric Structures} - -\index{metric structure} \index{coframe} -A metric structure is defined in {\bf EXCALC} by specifying a set of -basis one-forms (the coframe) together with the metric. - -Syntax:\label{COFRAME} - -\begin{tabbing} -\hspace*{2em} \k{COFRAME} \= -\s{identifier}\s{(index$_1$)}=\s{expression$_1$}, \\ -\> \s{identifier}\s{(index$_2$)}=\s{expression$_2$}, \\ -\> . \\ -\> . \\ -\> . \\ -\> \s{identifier}\s{(index$_n$)}=\s{expression$_n$} \\ -\> \hspace{1em} \k{WITH} \k{METRIC} \s{name}=\s{expression}; \\ -\end{tabbing} - -\index{euclidean metric} \index{COFRAME ! WITH METRIC} -This statement automatically sets the dimension of the space and the -index range. The clause {\tt WITH METRIC} can be omitted if the metric -\index{COFRAME ! WITH SIGNATURE} -is Euclidean and the shorthand {\tt WITH SIGNATURE \s{diagonal elements}} -\label{SIGNATURE} can be used in the case of a pseudo-Euclidean metric. The -splitting of a metric structure in its metric tensor coefficients and -basis one-forms is completely arbitrary including the extremes of an -orthonormal frame and a coordinate frame. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - coframe e r=d r, e(ph)=r*d ph - with metric g=e(r)*e(r)+e(ph)*e(ph); %Polar coframe - - coframe e(r)=d r,e(ph)=r*d(ph); %Same as before - - coframe o(t)=d t, o x=d x - with signature -1,1; %A Lorentz coframe - - coframe b(xi)=d xi, b(eta)=d eta %A lightcone coframe - with metric w=-1/2*(b(xi)*b(eta)+b(eta)*b(xi)); - - coframe e r=d r, e ph=d ph %Polar coordinate - with metric g=e r*e r+r**2*e ph*e ph; %basis - -\end{verbatim} - -Individual elements of the metric can be accessed just by calling them -with the desired indices. The value of the determinant of the -\index{determinant ! in DETM"!*} \ttindex{DETM"!*} -covariant metric is stored in the variable {\tt DETM!*}. The metric -is not needed for lowering or raising of indices as the system -performs this automatically, {\em i.e.} no matter in what index -position values were assigned to an indexed quantity, the values can -be retrieved for any index position just by writing the indexed -quantity with the desired indices. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - coframe e t=d t,e x=d x,e y=d y - with signature -1,1,1; - - pform f(k,l)=0; - - antisymmetric f; - - f(-t,-x):=ex$ f(-x,-y):=b$ f(-t,-y):=0$ - on nero; - - f(k,-l):=f(k,-l); - - X - F := - EX - T - - T - F := - EX - X - - Y - F := - B - X - - X - F := B - Y -\end{verbatim} - -Any expression containing differentials of the coordinate functions will -be transformed into an expression of the basis one-forms.The system also -knows how to take the exterior derivative of the basis one-forms. - -\index{spherical coordinates} -\example (Spherical coordinates)\index{EXCALC package ! example} - -\begin{verbatim} - coframe e(r)=d(r), e(th)=r*d(th), e(ph)=r*sin(th)*d(ph); - - d r^d th; - - R TH - (E ^E )/R - - d(e(th)); - - R TH - (E ^E )/R - - - pform f=0; - - fdomain f=f(r,th,ph); - - factor e; - - on rat; - - d f; %The "gradient" of F in spherical coordinates; - - R TH PH - E *@ F + (E *@ F)/R + (E *@ F)/(R*SIN(TH)) - R TH PH -\end{verbatim} - -The frame dual to the frame defined by the {\tt COFRAME} command can -be introduced by \k{FRAME} command. \index{FRAME command} - -\hspace*{2em} \k{FRAME} \s{identifier};\label{FRAME} - -This command causes the -dual property to be recognized, and the tangent vectors of the -coordinate functions are replaced by the frame basis vectors. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - coframe b r=d r,b ph=r*d ph,e z=d z; %Cylindrical coframe; - - frame x; - - on nero; - - x(-k) _| b(l); - - R - NS := 1 - R - - PH - NS := 1 - PH - - Z - NS := 1 - Z - - x(-k) |_ x(-l); %The commutator of the dual frame; - - - NS := X /R - PH R PH - - - NS := ( - X )/R %i.e. it is not a coordinate base; - R PH PH - -\end{verbatim} - -\index{DISPLAYFRAME command} \index{tracing ! EXCALC} -As a convenience, the frames can be displayed at any point in a program -by the command {\tt DISPLAYFRAME;}\label{DISPLAYFRAME}. - -\index{Hodge-* duality operator} -The Hodge-* duality operator returns the explicitly constructed dual -element if applied to coframe base elements. The metric is properly -taken into account. - -\index{Levi-Cevita tensor} \ttindex{EPS} -The total antisymmetric Levi-Cevita tensor {\tt EPS}\label{EPS} is -also available. The value of {\tt EPS} with an even permutation of the -indices in a covariant position is taken to be +1. - - -\section{Riemannian Connections} - -\index{Riemannian Connections} -The command {\tt RIEMANNCONX} is provided for calculating the -\index{RIEMANNCONX command} \label{RIEMANNCONX} -connection 1 forms. The values are stored on the name given to {\tt -RIEMANNCONX}. This command is far more efficient than calculating the -connection from the differential of the basis one-forms and using -inner products. - -\example (Calculate the connection 1-form and curvature 2-form on S(2)) -\index{EXCALC package ! example} - -\begin{verbatim} - coframe e th=r*d th,e ph=r*sin(th)*d ph; - - riemannconx om; - - om(k,-l); %Display the connection forms; - - TH - NS := 0 - TH - - PH PH - NS := (E *COS(TH))/(SIN(TH)*R) - TH - - TH PH - NS := ( - E *COS(TH))/(SIN(TH)*R) - PH - - PH - NS := 0 - PH - - pform curv(k,l)=2; - - - curv(k,-l):=d om(k,-l) + om(k,-m)^om(m-l); - %The curvature forms - - TH - CURV := 0 - TH - - PH TH PH 2 - CURV := ( - E ^E )/R - TH %Of course it was a sphere with - %radius R. - - TH TH PH 2 - CURV := (E ^E )/R - PH - - PH - CURV := 0 - PH -\end{verbatim} - -\section{Ordering and Structuring} - -\index{ordering ! exterior form} \index{FORDER command} -The ordering of an exterior form or vector can be changed by the -command {\tt FORDER}.\label{FORDER} In an expression, the first -identifier or kernel in the arguments of {\tt FORDER} is ordered ahead -of the second, and so on, and ordered ahead of all not appearing as -arguments. This ordering is done on the internal level and not only -on output. The execution of this statement can therefore have -tremendous effects on computation time and memory requirements. {\tt -REMFORDER}\label{REMFORDER} brings back standard ordering for those -elements that are listed as arguments. \index{REMFORDER command} - -An expression can be put in a more structured form by renaming a -subexpression. This is done with the command {\tt KEEP} which -has the syntax \index{KEEP command}\label{KEEP} - -\hspace*{2em} \k{KEEP} -\s{name$_1$}=\s{expression$_1$},\s{name$_2$}=\s{expression$_2$}, \ldots - -The effect is that rules are set up for simplifying \s{name} without -introducing its definition in an expression. In an expression the system -also tries by reordering to generate as many instances of \s{name} as -possible. - -\example\index{EXCALC package ! example} - -\begin{verbatim} - pform x=0,y=0,z=0,f=0,j=3; - - keep j=d x^d y^d z; - - j; - - J - - d j; - - 0 - - j^d x; - - 0 - - fdomain f=f(x); - - d f^d y^d z; - - @ F*J - X -\end{verbatim} - -\index{exterior product} -The capabilities of {\tt KEEP} are currently very limited. Only exterior -products should occur as righthand sides in {\tt KEEP}. - - -\section{Summary of Operators and Commands} -Table~\ref{EXCALC:sum} summarizes EXCALC commands and the page number they are -defined on. - -\begin{table} -\begin{tabular}{l l r} -\index{"\^{} ! exterior multiplication} \index{wedge} -\^{ } & Exterior Multiplication & \pageref{wedge} \\ -\index{"@ ! partial differentiation} -@ & Partial Differentiation & \pageref{at} \\ -\index{"@ ! tangent vector} -@ & Tangent Vector & \pageref{at1} \\ -\index{"\# ! Hodge-* operator} -\# & Hodge-* Operator & \pageref{hodge} \\ -\index{\_$\mid$ operator} -\_$|$ & Inner Product & \pageref{innerp} \\ -\index{$\mid$\_ operator} -$|$\_ & Lie Derivative & \pageref{lie} \\ -\index{COFRAME command} -COFRAME & Declaration of a coframe & \pageref{COFRAME} \\ -\index{d ! exterior differentiation} -d & Exterior differentiation & \pageref{d} \\ -\index{DISPLAYFRAME command} -DISPLAYFRAME & Displays the frame & \pageref{DISPLAYFRAME}\\ -\index{EPS ! Levi-Civita tensor} -EPS & Levi-Civita tensor & \pageref{EPS} \\ -\index{EXDEGREE} -EXDEGREE & Calculates the exterior degree of an expression & \pageref{EXDEGREE} \\ -\index{FDOMAIN command} -FDOMAIN & Declaration of implicit dependencies &\pageref{FDOMAIN} \\ -\index{FORDER command} -FORDER & Ordering command & \pageref{FORDER} \\ -\index{FRAME command} -FRAME & Declares the frame dual to the coframe & \pageref{FRAME} \\ -\index{INDEXRANGE command} -INDEXRANGE & Declaration of indices & \pageref{INDEXRANGE} \\ -\index{INDEX\_SYMMETRIES command} -INDEX\_SYMMETRIES & Declares arbitrary index symmetry properties & \pageref{INDEXSYMMETRIES} \\ -\index{KEEP command} -KEEP & Structuring command & \pageref{KEEP} \\ -\index{METRIC command} -METRIC & Clause of COFRAME to specify a metric & \pageref{COFRAME} \\ -\index{NOETHER function} -NOETHER & Calculates the Noether current & \pageref{NOETHER} \\ -\index{NOSUM command} -NOSUM & Inhibits summation convention & \pageref{NOSUM} \\ -\index{NOXPND command} -NOXPND d & Inhibits the use of product rule for d & -\pageref{NOXPNDD} \\ -\index{NOXPND "@ command} -NOXPND @ & Inhibits expansion into partial derivatives & -\pageref{NOXPNDA} \\ -\index{PFORM command} -PFORM & Declaration of exterior forms & \pageref{PFORM} \\ -\index{REMFORDER command} -REMFORDER & Clears ordering & \pageref{REMFORDER} \\ -\index{RENOSUM command} -RENOSUM & Enables summation convention & \pageref{RENOSUM} \\ -\index{RIEMANNCONX command} -RIEMANNCONX & Calculation of a Riemannian Connection & -\pageref{RIEMANNCONX} \\ -\index{SIGNATURE command} -SIGNATURE & Clause of COFRAME to specify a pseudo- & \pageref{SIGNATURE} \\ - & Euclidean metric & \\ -\index{SPACEDIM command} -SPACEDIM & Command to set the dimension of a space & -\pageref{SPACEDIM} \\ -\index{TVECTOR command} -TVECTOR & Declaration of vectors & \pageref{TVECTOR} \\ -\ttindex{VARDF} -VARDF & Variational derivative & \pageref{VARDF} \\ -\index{XPND command} -XPND d & Enables the use of product rule for d & \pageref{XPNDD} \\ - & (default) & \\ -\index{XPND ! "@} -XPND @ & Enables expansion into partial derivatives & \pageref{XPNDA} \\ - & (default) -\end{tabular} -\caption{EXCALC Command Summary}\label{EXCALC:sum} -\end{table} -\newpage -\section{Examples} - -The following examples should illustrate the use of {\bf EXCALC}. It is not -intended to show the most efficient or most elegant way of stating the -problems; rather the variety of syntactic constructs are exemplified. -The examples are on a test file distributed with {\bf EXCALC}. -\index{EXCALC package ! example} -{\small -\begin{verbatim} - -% Problem: Calculate the PDE's for the isovector of the heat equation. -% -------- -% (c.f. B.K. Harrison, f.B. Estabrook, "Geometric Approach...", -% J. Math. Phys. 12, 653, 1971) - -% The heat equation @ psi = @ psi is equivalent to the set of exterior -% xx t - -% equations (with u=@ psi, y=@ psi): -% T x - - -pform {psi,u,x,y,t}=0,a=1,{da,b}=2; - -a := d psi - u*d t - y*d x; - -da := - d u^d t - d y^d x; - -b := u*d x^d t - d y^d t; - - -% Now calculate the PDE's for the isovector. - -tvector v; - -pform {vpsi,vt,vu,vx,vy}=0; -fdomain vpsi=vpsi(psi,t,u,x,y),vt=vt(psi,t,u,x,y),vu=vu(psi,t,u,x,y), - vx=vx(psi,t,u,x,y),vy=vy(psi,t,u,x,y); - -v := vpsi*@ psi + vt*@ t + vu*@ u + vx*@ x + vy*@ y; - - -factor d; -on rat; - -i1 := v |_ a - l*a; - -pform o=1; - -o := ot*d t + ox*d x + ou*d u + oy*d y; - -fdomain f=f(psi,t,u,x,y); - -i11 := v _| d a - l*a + d f; - -let vx=-@(f,y),vt=-@(f,u),vu=@(f,t)+u*@(f,psi),vy=@(f,x)+y*@(f,psi), - vpsi=f-u*@(f,u)-y*@(f,y); - -factor ^; - -i2 := v |_ b - xi*b - o^a + zeta*da; - -let ou=0,oy=@(f,u,psi),ox=-u*@(f,u,psi), - ot=@(f,x,psi)+u*@(f,y,psi)+y*@(f,psi,psi); - -i2; - -let zeta=-@(f,u,x)-@(f,u,y)*u-@(f,u,psi)*y; - -i2; - -let xi=-@(f,t,u)-u*@(f,u,psi)+@(f,x,y)+u*@(f,y,y)+y*@(f,y,psi)+@(f,psi); - -i2; - -let @(f,u,u)=0; - -i2; % These PDE's have to be solved. - - -clear a,da,b,v,i1,i11,o,i2,xi,t; -remfdomain f,vpsi,vt,vu,vx,vy; -clear @(f,u,u); - - -% Problem: -% -------- -% Calculate the integrability conditions for the system of PDE's: -% (c.f. B.F. Schutz, "Geometrical Methods of Mathematical Physics" -% Cambridge University Press, 1984, p. 156) - - -% @ z /@ x + a1*z + b1*z = c1 -% 1 1 2 - -% @ z /@ y + a2*z + b2*z = c2 -% 1 1 2 - -% @ z /@ x + f1*z + g1*z = h1 -% 2 1 2 - -% @ z /@ y + f2*z + g2*z = h2 -% 2 1 2 ; - - -pform w(k)=1,integ(k)=4,{z(k),x,y}=0,{a,b,c,f,g,h}=1, - {a1,a2,b1,b2,c1,c2,f1,f2,g1,g2,h1,h2}=0; - -fdomain a1=a1(x,y),a2=a2(x,y),b1=b1(x,y),b2=b2(x,y), - c1=c1(x,y),c2=c2(x,y),f1=f1(x,y),f2=f2(x,y), - g1=g1(x,y),g2=g2(x,y),h1=h1(x,y),h2=h2(x,y); - - -a:=a1*d x+a2*d y$ -b:=b1*d x+b2*d y$ -c:=c1*d x+c2*d y$ -f:=f1*d x+f2*d y$ -g:=g1*d x+g2*d y$ -h:=h1*d x+h2*d y$ - -% The equivalent exterior system: -factor d; -w(1) := d z(-1) + z(-1)*a + z(-2)*b - c; -w(2) := d z(-2) + z(-1)*f + z(-2)*g - h; -indexrange 1,2; -factor z; -% The integrability conditions: - -integ(k) := d w(k) ^ w(1) ^ w(2); - -clear a,b,c,f,g,h,x,y,w(k),integ(k),z(k); -remfdomain a1,a2,b1,c1,c2,f1,f2,g1,g2,h1,h2; - -% Problem: -% -------- -% Calculate the PDE's for the generators of the d-theta symmetries of -% the Lagrangian system of the planar Kepler problem. -% c.f. W.Sarlet, F.Cantrijn, Siam Review 23, 467, 1981 -% Verify that time translation is a d-theta symmetry and calculate the -% corresponding integral. - -pform {t,q(k),v(k),lam(k),tau,xi(k),eta(k)}=0,theta=1,f=0, - {l,glq(k),glv(k),glt}=0; - -tvector gam,y; - -indexrange 1,2; - -fdomain tau=tau(t,q(k),v(k)),xi=xi(t,q(k),v(k)),f=f(t,q(k),v(k)); - -l := 1/2*(v(1)**2 + v(2)**2) + m/r$ % The Lagrangian. - -pform r=0; -fdomain r=r(q(k)); -let @(r,q 1)=q(1)/r,@(r,q 2)=q(2)/r,q(1)**2+q(2)**2=r**2; - -lam(k) := -m*q(k)/r; % The force. - -gam := @ t + v(k)*@(q(k)) + lam(k)*@(v(k))$ - -eta(k) := gam _| d xi(k) - v(k)*gam _| d tau$ - -y := tau*@ t + xi(k)*@(q(k)) + eta(k)*@(v(k))$ % Symmetry generator. - -theta := l*d t + @(l,v(k))*(d q(k) - v(k)*d t)$ - -factor @; - -s := y |_ theta - d f$ - -glq(k) := @(q k) _| s; -glv(k) := @(v k) _| s; -glt := @(t) _| s; - -% Translation in time must generate a symmetry. -xi(k) := 0; -tau := 1; - -glq k := glq k; -glv k := glv k; -glt; - -% The corresponding integral is of course the energy. -integ := - y _| theta; - - -clear l,lam k,gam,eta k,y,theta,s,glq k,glv k,glt,t,q k,v k,tau,xi k; -remfdomain r,f,tau,xi; - -% Problem: -% -------- -% Calculate the "gradient" and "Laplacian" of a function and the "curl" -% and "divergence" of a one-form in elliptic coordinates. - - -coframe e u = sqrt(cosh(v)**2 - sin(u)**2)*d u, - e v = sqrt(cosh(v)**2 - sin(u)**2)*d v, - e phi = cos u*sinh v*d phi; - -pform f=0; - -fdomain f=f(u,v,phi); - -factor e,^; -on rat,gcd; -order cosh v, sin u; -% The gradient: -d f; - -factor @; -% The Laplacian: -# d # d f; - -% Another way of calculating the Laplacian: --#vardf(1/2*d f^#d f,f); - -remfac @; - -% Now calculate the "curl" and the "divergence" of a one-form. - -pform w=1,a(k)=0; - -fdomain a=a(u,v,phi); - -w := a(-k)*e k; -% The curl: -x := # d w; - -factor @; -% The divergence: -y := # d # w; - - -remfac @; -clear x,y,w,u,v,phi,e k,a k; -remfdomain a,f; - - -% Problem: -% -------- -% Calculate in a spherical coordinate system the Navier Stokes equations. - -coframe e r=d r, e theta =r*d theta, e phi = r*sin theta *d phi; -frame x; - -fdomain v=v(t,r,theta,phi),p=p(r,theta,phi); - -pform v(k)=0,p=0,w=1; - -% We first calculate the convective derivative. - -w := v(-k)*e(k)$ - -factor e; on rat; - -cdv := @(w,t) + (v(k)*x(-k)) |_ w - 1/2*d(v(k)*v(-k)); - -%next we calculate the viscous terms; - -visc := nu*(d#d# w - #d#d w) + mu*d#d# w; - -% Finally we add the pressure term and print the components of the -% whole equation. - -pform nasteq=1,nast(k)=0; - -nasteq := cdv - visc + 1/rho*d p$ - -factor @; - -nast(-k) := x(-k) _| nasteq; - -remfac @,e; - -clear v k,x k,nast k,cdv,visc,p,w,nasteq,e k; -remfdomain p,v; - - -% Problem: -% -------- -% Calculate from the Lagrangian of a vibrating rod the equation of -% motion and show that the invariance under time translation leads -% to a conserved current. - -pform {y,x,t,q,j}=0,lagr=2; - -fdomain y=y(x,t),q=q(x),j=j(x); - -factor ^; - -lagr := 1/2*(rho*q*@(y,t)**2 - e*j*@(y,x,x)**2)*d x^d t; - -vardf(lagr,y); - -% The Lagrangian does not explicitly depend on time; therefore the -% vector field @ t generates a symmetry. The conserved current is - -pform c=1; -factor d; - -c := noether(lagr,y,@ t); - -% The exterior derivative of this must be zero or a multiple of the -% equation of motion (weak conservation law) to be a conserved current. - -remfac d; - -d c; - -% i.e. it is a multiple of the equation of motion. - -clear lagr,c,j,y,q; -remfdomain y,q,j; - -% Problem: -% -------- -% Show that the metric structure given by Eguchi and Hanson induces a -% self-dual curvature. -% c.f. T. Eguchi, P.B. Gilkey, A.J. Hanson, "Gravitation, Gauge Theories -% and Differential Geometry", Physics Reports 66, 213, 1980 - -for all x let cos(x)**2=1-sin(x)**2; - -pform f=0,g=0; -fdomain f=f(r), g=g(r); - -coframe o(r) = f*d r, - o(theta) = (r/2)*(sin(psi)*d theta - sin(theta)*cos(psi)*d phi), - o(phi) = (r/2)*(-cos(psi)*d theta - sin(theta)*sin(psi)*d phi), - o(psi) = (r/2)*g*(d psi + cos(theta)*d phi); - -frame e; - - -pform gamma(a,b)=1,curv2(a,b)=2; -index_symmetries gamma(a,b),curv2(a,b): antisymmetric; - -factor o; - -gamma(-a,-b) := -(1/2)*( e(-a) _| (e(-c) _| (d o(-b))) - -e(-b) _| (e(-a) _| (d o(-c))) - +e(-c) _| (e(-b) _| (d o(-a))) )*o(c)$ - - -curv2(-a,b) := d gamma(-a,b) + gamma(-c,b)^gamma(-a,c)$ - -let f=1/g,g=sqrt(1-(a/r)**4); - -pform chck(k,l)=2; -index_symmetries chck(k,l): antisymmetric; - -% The following has to be zero for a self-dual curvature. - -chck(k,l) := 1/2*eps(k,l,m,n)*curv2(-m,-n) + curv2(k,l); - -clear gamma(a,b),curv2(a,b),f,g,chck(a,b),o(k),e(k),r,phi,psi; -remfdomain f,g; - -% Example: 6-dimensional FRW model with quadratic curvature terms in -% ------- -% the Lagrangian (Lanczos and Gauss-Bonnet terms). -% cf. Henriques, Nuclear Physics, B277, 621 (1986) - -for all x let cos(x)**2+sin(x)**2=1; - -pform {r,s}=0; -fdomain r=r(t),s=s(t); - -coframe o(t) = d t, - o(1) = r*d u/(1 + k*(u**2)/4), - o(2) = r*u*d theta/(1 + k*(u**2)/4), - o(3) = r*u*sin(theta)*d phi/(1 + k*(u**2)/4), - o(4) = s*d v1, - o(5) = s*sin(v1)*d v2 - with metric g =-o(t)*o(t)+o(1)*o(1)+o(2)*o(2)+o(3)*o(3) - +o(4)*o(4)+o(5)*o(5); - -frame e; - -on nero; factor o,^; - -riemannconx om; - -pform curv(k,l)=2,{riemann(a,b,c,d),ricci(a,b),riccisc}=0; - -index_symmetries curv(k,l): antisymmetric, - riemann(k,l,m,n): antisymmetric in {k,l},{m,n} - symmetric in {{k,l},{m,n}}, - ricci(k,l): symmetric; - -curv(k,l) := d om(k,l) + om(k,-m)^om(m,l); - -riemann(a,b,c,d) := e(d) _| (e (c) _| curv(a,b)); - -% The rest is done in the Ricci calculus language, - -ricci(-a,-b) := riemann(c,-a,-d,-b)*g(-c,d); - -riccisc := ricci(-a,-b)*g(a,b); - -pform {laglanc,inv1,inv2} = 0; - -index_symmetries riemc3(k,l),riemri(k,l), - hlang(k,l),einst(k,l): symmetric; - -pform {riemc3(i,j),riemri(i,j)}=0; - -riemc3(-i,-j) := riemann(-i,-k,-l,-m)*riemann(-j,k,l,m)$ -inv1 := riemc3(-i,-j)*g(i,j); -riemri(-i,-j) := 2*riemann(-i,-k,-j,-l)*ricci(k,l)$ -inv2 := ricci(-a,-b)*ricci(a,b); -laglanc := (1/2)*(inv1 - 4*inv2 + riccisc**2); - - -pform {einst(a,b),hlang(a,b)}=0; - -hlang(-i,-j) := 2*(riemc3(-i,-j) - riemri(-i,-j) - - 2*ricci(-i,-k)*ricci(-j,K) + - riccisc*ricci(-i,-j) - (1/2)*laglanc*g(-i,-j)); - -% The complete Einstein tensor: - -einst(-i,-j) := (ricci(-i,-j) - (1/2)*riccisc*g(-i,-j))*alp1 + - hlang(-i,-j)*alp2$ - -alp1 := 1$ -factor alp2; - -einst(-i,-j) := einst(-i,-j); - -clear o(k),e(k),riemc3(i,j),riemri(i,j),curv(k,l),riemann(a,b,c,d), - ricci(a,b),riccisc,t,u,v1,v2,theta,phi,r,om(k,l),einst(a,b), - hlang(a,b); - -remfdomain r,s; - -% Problem: -% -------- -% Calculate for a given coframe and given torsion the Riemannian part and -% the torsion induced part of the connection. Calculate the curvature. - -% For a more elaborate example see E.Schruefer, F.W. Hehl, J.D. McCrea, -% "Application of the REDUCE package EXCALC to the Poincare gauge field -% theory of gravity", GRG Journal, vol. 19, (1988) 197--218 - -pform {ff, gg}=0; - -fdomain ff=ff(r), gg=gg(r); - -coframe o(4) = d u + 2*b0*cos(theta)*d phi, - o(1) = ff*(d u + 2*b0*cos(theta)*d phi) + d r, - o(2) = gg*d theta, - o(3) = gg*sin(theta)*d phi - with metric g = -o(4)*o(1)-o(4)*o(1)+o(2)*o(2)+o(3)*o(3); - -frame e; - -pform {tor(a),gwt(a)}=2,gamma(a,b)=1, - {u1,u3,u5}=0; - -index_symmetries gamma(a,b): antisymmetric; - -fdomain u1=u1(r),u3=u3(r),u5=u5(r); - -tor(4) := 0$ - -tor(1) := -u5*o(4)^o(1) - 2*u3*o(2)^o(3)$ - -tor(2) := u1*o(4)^o(2) + u3*o(4)^o(3)$ - -tor(3) := u1*o(4)^o(3) - u3*o(4)^o(2)$ - -gwt(-a) := d o(-a) - tor(-a)$ - -% The following is the combined connection. -% The Riemannian part could have equally well been calculated by the -% RIEMANNCONX statement. - -gamma(-a,-b) := (1/2)*( e(-b) _| (e(-c) _| gwt(-a)) - +e(-c) _| (e(-a) _| gwt(-b)) - -e(-a) _| (e(-b) _| gwt(-c)) )*o(c); - -pform curv(a,b)=2; -index_symmetries curv(a,b): antisymmetric; -factor ^; - -curv(-a,b) := d gamma(-a,b) + gamma(-c,b)^gamma(-a,c); - -clear o(k),e(k),curv(a,b),gamma(a,b),theta,phi,x,y,z,r,s,t,u,v,p,q,c,cs; -remfdomain u1,u3,u5,ff,gg; - -showtime; -end; - -\end{verbatim} -} -\end{document} +\documentstyle[11pt,reduce]{article} +\title{EXCALC: A System for Doing Calculations in the Calculus of Modern +Differential Geometry} +\author{Eberhard Schr\"{u}fer \\ +Institute SCAI.Alg \\ +German National Research Center for Information Technology (GMD) \\ +Schloss Birlinghoven \\ +D-53754 Sankt Augustin \\ +Germany \\[0.05in] +Email: schruefer@gmd.de} +\begin{document} +\maketitle + +\index{EXCALC package} + +\section*{Acknowledgments} + +This program was developed over several years. I would like to express +my deep gratitude to Dr. Anthony Hearn for his continuous interest in +this work, and especially for his hospitality and support during a +visit in 1984/85 at the RAND Corporation, where substantial progress +on this package could be achieved. The Heinrich Hertz-Stiftung +supported this visit. Many thanks are also due to Drs. F.W. Hehl, +University of Cologne, and J.D. McCrea, University College Dublin, for +their suggestions and work on testing this program. + +\section{Introduction} + +\index{differential geometry} +{\bf EXCALC} is designed for easy use by all who are familiar with the +calculus of Modern Differential Geometry. Its syntax is kept as close +as possible to standard textbook notations. Therefore, no great +experience in writing computer algebra programs is required. It is +almost possible to input to the computer the same as what would have +been written down for a hand-calculation. For example, the statement + +\begin{verbatim} + f*x^y + u _| (y^z^x) +\end{verbatim} + +\index{exterior calculus} +would be recognized by the program as a formula involving exterior +products and an inner product. The program is currently able to +handle scalar-valued exterior forms, vectors and operations between +them, as well as non-scalar valued forms (indexed forms). With this, +it should be an ideal tool for studying differential equations, +doing calculations in general relativity and field theories, or doing +such simple things as calculating the Laplacian of a tensor field for +an arbitrary given frame. With the increasing popularity of this +calculus, this program should have an application in almost any field +of physics and mathematics. + +Since the program is completely embedded in {\REDUCE}, all features and +facilities of {\REDUCE} are available in a calculation. Even for those +who are not quite comfortable in this calculus, there is a good chance +of learning it by just playing with the program. + +This is the last release of version 2. A much extended differential +geometry package (which includes complete symbolic index simplification, +tensors, mappings, bundles and others) is under development. + +Complaints and comments are appreciated and should be send to the author. +If the use of this program leads to a publication, this document should +be cited, and a copy of the article to the above address would be +welcome. + +\section{Declarations} + +Geometrical objects like exterior forms or vectors are introduced to the +system by declaration commands. The declarations can appear anywhere in +a program, but must, of course, be made prior to the use of the object. +Everything that has no declaration is treated as a constant; therefore +zero-forms must also be declared. + +An exterior form is introduced by\label{PFORM} \index{PFORM statement} +\index{exterior form ! declaration} + +\hspace*{2em} \k{PFORM} \s{declaration$_1$}, \s{declaration$_2$}, \ldots; + +where + +\begin{tabbing} +\s{declaration} ::= \s{name} $\mid$ \s{list of names}=\s{number} $\mid$ \s{identifier} $\mid$ \\ +\s{expression} \\ +\s{name} ::= \s{identifier} $\mid$ \s{identifier}(\s{arguments}) +\end{tabbing} + +For example + +\begin{verbatim} + pform u=k,v=4,f=0,w=dim-1; +\end{verbatim} + +declares {\tt U} to be an exterior form of degree {\tt K}, {\tt V} to be a +form of degree 4, {\tt F} to be a form of degree 0 (a function), and {\tt W} +to be a form of degree {\tt DIM}-1. + +If the exterior form should have indices, the declaration would be +\index{exterior form ! with indices} + +\begin{verbatim} + pform curv(a,b)=2,chris(a,b)=1; +\end{verbatim} + +The names of the indices are arbitrary. + +Exterior forms of the same degree can be grouped into lists to save typing. + +\begin{verbatim} + pform {x,y,z}=0,{rho(k,l),u,v(k)}=1; +\end{verbatim} + +The declaration of vectors is similar. The command {\tt TVECTOR}\label{TVECTOR} +takes a list of names. \index{TVECTOR command} \index{exterior form ! vector} + +\hspace*{2em} \k{TVECTOR} \s{name$_1$}, \s{name$_2$}, \ldots; + +For example, to declare {\tt X} as a vector and {\tt COMM} as a vector with +two indices, one would say + +\begin{verbatim} + tvector x,comm(a,b); +\end{verbatim} + +If a declaration of an already existing name is made, the old +declaration is removed, and the new one is taken. + +The exterior degree of a symbol or a general expression can be obtained +with the function \label{EXDEGREE} \index{EXDEGREE command} + +\hspace*{2em} \k{EXDEGREE} \s{expression}; + +Example: +\begin{verbatim} + exdegree(u + 3*chris(k,-k)); + + 1 +\end{verbatim} + + +\section{Exterior Multiplication} + +\index{"\^{} ! exterior multiplication} \index{exterior product} +Exterior multiplication between exterior forms is carried out with the +nary infix operator \^{ } (wedge)\label{wedge}. Factors are ordered +according to the usual ordering in {\REDUCE} using the commutation +rule for exterior products. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + pform u=1,v=1,w=k; + + u^v; + + U^V + + v^u; + + - U^V + + u^u; + + 0 + + w^u^v; + + K + ( - 1) *U^V^W + + (3*u-a*w)^(w+5*v)^u; + + A*(5*U^V^W - U^W^W) +\end{verbatim} + +It is possible to declare the dimension of the underlying space +by\label{SPACEDIM} \index{SPACEDIM command} \index{dimension} + +\hspace*{2em} \k{SPACEDIM} \s{number} $\mid$ \s{identifier}; + +If an exterior product has a degree higher than the dimension of the +space, it is replaced by 0: + +\begin{verbatim} + spacedim 4; + + pform u=2,v=3; + + u^v; + + 0 +\end{verbatim} + + +\section{Partial Differentiation} + +Partial differentiation is denoted by the operator {\tt @}\label{at}. Its +capability is the same as the {\REDUCE} {\tt DF} operator. +\index{"@ operator} \index{partial differentiation} +\index{differentiation ! partial} + +\example\index{EXCALC package ! example} + +\begin{verbatim} + @(sin x,x); + + COS(X) + + @(f,x); + + 0 +\end{verbatim} + +An identifier can be declared to be a function of certain variables. +\index{FDOMAIN command} +This is done with the command {\tt FDOMAIN}\label{FDOMAIN}. The +following would tell the partial differentiation operator that {\tt F} +is a function of the variables {\tt X} and {\tt Y} and that {\tt H} is +a function of {\tt X}. + +\begin{verbatim} + fdomain f=f(x,y),h=h(x); +\end{verbatim} + +Applying {\tt @} to {\tt F} and {\tt H} would result in + +\begin{verbatim} + @(x*f,x); + + F + X*@ F + X + + @(h,y); + + 0 +\end{verbatim} + +\index{tangent vector} +The partial derivative symbol can also be an operator with a single +argument. It then represents a natural base element of a tangent +vector\label{at1}. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + a*@ x + b*@ y; + + A*@ + B*@ + X Y +\end{verbatim} + +\section{Exterior Differentiation} +\index{exterior differentiation} +Exterior differentiation of exterior forms is carried out by the +operator {\tt d}\label{d}. Products are normally differentiated out, +{\em i.e.} + +\begin{verbatim} + pform x=0,y=k,z=m; + + d(x * y); + + X*d Y + d X^Y + + d(r*y); + + R*d Y + + d(x*y^z); + + K + ( - 1) *X*Y^d Z + X*d Y^Z + d X^Y^Z +\end{verbatim} + +This expansion can be suppressed by the command {\tt NOXPND D}\label{NOXPNDD}. +\index{NOXPND ! D} + +\begin{verbatim} + noxpnd d; + + d(y^z); + + d(Y^Z) +\end{verbatim} + +To obtain a canonical form for an exterior product when the expansion +is switched off, the operator {\tt D} is shifted to the right if it +appears in the leftmost place. + +\begin{verbatim} + d y ^ z; + + K + - ( - 1) *Y^d Z + d(Y^Z) +\end{verbatim} + +Expansion is performed again when the command {\tt XPND D}\label{XPNDD} +is executed. \index{XPND ! D} + +Functions which are implicitly defined by the {\tt FDOMAIN} command are +expanded into partial derivatives: + +\begin{verbatim} + pform x=0,y=0,z=0,f=0; + + fdomain f=f(x,y); + + d f; + + @ F*d X + @ F*d Y + X Y +\end{verbatim} + +If an argument of an implicitly defined function has further +dependencies the chain rule will be applied {\em e.g.} \index{chain rule} + + +\begin{verbatim} + fdomain y=y(z); + + d f; + + @ F*d X + @ F*@ Y*d Z + X Y Z +\end{verbatim} + +Expansion into partial derivatives can be inhibited by +{\tt NOXPND @}\label{NOXPNDA} +and enabled again by {\tt XPND @}\label{XPNDA}. +\index{NOXPND ! "@} \index{XPND ! "@} + +The operator is of course aware of the rules that a repeated +application always leads to zero and that there is no exterior form of +higher degree than the dimension of the space. + +\begin{verbatim} + d d x; + + 0 + + pform u=k; + spacedim k; + + d u; + + 0 +\end{verbatim} +\section{Inner Product} +\index{inner product ! exterior form} +The inner product between a vector and an exterior form is represented +by the diphthong \_$|$ \label{innerp} (underscore or-bar), which is the +notation of many textbooks. If the exterior form is an exterior +product, the inner product is carried through any factor. +\index{\_$\mid$ operator} + +\example\index{EXCALC package ! example} + +\begin{verbatim} + pform x=0,y=k,z=m; + + tvector u,v; + + u _| (x*y^z); + + K + X*(( - 1) *Y^U _| Z + U _| Y^Z) +\end{verbatim} + +In repeated applications of the inner product to the same exterior +form the vector arguments are ordered {\em e.g.} + +\begin{verbatim} + (u+x*v) _| (u _| (3*z)); + + - 3*U _| V _| Z +\end{verbatim} + +The duality of natural base elements is also known by the system, {\em i.e.} + +\begin{verbatim} + pform {x,y}=0; + + (a*@ x+b*@(y)) _| (3*d x-d y); + + 3*A - B +\end{verbatim} + +\section{Lie Derivative} + +\index{Lie Derivative} +The Lie derivative can be taken between a vector and an exterior form +or between two vectors. It is represented by the infix operator $|$\_ +\label{lie}. In the case of Lie differentiating, an exterior form by +a vector, the Lie derivative is expressed through inner products and +exterior differentiations, {\em i.e.} \index{$\mid$\_ operator} + +\begin{verbatim} + pform z=k; + + tvector u; + + u |_ z; + + U _| d Z + d(U _| Z) +\end{verbatim} + +If the arguments of the Lie derivative are vectors, the vectors are +ordered using the anticommutivity property, and functions (zero forms) +are differentiated out. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + tvector u,v; + + v |_ u; + + - U |_ V + + pform x=0,y=0; + + (x*u) |_ (y*v); + + - U*Y*V _| d X + V*X*U _| d Y + X*Y*U |_ V +\end{verbatim} + +\section{Hodge-* Duality Operator} + +\index{Hodge-* duality operator} \index{"\# ! Hodge-* operator} +The Hodge-*\label{hodge} duality operator maps an exterior form of degree +{\tt K} to an exterior form of degree {\tt N-K}, where {\tt N} is the +dimension of the space. The double application of the operator must +lead back to the original exterior form up to a factor. The following +example shows how the factor is chosen here + +\begin{verbatim} + spacedim n; + pform x=k; + + # # x; + + 2 + (K + K*N) + ( - 1) *X*SGN +\end{verbatim} +\pagebreak +\index{SGN ! indeterminate sign} \index{coframe} +The indeterminate SGN in the above example denotes the sign of the +determinant of the metric. It can be assigned a value or will be +automatically set if more of the metric structure is specified (via +COFRAME), {\em i.e.} it is then set to $g/|g|$, where $g$ is the +determinant of the metric. If the Hodge-* operator appears in an +exterior product of maximal degree as the leftmost factor, the Hodge-* +is shifted to the right according to + +\begin{verbatim} + pform {x,y}=k; + + # x ^ y; + + 2 + (K + K*N) + ( - 1) *X^# Y +\end{verbatim} + +More simplifications are performed if a coframe is defined. + + + +\section{Variational Derivative} + +\index{derivative ! variational} \index{variational derivative} +\ttindex{VARDF} +The function {\tt VARDF}\label{VARDF} returns as its value the +variation of a given Lagrangian n-form with respect to a specified +exterior form (a field of the Lagrangian). In the shared variable +\ttindex{BNDEQ"!*} +{\tt BNDEQ!*}, the expression is stored that has to yield zero if +integrated over the boundary. + +Syntax: + +\hspace*{2em} \k{VARDF}(\s{Lagrangian n-form},\s{exterior form}) + +\example\index{EXCALC package ! example} + +\begin{verbatim} + spacedim 4; + + pform l=4,a=1,j=3; + + l:=-1/2*d a ^ # d a - a^# j$ %Lagrangian of the e.m. field + + vardf(l,a); + + - (# J + d # d A) %Maxwell's equations + + bndeq!*; + + - 'A^# d A %Equation at the boundary +\end{verbatim} + +Restrictions: + +In the current implementation, the Lagrangian must be built up by the +fields and the operations {\tt d}, {\tt \#}, and {\tt @}. Variation +with respect to indexed quantities is currently not allowed. + +For the calculation of the conserved currents induced by symmetry +operators (vector fields), the function {\tt NOETHER}\label{NOETHER} +\index{NOETHER function} +is provided. It has the syntax: + +\hspace*{2em} +\k{NOETHER}(\s{Lagrangian n-form},\s{field},\s{symmetry generator}) + +\example\index{EXCALC package ! example} + +\begin{verbatim} + pform l=4,a=1,f=2; + + spacedim 4; + + l:= -1/2*d a^#d a; %Free Maxwell field; + + tvector x(k); %An unspecified generator; + + noether(l,a,x(-k)); + + ( - 2*d(X _|A)^# d A - (X _|d A)^# d A + d A^(X _|# d A))/2 + K K K +\end{verbatim} + +The above expression would be the canonical energy +momentum 3-forms of the Maxwell field, if X is interpreted +as a translation; + + + +\section{Handling of Indices} +\index{exterior form ! with indices} +Exterior forms and vectors may have indices. On input, the indices +are given as arguments of the object. A positive argument denotes a +superscript and a negative argument a subscript. On output, the +indexed quantity is displayed two dimensionally if {\tt NAT} is on. +\index{NAT flag} +Indices may be identifiers or numbers. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + pform om(k,l)=m,e(k)=1; + + e(k)^e(-l); + + K + E ^E + L + + om(4,-2); + + 4 + OM + 2 +\end{verbatim} + +In the current release, full simplification is performed only if an +index range is specified. It is hoped that this restriction can be +removed soon. If the index range (the values that the indices can +obtain) is specified, the given expression is evaluated for all +possible index values, and the summation convention is understood. + +\example\label{INDEXRANGE}\index{EXCALC package ! example} + +\begin{verbatim} + indexrange t,r,ph,z; + + pform e(k)=1,s(k,l)=2; + + w := e(k)*e(-k); + + T R PH Z + W := E *E + E *E + E *E + E *E + T R PH Z + + + s(k,l):=e(k)^e(l); + + T T + S := 0 + + R T T R + S := - E ^E + + PH T T PH + S := - E ^E + + . + . + . + +\end{verbatim} + +If the expression to be evaluated is not an assignment, the values of +the expression are displayed as an assignment to an indexed variable +with name {\tt NS}. This is done only on output, {\em i.e.} no actual +binding to the variable NS occurs. +\index{NS dummy variable} + +\begin{verbatim} + e(k)^e(l); + + T T + NS := 0 + + R T T R + NS := - E ^E + . + . + . +\end{verbatim} + +It should be noted, however, that the index positions on the variable +NS can sometimes not be uniquely determined by the system (because of +possible reorderings in the expression). Generally it is advisable to +use assignments to display complicated expressions. + +A range can also be assigned to individual index-names. For example, +the declaration + +\begin{verbatim} + indexrange {k,l}={x,y,z},{u,v,w}={1,2}; +\end{verbatim} + +would assign to the index identifiers k,l the range values x,y,z and +to the index identifiers u,v,w the range values 1,2. The use of an +index identifier not listed in previous indexrange statements has the +range of the union of all given index ranges. + +With the above example of an indexrange statement, the following +index evaluations would take place + +\begin{verbatim} + pform w n=0; + + w(k)*w(-k); + + X Y Z + W *W + W *W + W *W + X Y Z + + w(u)*w(-u); + + 1 2 + W *W + W *W + 1 2 + + w(r)*w(-r); + + 1 2 X Y Z + W *W + W *W + W *W + W *W + W *W + 1 2 X Y Z +\end{verbatim} + +In certain cases, one would like to inhibit the summation over +specified index names, or at all. For this the command + +\index{NOSUM command} +\hspace*{2em} \k{NOSUM} \s{indexname$_1$}, \ldots;\label{NOSUM} + +and the switch {\tt NOSUM} are \index{NOSUM switch} +available. The command {\tt NOSUM} has the effect that summation is +not performed over those indices which had been listed. The command +{\tt RENOSUM}\label{RENOSUM} enables summation again. The switch {\tt +NOSUM}, if on, inhibits any summation. \index{RENOSUM command} + +\label{INDEXSYMMETRIES} \index{INDEXSYMMETRIES command} +It is possible to declare symmetry properties for an indexed quantity by +the command {\tt INDEX\_SYMMETRIES}. A prototypical example is as +follows + +\begin{verbatim} + + index_symmetries u(k,l,m,n): symmetric in {k,l},{m,n} + antisymmetric in {{k,l},{m,n}}, + g(k,l),h(k,l): symmetric; + +\end{verbatim} + +It declares the object {\tt u} symmetric in the first two and last +two indices and antisymmetric with respect to commutation of the given +index pairs. If an object is completely symmetric or antisymmetric, +the indices need not to be given after the corresponding keyword as +shown above for {\tt g} and {\tt h}. + +If applicable, this command should +be issued, since great savings in memory and execution time result. +Only strict components are printed. + +The commands symmetric and antisymmetric of earlier releases have no +effect. + + +\section{Metric Structures} + +\index{metric structure} \index{coframe} +A metric structure is defined in {\bf EXCALC} by specifying a set of +basis one-forms (the coframe) together with the metric. + +Syntax:\label{COFRAME} + +\begin{tabbing} +\hspace*{2em} \k{COFRAME} \= +\s{identifier}\s{(index$_1$)}=\s{expression$_1$}, \\ +\> \s{identifier}\s{(index$_2$)}=\s{expression$_2$}, \\ +\> . \\ +\> . \\ +\> . \\ +\> \s{identifier}\s{(index$_n$)}=\s{expression$_n$} \\ +\> \hspace{1em} \k{WITH} \k{METRIC} \s{name}=\s{expression}; \\ +\end{tabbing} + +\index{euclidean metric} \index{COFRAME ! WITH METRIC} +This statement automatically sets the dimension of the space and the +index range. The clause {\tt WITH METRIC} can be omitted if the metric +\index{COFRAME ! WITH SIGNATURE} +is Euclidean and the shorthand {\tt WITH SIGNATURE \s{diagonal elements}} +\label{SIGNATURE} can be used in the case of a pseudo-Euclidean metric. The +splitting of a metric structure in its metric tensor coefficients and +basis one-forms is completely arbitrary including the extremes of an +orthonormal frame and a coordinate frame. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + coframe e r=d r, e(ph)=r*d ph + with metric g=e(r)*e(r)+e(ph)*e(ph); %Polar coframe + + coframe e(r)=d r,e(ph)=r*d(ph); %Same as before + + coframe o(t)=d t, o x=d x + with signature -1,1; %A Lorentz coframe + + coframe b(xi)=d xi, b(eta)=d eta %A lightcone coframe + with metric w=-1/2*(b(xi)*b(eta)+b(eta)*b(xi)); + + coframe e r=d r, e ph=d ph %Polar coordinate + with metric g=e r*e r+r**2*e ph*e ph; %basis + +\end{verbatim} + +Individual elements of the metric can be accessed just by calling them +with the desired indices. The value of the determinant of the +\index{determinant ! in DETM"!*} \ttindex{DETM"!*} +covariant metric is stored in the variable {\tt DETM!*}. The metric +is not needed for lowering or raising of indices as the system +performs this automatically, {\em i.e.} no matter in what index +position values were assigned to an indexed quantity, the values can +be retrieved for any index position just by writing the indexed +quantity with the desired indices. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + coframe e t=d t,e x=d x,e y=d y + with signature -1,1,1; + + pform f(k,l)=0; + + antisymmetric f; + + f(-t,-x):=ex$ f(-x,-y):=b$ f(-t,-y):=0$ + on nero; + + f(k,-l):=f(k,-l); + + X + F := - EX + T + + T + F := - EX + X + + Y + F := - B + X + + X + F := B + Y +\end{verbatim} + +Any expression containing differentials of the coordinate functions will +be transformed into an expression of the basis one-forms.The system also +knows how to take the exterior derivative of the basis one-forms. + +\index{spherical coordinates} +\example (Spherical coordinates)\index{EXCALC package ! example} + +\begin{verbatim} + coframe e(r)=d(r), e(th)=r*d(th), e(ph)=r*sin(th)*d(ph); + + d r^d th; + + R TH + (E ^E )/R + + d(e(th)); + + R TH + (E ^E )/R + + + pform f=0; + + fdomain f=f(r,th,ph); + + factor e; + + on rat; + + d f; %The "gradient" of F in spherical coordinates; + + R TH PH + E *@ F + (E *@ F)/R + (E *@ F)/(R*SIN(TH)) + R TH PH +\end{verbatim} + +The frame dual to the frame defined by the {\tt COFRAME} command can +be introduced by \k{FRAME} command. \index{FRAME command} + +\hspace*{2em} \k{FRAME} \s{identifier};\label{FRAME} + +This command causes the +dual property to be recognized, and the tangent vectors of the +coordinate functions are replaced by the frame basis vectors. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + coframe b r=d r,b ph=r*d ph,e z=d z; %Cylindrical coframe; + + frame x; + + on nero; + + x(-k) _| b(l); + + R + NS := 1 + R + + PH + NS := 1 + PH + + Z + NS := 1 + Z + + x(-k) |_ x(-l); %The commutator of the dual frame; + + + NS := X /R + PH R PH + + + NS := ( - X )/R %i.e. it is not a coordinate base; + R PH PH + +\end{verbatim} + +\index{DISPLAYFRAME command} \index{tracing ! EXCALC} +As a convenience, the frames can be displayed at any point in a program +by the command {\tt DISPLAYFRAME;}\label{DISPLAYFRAME}. + +\index{Hodge-* duality operator} +The Hodge-* duality operator returns the explicitly constructed dual +element if applied to coframe base elements. The metric is properly +taken into account. + +\index{Levi-Cevita tensor} \ttindex{EPS} +The total antisymmetric Levi-Cevita tensor {\tt EPS}\label{EPS} is +also available. The value of {\tt EPS} with an even permutation of the +indices in a covariant position is taken to be +1. + + +\section{Riemannian Connections} + +\index{Riemannian Connections} +The command {\tt RIEMANNCONX} is provided for calculating the +\index{RIEMANNCONX command} \label{RIEMANNCONX} +connection 1 forms. The values are stored on the name given to {\tt +RIEMANNCONX}. This command is far more efficient than calculating the +connection from the differential of the basis one-forms and using +inner products. + +\example (Calculate the connection 1-form and curvature 2-form on S(2)) +\index{EXCALC package ! example} + +\begin{verbatim} + coframe e th=r*d th,e ph=r*sin(th)*d ph; + + riemannconx om; + + om(k,-l); %Display the connection forms; + + TH + NS := 0 + TH + + PH PH + NS := (E *COS(TH))/(SIN(TH)*R) + TH + + TH PH + NS := ( - E *COS(TH))/(SIN(TH)*R) + PH + + PH + NS := 0 + PH + + pform curv(k,l)=2; + + + curv(k,-l):=d om(k,-l) + om(k,-m)^om(m-l); + %The curvature forms + + TH + CURV := 0 + TH + + PH TH PH 2 + CURV := ( - E ^E )/R + TH %Of course it was a sphere with + %radius R. + + TH TH PH 2 + CURV := (E ^E )/R + PH + + PH + CURV := 0 + PH +\end{verbatim} + +\section{Ordering and Structuring} + +\index{ordering ! exterior form} \index{FORDER command} +The ordering of an exterior form or vector can be changed by the +command {\tt FORDER}.\label{FORDER} In an expression, the first +identifier or kernel in the arguments of {\tt FORDER} is ordered ahead +of the second, and so on, and ordered ahead of all not appearing as +arguments. This ordering is done on the internal level and not only +on output. The execution of this statement can therefore have +tremendous effects on computation time and memory requirements. {\tt +REMFORDER}\label{REMFORDER} brings back standard ordering for those +elements that are listed as arguments. \index{REMFORDER command} + +An expression can be put in a more structured form by renaming a +subexpression. This is done with the command {\tt KEEP} which +has the syntax \index{KEEP command}\label{KEEP} + +\hspace*{2em} \k{KEEP} +\s{name$_1$}=\s{expression$_1$},\s{name$_2$}=\s{expression$_2$}, \ldots + +The effect is that rules are set up for simplifying \s{name} without +introducing its definition in an expression. In an expression the system +also tries by reordering to generate as many instances of \s{name} as +possible. + +\example\index{EXCALC package ! example} + +\begin{verbatim} + pform x=0,y=0,z=0,f=0,j=3; + + keep j=d x^d y^d z; + + j; + + J + + d j; + + 0 + + j^d x; + + 0 + + fdomain f=f(x); + + d f^d y^d z; + + @ F*J + X +\end{verbatim} + +\index{exterior product} +The capabilities of {\tt KEEP} are currently very limited. Only exterior +products should occur as righthand sides in {\tt KEEP}. + + +\section{Summary of Operators and Commands} +Table~\ref{EXCALC:sum} summarizes EXCALC commands and the page number they are +defined on. + +\begin{table} +\begin{tabular}{l l r} +\index{"\^{} ! exterior multiplication} \index{wedge} +\^{ } & Exterior Multiplication & \pageref{wedge} \\ +\index{"@ ! partial differentiation} +@ & Partial Differentiation & \pageref{at} \\ +\index{"@ ! tangent vector} +@ & Tangent Vector & \pageref{at1} \\ +\index{"\# ! Hodge-* operator} +\# & Hodge-* Operator & \pageref{hodge} \\ +\index{\_$\mid$ operator} +\_$|$ & Inner Product & \pageref{innerp} \\ +\index{$\mid$\_ operator} +$|$\_ & Lie Derivative & \pageref{lie} \\ +\index{COFRAME command} +COFRAME & Declaration of a coframe & \pageref{COFRAME} \\ +\index{d ! exterior differentiation} +d & Exterior differentiation & \pageref{d} \\ +\index{DISPLAYFRAME command} +DISPLAYFRAME & Displays the frame & \pageref{DISPLAYFRAME}\\ +\index{EPS ! Levi-Civita tensor} +EPS & Levi-Civita tensor & \pageref{EPS} \\ +\index{EXDEGREE} +EXDEGREE & Calculates the exterior degree of an expression & \pageref{EXDEGREE} \\ +\index{FDOMAIN command} +FDOMAIN & Declaration of implicit dependencies &\pageref{FDOMAIN} \\ +\index{FORDER command} +FORDER & Ordering command & \pageref{FORDER} \\ +\index{FRAME command} +FRAME & Declares the frame dual to the coframe & \pageref{FRAME} \\ +\index{INDEXRANGE command} +INDEXRANGE & Declaration of indices & \pageref{INDEXRANGE} \\ +\index{INDEX\_SYMMETRIES command} +INDEX\_SYMMETRIES & Declares arbitrary index symmetry properties & \pageref{INDEXSYMMETRIES} \\ +\index{KEEP command} +KEEP & Structuring command & \pageref{KEEP} \\ +\index{METRIC command} +METRIC & Clause of COFRAME to specify a metric & \pageref{COFRAME} \\ +\index{NOETHER function} +NOETHER & Calculates the Noether current & \pageref{NOETHER} \\ +\index{NOSUM command} +NOSUM & Inhibits summation convention & \pageref{NOSUM} \\ +\index{NOXPND command} +NOXPND d & Inhibits the use of product rule for d & +\pageref{NOXPNDD} \\ +\index{NOXPND "@ command} +NOXPND @ & Inhibits expansion into partial derivatives & +\pageref{NOXPNDA} \\ +\index{PFORM command} +PFORM & Declaration of exterior forms & \pageref{PFORM} \\ +\index{REMFORDER command} +REMFORDER & Clears ordering & \pageref{REMFORDER} \\ +\index{RENOSUM command} +RENOSUM & Enables summation convention & \pageref{RENOSUM} \\ +\index{RIEMANNCONX command} +RIEMANNCONX & Calculation of a Riemannian Connection & +\pageref{RIEMANNCONX} \\ +\index{SIGNATURE command} +SIGNATURE & Clause of COFRAME to specify a pseudo- & \pageref{SIGNATURE} \\ + & Euclidean metric & \\ +\index{SPACEDIM command} +SPACEDIM & Command to set the dimension of a space & +\pageref{SPACEDIM} \\ +\index{TVECTOR command} +TVECTOR & Declaration of vectors & \pageref{TVECTOR} \\ +\ttindex{VARDF} +VARDF & Variational derivative & \pageref{VARDF} \\ +\index{XPND command} +XPND d & Enables the use of product rule for d & \pageref{XPNDD} \\ + & (default) & \\ +\index{XPND ! "@} +XPND @ & Enables expansion into partial derivatives & \pageref{XPNDA} \\ + & (default) +\end{tabular} +\caption{EXCALC Command Summary}\label{EXCALC:sum} +\end{table} +\newpage +\section{Examples} + +The following examples should illustrate the use of {\bf EXCALC}. It is not +intended to show the most efficient or most elegant way of stating the +problems; rather the variety of syntactic constructs are exemplified. +The examples are on a test file distributed with {\bf EXCALC}. +\index{EXCALC package ! example} +{\small +\begin{verbatim} + +% Problem: Calculate the PDE's for the isovector of the heat equation. +% -------- +% (c.f. B.K. Harrison, f.B. Estabrook, "Geometric Approach...", +% J. Math. Phys. 12, 653, 1971) + +% The heat equation @ psi = @ psi is equivalent to the set of exterior +% xx t + +% equations (with u=@ psi, y=@ psi): +% T x + + +pform {psi,u,x,y,t}=0,a=1,{da,b}=2; + +a := d psi - u*d t - y*d x; + +da := - d u^d t - d y^d x; + +b := u*d x^d t - d y^d t; + + +% Now calculate the PDE's for the isovector. + +tvector v; + +pform {vpsi,vt,vu,vx,vy}=0; +fdomain vpsi=vpsi(psi,t,u,x,y),vt=vt(psi,t,u,x,y),vu=vu(psi,t,u,x,y), + vx=vx(psi,t,u,x,y),vy=vy(psi,t,u,x,y); + +v := vpsi*@ psi + vt*@ t + vu*@ u + vx*@ x + vy*@ y; + + +factor d; +on rat; + +i1 := v |_ a - l*a; + +pform o=1; + +o := ot*d t + ox*d x + ou*d u + oy*d y; + +fdomain f=f(psi,t,u,x,y); + +i11 := v _| d a - l*a + d f; + +let vx=-@(f,y),vt=-@(f,u),vu=@(f,t)+u*@(f,psi),vy=@(f,x)+y*@(f,psi), + vpsi=f-u*@(f,u)-y*@(f,y); + +factor ^; + +i2 := v |_ b - xi*b - o^a + zeta*da; + +let ou=0,oy=@(f,u,psi),ox=-u*@(f,u,psi), + ot=@(f,x,psi)+u*@(f,y,psi)+y*@(f,psi,psi); + +i2; + +let zeta=-@(f,u,x)-@(f,u,y)*u-@(f,u,psi)*y; + +i2; + +let xi=-@(f,t,u)-u*@(f,u,psi)+@(f,x,y)+u*@(f,y,y)+y*@(f,y,psi)+@(f,psi); + +i2; + +let @(f,u,u)=0; + +i2; % These PDE's have to be solved. + + +clear a,da,b,v,i1,i11,o,i2,xi,t; +remfdomain f,vpsi,vt,vu,vx,vy; +clear @(f,u,u); + + +% Problem: +% -------- +% Calculate the integrability conditions for the system of PDE's: +% (c.f. B.F. Schutz, "Geometrical Methods of Mathematical Physics" +% Cambridge University Press, 1984, p. 156) + + +% @ z /@ x + a1*z + b1*z = c1 +% 1 1 2 + +% @ z /@ y + a2*z + b2*z = c2 +% 1 1 2 + +% @ z /@ x + f1*z + g1*z = h1 +% 2 1 2 + +% @ z /@ y + f2*z + g2*z = h2 +% 2 1 2 ; + + +pform w(k)=1,integ(k)=4,{z(k),x,y}=0,{a,b,c,f,g,h}=1, + {a1,a2,b1,b2,c1,c2,f1,f2,g1,g2,h1,h2}=0; + +fdomain a1=a1(x,y),a2=a2(x,y),b1=b1(x,y),b2=b2(x,y), + c1=c1(x,y),c2=c2(x,y),f1=f1(x,y),f2=f2(x,y), + g1=g1(x,y),g2=g2(x,y),h1=h1(x,y),h2=h2(x,y); + + +a:=a1*d x+a2*d y$ +b:=b1*d x+b2*d y$ +c:=c1*d x+c2*d y$ +f:=f1*d x+f2*d y$ +g:=g1*d x+g2*d y$ +h:=h1*d x+h2*d y$ + +% The equivalent exterior system: +factor d; +w(1) := d z(-1) + z(-1)*a + z(-2)*b - c; +w(2) := d z(-2) + z(-1)*f + z(-2)*g - h; +indexrange 1,2; +factor z; +% The integrability conditions: + +integ(k) := d w(k) ^ w(1) ^ w(2); + +clear a,b,c,f,g,h,x,y,w(k),integ(k),z(k); +remfdomain a1,a2,b1,c1,c2,f1,f2,g1,g2,h1,h2; + +% Problem: +% -------- +% Calculate the PDE's for the generators of the d-theta symmetries of +% the Lagrangian system of the planar Kepler problem. +% c.f. W.Sarlet, F.Cantrijn, Siam Review 23, 467, 1981 +% Verify that time translation is a d-theta symmetry and calculate the +% corresponding integral. + +pform {t,q(k),v(k),lam(k),tau,xi(k),eta(k)}=0,theta=1,f=0, + {l,glq(k),glv(k),glt}=0; + +tvector gam,y; + +indexrange 1,2; + +fdomain tau=tau(t,q(k),v(k)),xi=xi(t,q(k),v(k)),f=f(t,q(k),v(k)); + +l := 1/2*(v(1)**2 + v(2)**2) + m/r$ % The Lagrangian. + +pform r=0; +fdomain r=r(q(k)); +let @(r,q 1)=q(1)/r,@(r,q 2)=q(2)/r,q(1)**2+q(2)**2=r**2; + +lam(k) := -m*q(k)/r; % The force. + +gam := @ t + v(k)*@(q(k)) + lam(k)*@(v(k))$ + +eta(k) := gam _| d xi(k) - v(k)*gam _| d tau$ + +y := tau*@ t + xi(k)*@(q(k)) + eta(k)*@(v(k))$ % Symmetry generator. + +theta := l*d t + @(l,v(k))*(d q(k) - v(k)*d t)$ + +factor @; + +s := y |_ theta - d f$ + +glq(k) := @(q k) _| s; +glv(k) := @(v k) _| s; +glt := @(t) _| s; + +% Translation in time must generate a symmetry. +xi(k) := 0; +tau := 1; + +glq k := glq k; +glv k := glv k; +glt; + +% The corresponding integral is of course the energy. +integ := - y _| theta; + + +clear l,lam k,gam,eta k,y,theta,s,glq k,glv k,glt,t,q k,v k,tau,xi k; +remfdomain r,f,tau,xi; + +% Problem: +% -------- +% Calculate the "gradient" and "Laplacian" of a function and the "curl" +% and "divergence" of a one-form in elliptic coordinates. + + +coframe e u = sqrt(cosh(v)**2 - sin(u)**2)*d u, + e v = sqrt(cosh(v)**2 - sin(u)**2)*d v, + e phi = cos u*sinh v*d phi; + +pform f=0; + +fdomain f=f(u,v,phi); + +factor e,^; +on rat,gcd; +order cosh v, sin u; +% The gradient: +d f; + +factor @; +% The Laplacian: +# d # d f; + +% Another way of calculating the Laplacian: +-#vardf(1/2*d f^#d f,f); + +remfac @; + +% Now calculate the "curl" and the "divergence" of a one-form. + +pform w=1,a(k)=0; + +fdomain a=a(u,v,phi); + +w := a(-k)*e k; +% The curl: +x := # d w; + +factor @; +% The divergence: +y := # d # w; + + +remfac @; +clear x,y,w,u,v,phi,e k,a k; +remfdomain a,f; + + +% Problem: +% -------- +% Calculate in a spherical coordinate system the Navier Stokes equations. + +coframe e r=d r, e theta =r*d theta, e phi = r*sin theta *d phi; +frame x; + +fdomain v=v(t,r,theta,phi),p=p(r,theta,phi); + +pform v(k)=0,p=0,w=1; + +% We first calculate the convective derivative. + +w := v(-k)*e(k)$ + +factor e; on rat; + +cdv := @(w,t) + (v(k)*x(-k)) |_ w - 1/2*d(v(k)*v(-k)); + +%next we calculate the viscous terms; + +visc := nu*(d#d# w - #d#d w) + mu*d#d# w; + +% Finally we add the pressure term and print the components of the +% whole equation. + +pform nasteq=1,nast(k)=0; + +nasteq := cdv - visc + 1/rho*d p$ + +factor @; + +nast(-k) := x(-k) _| nasteq; + +remfac @,e; + +clear v k,x k,nast k,cdv,visc,p,w,nasteq,e k; +remfdomain p,v; + + +% Problem: +% -------- +% Calculate from the Lagrangian of a vibrating rod the equation of +% motion and show that the invariance under time translation leads +% to a conserved current. + +pform {y,x,t,q,j}=0,lagr=2; + +fdomain y=y(x,t),q=q(x),j=j(x); + +factor ^; + +lagr := 1/2*(rho*q*@(y,t)**2 - e*j*@(y,x,x)**2)*d x^d t; + +vardf(lagr,y); + +% The Lagrangian does not explicitly depend on time; therefore the +% vector field @ t generates a symmetry. The conserved current is + +pform c=1; +factor d; + +c := noether(lagr,y,@ t); + +% The exterior derivative of this must be zero or a multiple of the +% equation of motion (weak conservation law) to be a conserved current. + +remfac d; + +d c; + +% i.e. it is a multiple of the equation of motion. + +clear lagr,c,j,y,q; +remfdomain y,q,j; + +% Problem: +% -------- +% Show that the metric structure given by Eguchi and Hanson induces a +% self-dual curvature. +% c.f. T. Eguchi, P.B. Gilkey, A.J. Hanson, "Gravitation, Gauge Theories +% and Differential Geometry", Physics Reports 66, 213, 1980 + +for all x let cos(x)**2=1-sin(x)**2; + +pform f=0,g=0; +fdomain f=f(r), g=g(r); + +coframe o(r) = f*d r, + o(theta) = (r/2)*(sin(psi)*d theta - sin(theta)*cos(psi)*d phi), + o(phi) = (r/2)*(-cos(psi)*d theta - sin(theta)*sin(psi)*d phi), + o(psi) = (r/2)*g*(d psi + cos(theta)*d phi); + +frame e; + + +pform gamma(a,b)=1,curv2(a,b)=2; +index_symmetries gamma(a,b),curv2(a,b): antisymmetric; + +factor o; + +gamma(-a,-b) := -(1/2)*( e(-a) _| (e(-c) _| (d o(-b))) + -e(-b) _| (e(-a) _| (d o(-c))) + +e(-c) _| (e(-b) _| (d o(-a))) )*o(c)$ + + +curv2(-a,b) := d gamma(-a,b) + gamma(-c,b)^gamma(-a,c)$ + +let f=1/g,g=sqrt(1-(a/r)**4); + +pform chck(k,l)=2; +index_symmetries chck(k,l): antisymmetric; + +% The following has to be zero for a self-dual curvature. + +chck(k,l) := 1/2*eps(k,l,m,n)*curv2(-m,-n) + curv2(k,l); + +clear gamma(a,b),curv2(a,b),f,g,chck(a,b),o(k),e(k),r,phi,psi; +remfdomain f,g; + +% Example: 6-dimensional FRW model with quadratic curvature terms in +% ------- +% the Lagrangian (Lanczos and Gauss-Bonnet terms). +% cf. Henriques, Nuclear Physics, B277, 621 (1986) + +for all x let cos(x)**2+sin(x)**2=1; + +pform {r,s}=0; +fdomain r=r(t),s=s(t); + +coframe o(t) = d t, + o(1) = r*d u/(1 + k*(u**2)/4), + o(2) = r*u*d theta/(1 + k*(u**2)/4), + o(3) = r*u*sin(theta)*d phi/(1 + k*(u**2)/4), + o(4) = s*d v1, + o(5) = s*sin(v1)*d v2 + with metric g =-o(t)*o(t)+o(1)*o(1)+o(2)*o(2)+o(3)*o(3) + +o(4)*o(4)+o(5)*o(5); + +frame e; + +on nero; factor o,^; + +riemannconx om; + +pform curv(k,l)=2,{riemann(a,b,c,d),ricci(a,b),riccisc}=0; + +index_symmetries curv(k,l): antisymmetric, + riemann(k,l,m,n): antisymmetric in {k,l},{m,n} + symmetric in {{k,l},{m,n}}, + ricci(k,l): symmetric; + +curv(k,l) := d om(k,l) + om(k,-m)^om(m,l); + +riemann(a,b,c,d) := e(d) _| (e (c) _| curv(a,b)); + +% The rest is done in the Ricci calculus language, + +ricci(-a,-b) := riemann(c,-a,-d,-b)*g(-c,d); + +riccisc := ricci(-a,-b)*g(a,b); + +pform {laglanc,inv1,inv2} = 0; + +index_symmetries riemc3(k,l),riemri(k,l), + hlang(k,l),einst(k,l): symmetric; + +pform {riemc3(i,j),riemri(i,j)}=0; + +riemc3(-i,-j) := riemann(-i,-k,-l,-m)*riemann(-j,k,l,m)$ +inv1 := riemc3(-i,-j)*g(i,j); +riemri(-i,-j) := 2*riemann(-i,-k,-j,-l)*ricci(k,l)$ +inv2 := ricci(-a,-b)*ricci(a,b); +laglanc := (1/2)*(inv1 - 4*inv2 + riccisc**2); + + +pform {einst(a,b),hlang(a,b)}=0; + +hlang(-i,-j) := 2*(riemc3(-i,-j) - riemri(-i,-j) - + 2*ricci(-i,-k)*ricci(-j,K) + + riccisc*ricci(-i,-j) - (1/2)*laglanc*g(-i,-j)); + +% The complete Einstein tensor: + +einst(-i,-j) := (ricci(-i,-j) - (1/2)*riccisc*g(-i,-j))*alp1 + + hlang(-i,-j)*alp2$ + +alp1 := 1$ +factor alp2; + +einst(-i,-j) := einst(-i,-j); + +clear o(k),e(k),riemc3(i,j),riemri(i,j),curv(k,l),riemann(a,b,c,d), + ricci(a,b),riccisc,t,u,v1,v2,theta,phi,r,om(k,l),einst(a,b), + hlang(a,b); + +remfdomain r,s; + +% Problem: +% -------- +% Calculate for a given coframe and given torsion the Riemannian part and +% the torsion induced part of the connection. Calculate the curvature. + +% For a more elaborate example see E.Schruefer, F.W. Hehl, J.D. McCrea, +% "Application of the REDUCE package EXCALC to the Poincare gauge field +% theory of gravity", GRG Journal, vol. 19, (1988) 197--218 + +pform {ff, gg}=0; + +fdomain ff=ff(r), gg=gg(r); + +coframe o(4) = d u + 2*b0*cos(theta)*d phi, + o(1) = ff*(d u + 2*b0*cos(theta)*d phi) + d r, + o(2) = gg*d theta, + o(3) = gg*sin(theta)*d phi + with metric g = -o(4)*o(1)-o(4)*o(1)+o(2)*o(2)+o(3)*o(3); + +frame e; + +pform {tor(a),gwt(a)}=2,gamma(a,b)=1, + {u1,u3,u5}=0; + +index_symmetries gamma(a,b): antisymmetric; + +fdomain u1=u1(r),u3=u3(r),u5=u5(r); + +tor(4) := 0$ + +tor(1) := -u5*o(4)^o(1) - 2*u3*o(2)^o(3)$ + +tor(2) := u1*o(4)^o(2) + u3*o(4)^o(3)$ + +tor(3) := u1*o(4)^o(3) - u3*o(4)^o(2)$ + +gwt(-a) := d o(-a) - tor(-a)$ + +% The following is the combined connection. +% The Riemannian part could have equally well been calculated by the +% RIEMANNCONX statement. + +gamma(-a,-b) := (1/2)*( e(-b) _| (e(-c) _| gwt(-a)) + +e(-c) _| (e(-a) _| gwt(-b)) + -e(-a) _| (e(-b) _| gwt(-c)) )*o(c); + +pform curv(a,b)=2; +index_symmetries curv(a,b): antisymmetric; +factor ^; + +curv(-a,b) := d gamma(-a,b) + gamma(-c,b)^gamma(-a,c); + +clear o(k),e(k),curv(a,b),gamma(a,b),theta,phi,x,y,z,r,s,t,u,v,p,q,c,cs; +remfdomain u1,u3,u5,ff,gg; + +showtime; +end; + +\end{verbatim} +} +\end{document} Index: r36/doc/FIDE.DOC ================================================================== --- r36/doc/FIDE.DOC +++ r36/doc/FIDE.DOC @@ -1,1983 +1,1983 @@ - - - - - - - - - - - - - - F I D E - ========== - - - - - A REDUCE package for automation of - - FInite difference method for partial - - Differential Equation solving - - - - - - - Version 1.1 - - - - - User's Manual - ------------- - - - - - Richard Liska - - - - - Faculty of Nuclear Science and Physical Engineering - Technical University of Prague - Brehova 7, 115 19 Prague 1, Czechoslovakia - E-mail: tjerl@cspuni12.bitnet (EARN) - Fax: (42 - 2) 84 73 54 - Tel: (42 - 2) 84 77 86 - - - - May 1991 - - - - - 1 - - - - - - - - - - Abstract - -------- - - - The FIDE package performs automation of the process of numerical -solving partial differential equations systems (PDES) by means of -computer algebra. For PDES solving finite difference method is applied. -The computer algebra system REDUCE and the numerical programming -language FORTRAN are used in the presented methodology. The main aim of -this methodology is to speed up the process of preparing numerical -programs for solving PDES. This process is quite often, especially for -complicated systems, a tedious and time consuming task. - In the process one can find several stages in which computer -algebra can be used for performing routine analytical calculations, -namely: transforming differential equations into different coordinate -systems, discretization of differential equations, analysis of -difference schemes and generation of numerical programs. The FIDE -package consists of the following modules: - - EXPRES for transforming PDES into any orthogonal coordinate system. - IIMET for discretization of PDES by integro-interpolation method. - APPROX for determining the order of approximation of difference - scheme. - CHARPOL for calculation of amplification matrix and characteristic - polynomial of difference scheme, which are needed in Fourier - stability analysis. - HURWP for polynomial roots locating necessary in verifying the von - Neumann stability condition. - LINBAND for generating the block of FORTRAN code, which solves a - system of linear algebraic equations with band matrix - appearing quite often in difference schemes. - - Version 1.1 of the FIDE package is the result of porting FIDE -package to REDUCE 3.4. In comparison with Version 1.0 some features has -been changed in the LINBAND module (possibility to interface several -numerical libraries). - - - - - -References ----------- - -[1] R. Liska, L. Drska: FIDE: A REDUCE package for automation of FInite - difference method for solving pDE. In ISSAC '90, Proceedings of - the International Symposium on Symbolic and Algebraic Computation, - Ed. S. Watanabe, M. Nagata. p. 169-176, ACM Press, Addison Wesley, - New York 1990. - - - 2 - - - - Table of contents - ================= - -1 E X P R E S 4 - -1.1 The specification of the coordinate system.......................4 -1.2 The declaration of tensor quantities.............................5 -1.3 New infix operators..............................................5 -1.4 New prefix operators.............................................5 -1.5 Tensor expressions...............................................6 -1.6 Assigning statement..............................................7 - -2 I I M E T 8 - -2.1 Specification of the coordinates and the indices - corresponding to them............................................8 -2.2 Difference grids.................................................9 -2.3 Declaring the dependence of functions on coordinates............10 -2.4 Functions and difference grids..................................11 -2.5 Equations and difference grids..................................12 -2.6 Discretization of basic terms...................................13 -2.7 Discretization of a system of equations.........................18 -2.8 Error messages..................................................20 - -3 A P P R O X 21 - -3.1 Specification of the coordinates and the indices - corresponding to them...........................................21 -3.2 Specification of the Taylor expansion...........................21 -3.3 Function declaration............................................22 -3.4 Order of accuracy determination.................................23 - -4 C H A R P O L 24 - -4.1 Commands common with the IIMET module...........................24 -4.2 Function declaration............................................24 -4.3 Amplification matrix............................................25 -4.4 Characteristic polynomial.......................................26 -4.5 Automatic denotation............................................26 - -5 H U R W P 28 - -5.1 Conformal mapping...............................................28 -5.2 Investigation of polynomial roots...............................28 - -6 L I N B A N D 30 - -6.1 Program generation..............................................30 -6.2 Choosing the numerical library..................................32 -6.3 Completion of the generated code................................32 - - - - - - - 3 - - - - - - - - - - - - - - - - 1 E X P R E S - =========== - - - - A Module for Transforming Differential - Operators and Equations into an Arbitrary Orthogonal - Coordinate System - - - - This module makes it possible to express various scalar, vector, -and tensor differential equations in any orthogonal coordinate system. -All transformations needed are executed automatically according to the -coordinate system given by the user. The module was implemented -according to the similar MACSYMA module from [1]. - - -1.1 The specification of the coordinate system - ------------------------------------------ - - The coordinate system is specified using the following statement: - - SCALEFACTORS ,,...,,,...,; - ::= 2 | 3 coordinate system dimension - ::= "algebraic expression" the expression of the i-th - Cartesian coordinate in new - coordinates - ::= "identifier" the i-th new coordinate - -All evaluated quantities are transformed into the coordinate system set -by the last SCALEFACTORS statement. By default, if this statement is not -applied, the three-dimensional Cartesian coordinate system is employed. -During the evaluation of SCALEFACTORS statement the metric coefficients, -i.e. scale factors SF(i), of a defined coordinate system are computed -and printed. If the WRCHRI switch is ON, then the nonzero Christoffel -symbols of the coordinate system are printed too. By default the WRCHRI -switch is OFF. - - - - - - - 4 - - - - - - -1.2 The declaration of tensor quantities - ------------------------------------ - - Tensor quantities are represented by identifiers. The VECTORS -declaration declares the identifiers as vectors, the DYADS declaration -declares the identifiers as dyads. i.e. two-dimensional tensors, and the -TENSOR declaration declares the identifiers as tensor variables. The -declarations have the following syntax: - - ,,...,; - ::= VECTORS | DYADS | TENSOR - ::= "identifier" - -The value of the identifier V declared as vector in the two-dimensional -coordinate system is (V(1), V(2)), where V(i) are the components of -vector V. The value of the identifier T declared as a dyad is ((T(1,1), -T(1,2)), (T(2,1), T(2,2))). The value of the tensor variable can be any -tensor (see below). Tensor variables can be used only for a single -coordinate system, after the coordinate system redefining by a new -SCALEFACTORS statement, the tensor variables have to be re-defined using -the assigning statement. - - -1.3 New infix operators - ------------------- - - For four different products between the tensor quantities, new -infix operators have been introduced (in the explaining examples, a -two-dimensional coordinate system, vectors U, V, and dyads T, W are -considered): - - . - scalar product U.V = U(1)*V(1)+U(2)*V(2) - ? - vector product U?V = U(1)*V(2)-U(2)*V(1) - & - outer product U&V = ((U(1)*V(1),U(1)*V(2)), - (U(2)*V(1),U(2)*V(2))) - # - double scalar product T#W = T(1,1)*W(1,1)+T(1,2)*W(1,2)+ - T(2,1)*W(2,1)+T(2,2)*W(2,2) - -The other usual arithmetic infix operators +, -, *, ** can be used in -all situations that have sense (e.g. vector addition, a multiplication -of a tensor by a scalar, etc.). - - -1.4 New prefix operators - -------------------- - - New prefix operators have been introduced to express tensor -quantities in its components and the differential operators over the -tensor quantities: - - VECT - the explicit expression of a vector in its components - DYAD - the explicit expression of a dyad in its components - - 5 - - - - - - - GRAD - differential operator of gradient - DIV - differential operator of divergence - LAPL - Laplace's differential operator - CURL - differential operator of curl - DIRDF - differential operator of the derivative in direction - (1st argument is the directional vector) - -The results of the differential operators are written using the DIFF -operator. DIFF(,) expresses the derivative of -with respect to the coordinate . This operator is not further -simplified. If the user wants to make it simpler as common derivatives, -he performs the following declaration: - - FOR ALL X,Y LET DIFF(X,Y) = DF(X,Y); . - -Then, however, we must realize that if the scalars or tensor quantities -do not directly explicitly depend on the coordinates, their dependencies -have to be declared using the DEPEND statements, otherwise the -derivative will be evaluated to zero. The dependence of all vector or -dyadic components (as dependence of the name of vector or dyad) has to -appear before VECTORS or DYADS declarations, otherwise after these -declarations one has to declare the dependencies of all components. For -formulating the explicit derivatives of tensor expressions, the -differentiation operator DF can be used (e.g. the differentiation of a -vector in its components). - - -1.5 Tensor expressions - ------------------ - - Tensor expressions are the input into the EXPRES module and can -have a variety of forms. The output is then the formulation of the given -tensor expression in the specified coordinate system. The most general -form of a tensor expression is described as follows (the -conditions (d=i) represent the limitation on the dimension of the -coordinate system equalling i): - - ::= | | - ::= "algebraic expression, can contain " | - "tensor variable with scalar value" | - . | # | - (d=2)? | DIV | - LAPL | (d=2) ROT | - DIRDF(,) - ::= "identifier declared by VECTORS statement" | - "tensor variable with vector value" | - VECT(,...,) | - | - + | - | - * | / | - . | . | (d=3) - ? | (d=2) ? | - (d=2) ? | GRAD | - - 6 - - - - - - - DIV | LAPL | (d=3) ROT | - DIRDF(,) | DF(,"usual - further arguments") - ::= "identifier declared by DYADS statement" | - "tensor variable with dyadic value" | - DYAD((,...,),...,(, - ...,)) | - | + | - - | * | / - | . | & | - (d=3) ? | (d=3) ? | - GRAD | DF(,"usual further arguments") - - -1.6 Assigning statement - ------------------- - - The assigning statement for tensor variables has a usual syntax, -namely: - - := - ::= "identifier declared TENSOR" . - -The assigning statement assigns the tensor variable the value of the -given tensor expression, formulated in the given coordinate system. -After a change of the coordinate system, the tensor variables have to be -redefined. - - - -References ----------- - -[1] M. C. Wirth, On the Automation of Computational Physics. PhDr - Thesis. Report UCRL-52996, Lawrence Livermore National - Laboratory, Livermore, 1980. - - - - - - - - - - - - - - - - - - - 7 - - - - - - - - - - - - - - - - 2 I I M E T - ========= - - - - A Module for Discretizing the Systems - of Partial Differential Equations - - - - This program module makes it possible to discretize the specified -system of partial differential equations using the integro-interpolation -method, minimizing the number of the used interpolations in each -independent variable. It can be used for non-linear systems and vector -or tensor variables as well. The user specifies the way of discretizing -individual terms of differential equations, controls the discretization -and obtains various difference schemes according to his own wish. - - -2.1 Specification of the coordinates and the indices corresponding - to them - -------------------------------------------------------------- - - The independent variables of differential equations will be called -coordinates. The names of the coordinates and the indices that will -correspond to the particular coordinates in the difference scheme are -defined using the COORDINATES statement: - - COORDINATES {,} [ INTO - {,}]; - ::= "identifier" - the name of the coordinate - ::= "identifier" - the name of the index - -This statement specifies that the will correspond to the -. A new COORDINATES statement cancels the definitions given by -the preceding COORDINATES statement. If the part [ INTO ... ] is not -included in the statement, the statement assigns the coordinates the -indices I, J, K, L, M, N, respectively. If it is included, the number of -coordinates and the number of indices should be the same. - - - - - - 8 - - - - - - -2.2 Difference grids - ---------------- - - In the discretization, orthogonal difference grids are employed. -In addition to the basic grid, called the integer one, there is another, -the half-integer grid in each coordinate, whose cellular boundary points -lie in the centers of the cells of the integer grid. The designation of -the cellular separating points and centers is determined by the -CENTERGRID switch: if it is ON and the index in the given coordinate is -I, the centers of the grid cells are designated by indices I, I + 1,..., -and the boundary points of the cells by indices I + 1/2,..., if, on the -contrary, the switch is OFF, the cellular centers are designated by -indices I + 1/2,..., and the boundary points by indices I, I + 1,... -(see Fig. 2.1). - - - ON CENTERGRID - I-1/2 I I+1/2 I+1 I+3/2 ----|--------|--------|--------------|--------------|---- - I I+1/2 I+1 I+3/2 I+2 - OFF CENTERGRID - - Figure 2.1 Types of grid - - -In the case of ON CENTERGRID, the indices i,i+1,i-1... thus designate -the centers of the cells of the integer grid and the boundary points of -the cells of the half-integer grid, and, similarly, in the case of OFF -CENTERGRID, the boundaries of the cells of the integer grid and the -central points of the half-integer grid. The meaning of the integer and -half-integer grids depends on the CENTERGRID switch in the described -way. After the package is loaded, the CENTERGRID is ON. Obviously, this -switch is significant only for non-uniform grids with a variable size of -each cell. - The grids can be uniform, i.e. with a constant cell size - the step -of the grid. The following statement: - - GRID UNIFORM,{,}; - -defines uniform grids in all coordinates occurring in it. Those -coordinates that do not occur in the GRID UNIFORM statement are supposed -to have non-uniform grids. - In the outputs, the grid step is designated by the identifier that -is made by putting the character H before the name of the coordinate. -For a uniform grid, this identifier (e.g. for the coordinate X the grid -step HX) has the meaning of a step of an integer or half-integer grids -that are identical. For a non-uniform grid, this identifier is an -operator and has the meaning of a step of an integer grid, i.e. the -length of a cell whose center (in the case of ON CENTERGRID) or -beginning (in the case of OFF CENTERGRID) is designated by a single -argument of this operator. For each coordinate s designated by the - - - 9 - - - - - - -identifier i, this step of the integer non-uniform grid is defined as -follows: - - Hs(i+j) = s(i+j+1/2) - s(i+j-1/2) at ON CENTERGRID - Hs(i+j) = s(i+j+1) - s(i+j) at OFF CENTERGRID - -for all integers j (s(k) designates the value of the coordinate s in the -cellular boundary point subscripted with the index k). The steps of the -half-integer non-uniform grid are not applied in outputs. - - -2.3 Declaring the dependence of functions on coordinates - ---------------------------------------------------- - - In the system of partial differential equations, two types of -functions, in other words dependent variables can occur: namely, the -given functions, whose values are known before the given system is -solved, and the sought functions, whose values are not available until -the system of equations is solved. The functions can be scalar, vector, -or tensor, for vector or tensor functions the EXPRES module has to be -applied at the same time. The names of the functions employed in the -given system and their dependence on the coordinates are specified using -the DEPENDENCE statement. - - DEPENDENCE {,}; - ::= ([],{, - }) - ::= "identifier" - the name of the function - ::= 1|2 tensor order of the function (the value of - the function is 1 - vector, 2 - dyad (two- - dimensional tensor)) - -Every in the statement determines on which -the depends. If the tensor of the function occurs in -the , the is declared as a vector or a dyad. If, -however, the has been declared by the VECTORS and DYADS -statements of the EXPRES module, the user need not present the tensor -. By default, a function without any declaration is regarded as -scalar. In the discretization, all scalar components of tensor functions -are replaced by identifiers that arise by putting successively the -function name and the individual indices of the given component (e.g. -the tensor component T(1,2), written in the EXPRES module as T(1,2), is -represented by the identifier T12). Before the DEPENDENCE statement is -executed, the coordinates have to be defined using the COORDINATES -statement. There may be several DEPENDENCE statements. The DEPENDENCE -statement cancels all preceding determinations of which grids are to be -used for differentiating the function or the equation for this function. -These determinations can be either defined by the ISGRID or GRIDEQ -statements, or computed in the evaluation of the IIM statement. - The GIVEN statement: - - GIVEN {,}; - - 10 - - - - - - - -declares all functions included in it as given functions whose values -are known to the user or can be computed. The CLEARGIVEN statement: - - CLEARGIVEN; - -cancels all preceding GIVEN declarations. If the TWOGRID switch is ON, -the given functions can be differentiated both on the integer and the -half-integer grids. If the TWOGRID switch is OFF, any given function can -be differentiated only on one grid. After the package is loaded, the -TWOGRID is ON. - - -2.4 Functions and difference grids - ------------------------------ - - Every scalar function or scalar component of a vector or a dyadic -function occurring in the discretized system can be discretized in any -of the coordinates either on the integer or half-integer grid. One of -the tasks of the IIMET module is to find the optimum distribution of -each of these dependent variables of the system on the integer and -half-integer grids in all variables so that the number of the performed -interpolations in the integro-interpolation method will be minimal. - Using the statement - - SAME {,}; - -all functions given in one of these declarations will be discretized on -the same grids in all coordinates. In each SAME statement, at least one -of these functions in one SAME statement must be the sought one. If the -given function occurs in the SAME statement, it will be discretized only -on one grid, regardless of the state of the TWOGRID switch. If a vector -or a dyadic function occurs in the SAME statement, what has been said -above relates to all its scalar components. There are several SAME -statements that can be presented. All SAME statements can be canceled by -the following statement: - - CLEARSAME; - -The SAME statement can be successfully used, for example, when the given -function depends on the function sought in a complicated manner that -cannot be included either in the differential equation or in the -difference scheme explicitly, and when both the functions are desired to -be discretized in the same points so that the user will not be forced to -execute the interpolation during the evaluation of the given function. - In some cases, it is convenient too to specify directly which -variable on which grid is to be discretized, for which case the ISGRID -statement is applied: - - ISGRID {,}; - ::= ([,]{,}) - ::= .. , - - 11 - - - - - - - ::= ONE | HALF designation of the integer - (ONE) and half-integer (HALF) - grids - ::= | for the vector - , for the dyadic - it is not presented for the - scalar - ::= *| "natural number from 1 to the space dimension - the space dimension is specified in the EXPRES - module by the SCALEFACTORS statement, * means all - components - -The statement defines that the given functions or their components will -be discretized in the specified coordinates on the specified grids, so -that, for example, the statement ISGRID U (X..ONE,Y..HALF), V(1,Z..ONE), -T(*,1,X..HALF); defines that scalar U will be discretized on the integer -grid in the coordinate X, and on the half-integer one in the coordinate -Y, the first component of vector V will be on the integer grid in the -coordinate Z, and the first column of tensor T will be on the -half-integer grid in the coordinate X. The ISGRID statement can be -applied more times. The functions used in this statement have to be -declared before by the DEPENDENCE statement. - - -2.5 Equations and difference grids - ------------------------------ - - Every equation of the system of partial differential equations is -an equation for some sought function (specified in the IIM statement). -The correspondence between the sought functions and the equations is -mutually unambiguous. The GRIDEQ statement makes it possible to -determine on which grid an individual equation will be discretized in -some or all coordinates - - GRIDEQ {,}; - ::= ({,}) - -Every equation can be discretized in any coordinate either on the -integer or half-integer grid. This statement determines the -discretization of the equations given by the functions included in it in -given coordinates, on given grids. The meaning of the fact that an -equation is discretized on a certain grid is as follows: index I used in -the DIFMATCH statements (discussed in the following section), specifying -the discretization of the basic terms, will be located in the center of -the cell of this grid, and indices I+1/2, I-1/2 from the DIFMATCH -statement on the boundaries of the cell of this grid. The actual name of -the index in the given coordinate is determined using the COORDINATES -statement, and its location on the grid is set by the CENTERGRID switch. - - - - - - 12 - - - - - - -2.6 Discretization of basic terms - ----------------------------- - - The discretization of a system of partial differential equations is -executed successively in individual coordinates. In the discretization -of an equation in one coordinate, the equation is linearized into its -basic terms first that will be discretized independently then. If D is -the designation for the discretization operator in the coordinate x, -this linearization obeys the following rules: - - 1. D(a+b) = D(a)+D(b) - 2. D(-a) = -D(a) - 3. D(p.a) = p.D(a) (p does not depend on the coordinate x) - 4. D(a/p) = D(a)/p - - The linearization lasts as long as some of these rules can be -applied. The basic terms that must be discretized after the -linearization have then the forms of the following quantities: - - 1. The actual coordinate in which the discretization is performed. - 2. The sought function. - 3. The given function. - 4. The product of the quantities 1 - 7. - 5. The quotient of the quantities 1 - 7. - 6. The natural power of the quantities 1 - 7. - 7. The derivative of the quantities 1 - 7 with respect to the - actual coordinate. - -The way of discretizing these basic terms, while the functions are on -integer and half-integer grids, is determined using the DIFMATCH -statement: - - DIFMATCH ,,{{,} - , }; - ::= ALL | "identifier" - the coordinate name from - the COORDINATES statement - ::= | - | - | * - | / | - ** | - DIFF(,[,])| - ({,}) - ::= X - ::= U | V | W - ::= F | G - ::= N | "integer greater than 1" - ::= "integer greater than 2" - ::= = - ::= | - - - 13 - - - - - - - ::= "non-negative integer" - ::= ()| - "natural number"|DI|DIM1|DIP1|DIM2|DIP2| - | - | - + | - * | - / | - () | - ** - ::= X | U | V | W | F | G - ::= | - + | - - - ::= I - = "rational number" - DIFCONST {,}; - ::= "identifier" - the constant parameter of - the difference scheme. - DIFFUNC {,}; - ::= "identifier" - prefix operator, that can - appear in discretized equations (e.g. SIN). - -The first parameter of the DIFMATCH statement determines the coordinate -for which the discretization defined in it is valid. If ALL is used, the -discretization will be valid for all coordinates, and this -discretization is accepted when it has been checked whether there has -been no other discretization defined for the given coordinate and the -given pattern term. Each pattern sought function, occurring in the -pattern term, must be included in the specification of the grids. The -pattern given functions from the pattern term can occur in the grid -specification, but in some cases (see below) need not. In the grid -specification the maximum number of 3 pattern functions may occur. The -discretization of each pattern term has to be specified in all -combinations of the pattern functions occurring in the grid -specification, on the integer and half-integer grids, that is 2**n -variants for the grid specification with n pattern functions -(n=0,1,2,3). The discretized term is the discretization of the pattern -term in the pattern coordinate X in the point X(I) on the pattern grid -(see Fig. 2.2), and the pattern functions occurring in the grid -specification are in the discretized term on the respective grids from -this specification (to the discretized term corresponds the grid -specification preceding it). - - integer grid - X(I-1) X(I) X(I+1) - | DIM1 | DIP1 | ----|------|------|-------------|-------------|-----|-----|--- - | DIM2 | DI | DIP2 | - X(I-3/2) X(I-1/2) X(I+1/2) X(I+3/2) - half-integer grid - - Figure 2.2 Pattern grid - - 14 - - - - - - - -The pattern grid steps defined as - - DIM2 = X(I - 1/2) - X(I - 3/2) - DIM1 = X(I) - X(I - 1) - DI = X(I + 1/2) - X(I - 1/2) - DIP1 = X(I + 1) - X(I) - DIP2 = X(I + 3/2) - X(I + 1/2) - -can occur in the discretized term. - In the integro-interpolation method, the discretized term is -specified by the integral - - =1/(X(I+1/2)-X(I-1/2))*DINT(X(I-1/2),X(I+1/2), - ,X), - -where DINT is operator of definite integration DINT(from, to, function, -variable). The number of interpolations determines how many -interpolations were needed for calculating this integral in the given -discrete form (the function on the integer or half-integer grid). If the -integro-interpolation method is not used, the more convenient is the -distribution of the functions on the half-integer and integer grids, the -smaller number is chosen by the user. The parameters of the difference -scheme defined by the DIFCONST statement can occur in the discretized -expression too (for example, the implicit-explicit scheme on the -implicit layer multiplied by the constant C and on the explicit one by -(1-C)). As a matter of fact, all DIFMATCH statements create a base of -pattern terms with the rules of how to discretize these terms in -individual coordinates under the assumption that the functions occurring -in the pattern terms are on the grids determined in the grid -specification (all combinations must be included). - The DIFMATCH statement does not check whether the discretized term -is actually the discretization of the pattern term or whether in the -discretized term occur the functions from the grid specification on the -grids given by this specification. An example can be the following -definition of the discretization of the first and second derivatives of -the sought function in the coordinate R on a uniform grid: - - DIFMATCH R,DIFF(U,X),U=ONE,2,(U(I+1)-U(I-1))/(2*DI); - U=HALF,0,(U(I+1/2)-U(I-1/2))/DI; - DIFMATCH R,DIFF(U,X,2),U=ONE,0,(U(I+1)-2*U(I)+U(I-1))/DI**2, - U=HALF,2,(U(I+3/2)-U(I+1/2)-U(I-1/2)+U(I-3/2))/(2*DI**2); - - All DIFMATCH statements can be cleared by the statement - - CLEARDIFMATCH; - -After this statement user has to supply its own DIFMATCH statements. - But now back to the discretizing of the basic terms obtained by the -linearization of the partial differential equation, as mentioned at the -beginning of this section. Using the method of pattern matching, for -each basic term a term representing its pattern is found in the base of - - 15 - - - - - - -pattern terms (specified by the DIFMATCH statements). The pattern -matching obeys the following rules: - - 1. The pattern for the coordinate in which the discretization is - executed is the pattern coordinate X. - - 2. The pattern for the sought function is some pattern sought - function, and this correspondence is mutually unambiguous. - - 3. The pattern for the given function is some pattern given - function, or, in case the EQFU switch is ON, some pattern sought - function, and, again, the correspondence of the pattern with the - given function is mutually unambiguous (after loading the EQFU - switch is ON). - - 4. The pattern for the products of quantities is the product of the - patterns of these quantities, irrespective of their sequence. - - 5. The pattern for the quotient of quantities is the quotient of the - patterns of these quantities. - - 6. The pattern for the natural power of a quantity is the same power - of the pattern of this quantity or the power of this quantity with - the pattern exponent N. - - 7. The pattern for the derivative of a quantity with respect to the - coordinate in which the discretization is executed is the derivative - of the pattern of this quantity with respect to the pattern - coordinate X of the same order of differentiation. - - 8. The pattern for the sum of the quantities that have the same - pattern with the identical correspondence of functions and pattern - functions is this common pattern (so that it will not be necessary - to multiply the parentheses during discretizing the products in the - second and further coordinates). - -When matching the pattern of one basic term, the program finds the -pattern term and the functions corresponding to the pattern functions, -maybe also the exponent corresponding to the pattern exponent N. After -determining on which grids the individual functions and the individual -equations will be discretized, which will be discussed in the next -section, the program finds in the pattern term base the discretized term -either with pattern functions on the same grids as are the functions -from the basic term corresponding to them in case that the given -equation is differentiated on the integer grid, or with pattern -functions on inverse grids (an inverse integer grid is a half-integer -grid, and vice versa) compared with those used for the functions from -the basic term corresponding to them in case the given equation is -differentiated on the half-integer grid (the discretized term in the -DIFMATCH statement is expressed in the point X(I), i.e. on the integer -grid, and holds for the discretizing of the equation on the integer -grid; with regard to the substitutions for the pattern index I mentioned - - 16 - - - - - - -later, it is possible to proceed in this way and not necessary to define -the discretization in the points X(I+1/2) too, i.e. on the half-integer -grid). The program replaces in the thus obtained discretized term: - - 1. The pattern coordinate X with the particular coordinate s in - which the discretization is actually performed. - - 2. The pattern index I and the grid steps DIM2, DIM1, DI, DIP1, DIP2 - with the expression given in table 2.1 according to the state of the - CENTERGRID switch and to the fact whether the given equation is - discretized on the integer or half-integer grid (i is the index - corresponding to the coordinate s according to the COORDINATES - statement, the grid steps were defined in section 2.2) - - 3. The pattern functions with the corresponding functions from the - basic term and, possibly, the pattern exponent with the - corresponding exponent from the basic term. - --------------------------------------------------------------------- -| the equation discretized on | -| the integer grid | the half-integer grid | -| CENTERGRID |CENTERGRID|CENTERGRID| CENTERGRID | -| OFF | ON | OFF | ON | -|------------------------------------------------------------------| -| I | i | i+1/2 | -|----|-------------------------------------------------------------| -|DIM2|(Hs(i-2)+Hs(i-1))/2| Hs(i-1) |(Hs(i-1)+Hs(i))/2 | -|DIM1| Hs(i-1) | (Hs(i-1)+Hs(i))/2 | Hs(i) | -|DI |(Hs(i-1)+Hs(i))/2 | Hs(i) |(Hs(i)+Hs(i+1))/2 | -|DIP1| Hs(i) | (Hs(i)+Hs(i+1))/2 | Hs(i+1) | -|DIP2|(Hs(i)+Hs(i+1))/2 | Hs(i+1) |(Hs(i+1)+Hs(i+2))/2| --------------------------------------------------------------------- - - Table 2.1 Values of the pattern index and - the pattern grid steps. - - More details will be given now to the discretization of the given -functions and its specification. The given function may occur in the -SAME statement, which makes it bound with some sought function, in other -words it can be discretized only on one grid. This means that all basic -terms, in which this function occurs, must have their pattern terms in -whose discretization definitions by the DIFMATCH statement the pattern -function corresponding to the mentioned given function has to occur in -the grid specification. If the given function does not occur in the SAME -statement and the TWOGRID switch is OFF, i.e. it can be discretized only -on one grid again, the same holds true. If, however, the given function -does not occur in the SAME statement and the TWOGRID switch is ON, i.e. -it can be discretized simultaneously on the integer and the half-integer -grids, then the basic terms of the equations including this function -have their pattern terms in whose discretization definitions the pattern -function corresponding to the mentioned given function need not occur in -the grid specification. If, however, in spite of all, this pattern - - 17 - - - - - - -function in the discretization definition does occur in the grid -specification, it is the alternative with a smaller number of -interpolations occurring in the DIFMATCH statement that is selected for -each particular basic term with a corresponding pattern (the given -function can be on the integer or half-integer grid). - Before the discretization is executed, it is necessary to define -using the DIFMATCH statements the discretization of all pattern terms -that are the patterns of all basic terms of all equations appearing in -the discretized system in all coordinates. The fact that the pattern -terms of the basic terms of partial equations occur repeatedly in -individual systems has made it possible to create a library of the -discretizations of the basic types of pattern terms using the -integro-interpolation method. This library is a component part of the -IIMET module (in its end) and makes work easier for those users who find -the pattern matching mechanism described here too difficult. New -DIFMATCH statements have to be created by those whose equations will -contain a basic term having no pattern in this library, or those who -need another method to perform the discretization. The described -implemented algorithm of discretizing the basic terms is sufficiently -general to enable the use of a nearly arbitrary discretization on -orthogonal grids. - - -2.7 Discretization of a system of equations - --------------------------------------- - - All statements influencing the run of the discretization that one -want use in this run have to be executed before the discretization is -initiated. The COORDINATES, DEPENDENCE, and DIFMATCH statements have to -occur in all applications. Further, if necessary, the GRID UNIFORM, -GIVEN, ISGRID, GRIDEQ, SAME, and DIFCONST statements can be used, or -some of the CENTREGRID, TWOGRID, EQFU, and FULLEQ switches can be set. -Only then the discretization of a system of partial differential -equations can be started using the IIM statement: - - IIM {,,}; - ::= "identifier" - the name of the array for storing - the result - ::= "identifier" - the name of the function - whose behavior is described by the - equation - ::= = - ::= "algebraic expression" , the derivatives are - designated by the DIFF operator - ::= "algebraic expression" - -Hence, in the IIM statement the name of the array in which the resulting -difference schemes will be stored, and the pair sought function - -equation, which describes this function, are specified. The meaning of -the relation between the sought function and its equation during the -discretization lies in the fact that the sought function is preferred in -its equation so that the interpolation is not, if possible, used in - - 18 - - - - - - -discretizing the terms of this equation that contain it. In the -equations, the functions and the coordinates appear as identifiers. The -identifiers that have not been declared as functions by the DEPENDENCE -statement or as coordinates by the COORDINATES statement are considered -constants independent of the coordinates. The partial derivatives are -expressed by the DIFF operator that has the same syntax as the standard -differentiation operator DF. The functions and the equations can also -have the vector or tensor character. If these non-scalar quantities are -applied, the EXPRES module has to be used together with the IIMET -module, and also non-scalar differential operators such as GRAD, DIV, -etc. can be employed. - The sequence performed by the program in the discretization can be -briefly summed up in the following items: - - 1. If there are non-scalar functions or equations in a system of - equations, they are automatically converted into scalar quantities - by means of the EXPRES module. - - 2. In each equation, the terms containing derivatives are - transferred to the left side, and the other terms to the right side - of the equation. - - 3. For each coordinate, with respect to the sequence in which they - occur in the COORDINATES statement, the following is executed: - - a) It is determined on which grids all functions and all equations - in the actual coordinate will be discretized, and simultaneously the - limits are kept resulting from the ISGRID, GRIDEQ, and SAME - statements if they were used. Such a distribution of functions and - equations on the grids is selected among all possible variants that - ensures the minimum sum of all numbers of the interpolations of the - basic terms (specified by the DIFMATCH statement) of all equations - if the FULLEQ switch is ON, or of all left sides of the equations if - the FULLEQ switch is OFF (after the loading the FULLEQ switch is - ON). - - b) The discretization itself is executed, as specified by the - DIFMATCH statements. - - 4. If the array name is A, then if there is only one scalar equation - in the IIM statement, the discretized left side of this equation is - stored in A(0) and the discretized right side in A(1) (after the - transfer mentioned in item 2), if there are more scalar equations - than one in the IIM statement, the discretization of the left side - of the i-th scalar equation is stored in A(i,0) and the - discretization of the right side in A(i,1). - -The IIM statement can be used more times during one program run, and -between its calls, the discretizing process can be altered using other -statements of this module. - - - - 19 - - - - - - -2.8 Error messages - -------------- - - The IIMET module provides error messages in the case of the user's -errors. Similarly as in the REDUCE system, the error reporting is marked -with five stars : "*****" on the line start. Some error messages are -identical with those of the REDUCE system. Here are given some other -error messages that require a more detailed explanation: - -***** Matching of X term not found - - the discretization of the pattern term that is the pattern of - the basic term printed on the place X has not been - defined (using the DIFMATCH statement) -***** Variable of type F not defined on grids in DIFMATCH - - in the definition of the discretizing of the pattern term - the given functions were not used in the grid - specification and are needed now -***** X Free vars not yet implemented - - in the grid specification in the DIFMATCH statement - more than 3 pattern functions were used -***** All grids not given for term X - - in the definition of the discretization of the pattern of - the basic term printed on the place X not all - necessary combinations of the grid specification - of the pattern functions were presented - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 20 - - - - - - - - - - - - - - - - 3 A P P R O X - =========== - - - - - A Module for Determining the Precision Order - of the Difference Scheme - - - - This module makes it possible to determine the differential -equation that is solved by the given difference scheme, and to determine -the order of accuracy of the solution of this scheme in the grid steps -in individual coordinates. The discrete function values are expanded -into the Taylor series in the specified point. - - -3.1 Specification of the coordinates and the indices - corresponding to them - ------------------------------------------------ - - The COORDINATES statement, described in the IIMET module manual, -specifying the coordinates and the indices corresponding to them is the -same for this program module as well. It has the same meaning and -syntax. The present module version assumes a uniform grid in all -coordinates. The grid step in the input difference schemes has to be -designated by an identifier consisting of the character H and the name -of the coordinate, e.g. the step of the coordinate X is HX. - - -3.2 Specification of the Taylor expansion - ------------------------------------- - - In the determining of the approximation order, all discrete values -of the functions are expanded into the Taylor series in all coordinates. -In order to determine the Taylor expansion, the program needs to know -the point in which it performs this expansion, and the number of terms -in the Taylor series in individual coordinates. The center of the Taylor -expansion is specified by the CENTER statement and the number of terms -in the Taylor series in individual coordinates by the MAXORDER -statement: - - - 21 - - - - - - - CENTER
{,
}; -
::= = - ::= "rational number" - MAXORDER {,}; - ::= = - ::= "natural number" - -The increment in the CENTER statement determines that the center of the -Taylor expansion in the given coordinate will be in the point specified -by the index I + , where I is the index corresponding to this -coordinate, defined using the COORDINATES statement, e.g. the following -example - - COORDINATE T,X INTO N,J; - CENTER T = 1/2, X = 1; - MAXORDER T = 2, X = 3; - -specifies that the center of the Taylor expansion will be in the point -(t(n+1/2),x(j+1)) and that until the second derivatives with respect to -t (second powers of ht) and until the third derivatives with respect to -x (third powers of hx) the expansion will be performed. The CENTER and -MAXORDER statements can be placed only after the COORDINATES statement. -If the center of the Taylor expansion is not defined in some coordinate, -it is supposed to be in the point given by the index of this coordinate -(i.e. zero increment). If the number of the terms of the Taylor -expansion is not defined in some coordinate, the expansion is performed -until the third derivatives with respect to this coordinate. - - -3.3 Function declaration - -------------------- - - All functions whose discrete values are to be expanded into the -Taylor series must be declared using the FUNCTIONS statement: - - FUNCTIONS {,}; - ::= "identifier" - -In the specification of the difference scheme, the functions are used as -operators with one or more arguments, designating the discrete values of -the functions. Each argument is the sum of the coordinate index (from -the COORDINATES statement) and a rational number. If some index is -omitted in the arguments of a function, this functional value is -supposed to lie in the point in which the Taylor expansion is performed, -as specified by the CENTER statement. In other words, if the COORDINATES -and CENTER statements, shown in the example in the previous section, are -valid, then it holds that U(N+1) = U(N+1,J+1) and U(J-1) = U(N+1/2,J-1). -The FUNCTIONS statement can declare both the sought and the known -functions for the expansion. - - - - - 22 - - - - - - -3.4 Order of accuracy determination - ------------------------------- - - The order of accuracy of the difference scheme is determined by the -APPROX statement: - - APPROX (); - ::= = - ::= "algebraic expression" - -In the difference scheme occur the functions in the form described in -the preceding section, the coordinate indices and the grid steps -described in section 3.1, and the other symbolic parameters of the -difference scheme. The APPROX statement expands all discrete values of -the functions declared in the FUNCTIONS statement into the Taylor series -in all coordinates (the point in which the Taylor expansion is performed -is specified by the CENTER statement, and the number of the expansion -terms by the MAXORDER statement), substitutes the expansions into the -difference scheme, which gives a modified differential equation. The -modified differential equation, containing the grid steps too, is an -equation that is really solved by the difference scheme (into the given -orders in the grid steps). - The partial differential equation, whose solution is approximated -by the difference scheme, is determined by replacing the grid steps by -zeros and is displayed after the following message: - - "Difference scheme approximates differential equation" - -Then the following message is displayed: - - "with orders of approximation:" - -and the lowest powers (except for zero) of the grid steps in all -coordinates, occurring in the modified differential equation are -written. If the PRAPPROX switch is ON, then the rest of the modified -differential equation is printed. If this rest is added to the left hand -side of the approximated differential equation, one obtain modified -equation. By default the PRAPPROX switch is OFF. If the grid steps are -found in some denominator in the modified equation, i.e. with a negative -exponent, the following message is written, preceding the approximated -differential equation: - - "Reformulate difference scheme, grid steps remain in denominator" - -and the approximated differential equation is not correctly determined -(one of its sides is zero). Generally, this message means that there is -a term in the difference scheme that is not a difference replacement of -the derivative, i.e. the ratio of the differences of the discrete -function values and the discrete values of the coordinates (the steps of -the difference grid). The user, however, must realize that in some cases -such a term occurs purposefully in the difference scheme (e.g. on the -grid boundary to keep the scheme conservative). - - 23 - - - - - - - - - - - - - - - - 4 C H A R P O L - ============= - - - - A Module for Calculating the Amplification Matrix - and the Characteristic Polynomial of the - Difference Scheme - - - - This program module is used for the first step of the stability -analysis of the difference scheme using the Fourier method. It -substitutes the Fourier components into the difference scheme, -calculates the amplification matrix of the scheme for transition from -one time layer to another, and computes the characteristic polynomial of -this matrix. - - -4.1 Commands common with the IIMET module - ------------------------------------- - - The COORDINATES and GRID UNIFORM statements, described in the IIMET -module manual, are applied in this module as well, having the same -meaning and syntax. The time coordinate is assumed to be designated by -the identifier T. The present module version requires all coordinates to -have uniform grids, i.e. to be declared in the GRID UNIFORM statement. -The grid step in the input difference schemes has to be designated by -the identifier consisting of the character H and the name of the -coordinate, e.g. the step of the time coordinate T is HT. - - -4.2 Function declaration - -------------------- - - The UNFUNC statement declares the names of the sought functions -used in the difference scheme: - - UNFUNC {,} - ::= "identifier" - the name of the sought function - -The functions are used in the difference schemes as operators with one -or more arguments for designating the discrete function values. Each - - 24 - - - - - - -argument is the sum of the index (from the COORDINATES statement) and a -rational number. If some index is omitted in the function arguments, -this function value is supposed to lie in the point specified only by -this index, which means that, with the indices N and J and the function -U, it holds that U(N+1) = U(N+1,J) and U(J-1) = U(N,J-1). As two-step -(in time) difference schemes may be used only, the time index may occur -either completely alone in the arguments, or in the sum with a one. - - -4.3 Amplification matrix - -------------------- - - The AMPMAT matrix operator computes the amplification matrix of a -two-step difference scheme. Its argument is an one column matrix of the -dimension (1,k), where k is the number of the equations of the -difference scheme, that contains the difference equations of this scheme -as algebraic expressions equal to the difference of the right and left -sides of the difference equations. The value of the AMPMAT matrix -operator is the square amplification matrix of the dimension (k,k). -During the computation of the amplification matrix, two new identifiers -are created for each spatial coordinate. The identifier made up of the -character K and the name of the coordinate represents the wave number in -this coordinate, and the identifier made up of the character A and the -name of the coordinate represents the product of this wave number and -the grid step in this coordinate divided by the least common multiple of -all denominators occurring in the scheme in the function argument -containing the index of this coordinate. On the output an equation is -displayed defining the latter identifier. For example, if in the case of -function U and index J in the coordinate X the expression U(J+1/2) has -been used in the scheme (and, simultaneously, no denominator higher than -2 has occurred in the arguments with J), the following equation is -displayed: AX: = (KX*HX)/2. The definition of these quantities As allows -to express every sum occurring in the argument of the exponentials as -the sum of these quantities multiplied by integers, so that after a -transformation, the amplification matrix will contain only sin(As) and -cos(As) (for all spatial coordinates s). The AMPMAT operator performs -these transformations automatically. If the PRFOURMAT switch is ON -(after the loading it is ON), the matrices H0 and H1 (the amplification -matrix is equal to -H1**(-1)*H0) are displayed during the evaluation of -the AMPMAT operator. These matrices can be used for finding a suitable -substitution for the goniometric functions in the next run for a greater -simplification. - The TCON matrix operator transforms the square matrix into a -Hermit-conjugate matrix, i.e. a transposed and complex conjugate one. -Its argument is the square matrix and its value is Hermit-conjugate -matrix of the argument. The Hermit-conjugate matrix is used for testing -the normality and unitarity of the amplification matrix in the -determining of the sufficient stability condition. - - - - - - 25 - - - - - - -4.4 Characteristic polynomial - ------------------------- - - The CHARPOL operator calculates the characteristic polynomial of -the given square matrix. The variable of the characteristic polynomial -is designated by the LAM identifier. The operator has one argument, the -square matrix, and its value is its characteristic polynomial in LAM. - - -4.5 Automatic denotation - -------------------- - - Several statements and procedures are designed for automatic -denotation of some parts of algebraic expressions by identifiers. This -denotation is namely useful when we obtain very large expressions, which -cannot fit into the available memory. We can denote subparts of an -expression from the previous step of calculation by identifiers, replace -these subparts by these identifiers and continue the analytic -calculation only with these identifiers. Every time we use this -technique we have to explicitly survive in processed expressions those -algebraic quantities which will be necessary in the following steps of -calculation. The process of denotation and replacement is performed -automatically and the algebraic values which are denoted by these new -identifiers can be written out at any time. We describe how this -automatic denotation can be used. - The statement DENOTID defines the beginning letters of newly -created identifiers. Its syntax is - - DENOTID ; - ::= "identifier" - -After this statement the new identifiers created by the operators -DENOTEPOL and DENOTEMAT will begin with the letters of the identifier - used in this statement. Without using any DENOTID statement all new -identifiers will begin with one letter A. We suggest to use this -statement every time before using operators DENOTEPOL or DENOTEMAT with -some new identifier and to choose identifiers used in this statement in -such a way that the newly created identifiers are not equal to any -identifiers used in the expressions you are working with. - The operator DENOTEPOL has one argument, a polynomial in LAM, and -denotes the real and imaginary part of its coefficients by new -identifiers. The real part of the j-th LAM power coefficient is denoted -by the identifier R0j and the imaginary part by I0j, where -is the identifier used in the last DENOTID statement. The denotation is -done only for non-numeric coefficients. The value of this operator is -the polynomial in LAM with coefficients constructed from the new -identifiers. The algebraic expressions which are denoted by these -identifiers are stored as LISP data structure standard quotient in the -LISP variable DENOTATION!* (assoc. list). - The operator DENOTEMAT has one argument, a matrix, and denotes the -real and imaginary parts of its elements. The real part of the (j,k) -matrix element is denoted by the identifier Rjk and the imaginary - - 26 - - - - - - -part by Ijk. The returned value of the operator is the original -matrix with non-numeric elements replaced by Rjk + I*Ijk. Other -matters are the same as for the DENOTEPOL operator. - The statement PRDENOT has the syntax - - PRDENOT; - -and writes from the variable DENOTATION!* the definitions of all new -identifiers introduced by the DENOTEPOL and DENOTEMAT operators since -the last call of CLEARDENOT statement (or program start) in the format -defined by the present setting of output control declarations and -switches. The definitions are written in the same order as they have -been entered, so that the definitions of the first DENOTEPOL or -DENOTEMAT operators are written first. This order guarantees that this -statement can be utilized directly to generate a semantically correct -numerical program (the identifiers from the first denotation can appear -in the second one, etc.). - The statement CLEARDENOT with the syntax - - CLEARDENOT; - -clears the variable DENOTATION!*, so that all denotations saved earlier -by the DENOTEPOL and DENOTEMAT operators in this variable are lost. The -PRDENOT statement succeeding this statement writes nothing. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 27 - - - - - - - - - - - - - - - - 5 H U R W P - ========= - - - - A Module for Polynomial Roots Locating - - - - This module is used for verifying the stability of a polynomial, -i.e. for verifying if all roots of a polynomial lie in a unit circle -with its center in the origin. By investigating the characteristic -polynomial of the difference scheme, the user can determine the -conditions of the stability of this scheme. - - -5.1 Conformal mapping - ----------------- - - The HURW operator transforms a polynomial using the conformal -mapping LAM=(z+1)/(z-1). Its argument is a polynomial in LAM and its -value is a transformed polynomial in LAM (LAM=z). If P is a polynomial -in LAM, then it holds: all roots LAM1i of the polynomial P are in their -absolute values smaller than one, i.e. |LAM1i|<1, iff the real parts of -all roots LAM2i of the HURW(P) polynomial are negative, i.e. Re -(LAM2i)<0. - The elimination of the unit polynomial roots (LAM=1), which has to -occur before the conformal transformation is performed, is made by the -TROOT1 operator. The argument of this operator is a polynomial in LAM -and its value is a polynomial in LAM not having its root equal to one -any more. Mostly, the investigated polynomial has some more parameters. -For some special values of those parameters, the polynomial may have a -unit root. During the evaluation of the TROOT1 operator, the condition -concerning the polynomial parameters is displayed, and if it is -fulfilled, the resulting polynomial has a unit root. - - -5.2 Investigation of polynomial roots - --------------------------------- - - The HURWITZP operator checks whether a polynomial is the Hurwitz -polynomial, i.e. whether all its roots have negative real parts. The -argument of the HURWITZP operator is a polynomial in LAM with real or - - 28 - - - - - - -complex coefficients, and its value is YES if the argument is the -Hurwitz polynomial. It is NO if the argument is not the Hurwitz -polynomial, and COND if it is the Hurwitz polynomial when the conditions -displayed by the HURWITZP operator during its analysis are fulfilled. -These conditions have the form of inequalities and contain algebraic -expressions made up of the polynomial coefficients. The conditions have -to be valid either simultaneously, or they are designated and a -proposition is created from them by the AND and OR logic operators that -has to be fulfilled (it is the condition concerning the parameters -occurring in the polynomial coefficient) by a polynomial to be the -Hurwitz one. This proposition is the sufficient condition, the necessary -condition is the fulfillment of all the inequalities displayed. - If the HURWITZP operator is called interactively, the user is -directly asked if the inequalities are or are not valid. The user -responds "Y" if the displayed inequality is valid, "N" if it is not, and -"?" if he does not know whether the inequality is true or not. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 29 - - - - - - - - - - - - - - - - 6 L I N B A N D - ============= - - - - A Module for Generating the Numeric Program for - Solving a System of Linear Algebraic Equations - with Band Matrix - - - - The LINBAND module generates the numeric program in the FORTRAN -language, which solves a system of linear algebraic equations with band -matrix using the routine from the LINPACK, NAG ,IMSL or ESSL program -library. As input data only the system of equations is given to the -program. Automatically, the statements of the FORTRAN language are -generated that fill the band matrix of the system in the corresponding -memory mode of chosen library, call the solving routine, and assign the -chosen variables to the solution of the system. The module can be used -for solving linear difference schemes often having the band matrix. - - -6.1 Program generation - ------------------ - - The program in the FORTRAN language is generated by the -GENLINBANDSOL statement (the braces in this syntax definition occur -directly in the program and do not have the usual meaning of the -possibility of repetition, they designate REDUCE lists): - - GENLINBANDSOL (,,{}); - ::= "natural number" - ::= "natural number" - ::= | , - ::= {,} | - ::= "kernel" - ::= = - ::= "algebraic expression" - ::= "algebraic expression" - ::= {DO,{,,,},} - ::= "identifier" - ::= - - - 30 - - - - - - - ::= - ::= - ::= "algebraic expression" with natural value - (evaluated in FORTRAN) - ::= | , - ::= {,} - -The first and second argument of the GENLINBANDSOL statement specifies -the number of the lower (below the main diagonal) and the upper -diagonals of the band matrix of the system. The system of linear - algebraic equations is specified by means of lists expressed by braces -{ } in the REDUCE system. The variables of the equation system can be -identifiers, but most probably they are operators with an argument or -with arguments that are analogous to array in FORTRAN. The left side of -each equation has to be a linear combination of the system variables, -the right side, on the contrary, is not allowed to contain any variables -of the system. The sequence of the band matrix lines is given by the -sequence of the equations, and the sequence of the columns by the -sequence of the variables in the list describing the equation system. - The meaning of the loop in the system list is similar to that of -the DO loop of the FORTRAN language. The individual variables and -equations described by the loop are obtained as follows: - - 1. = . - 2. The value is substituted into the variables and - equations of the loop, by which further variables and - equations of the system are obtained. - 3. is increased by . - 4. If is less or equal , then go to step 2, else all - variables and equations described by the loop have already been - obtained. - -The variables and equations of the system included in the loop usually -contain the loop parameter, which mostly occur in the operator arguments -in the REDUCE language, or in the array indices in the FORTRAN language. - If NL = , NU = , and for some loop F = , T -= , S = and N is the number of the equations in the loop -, it has to be true that - - UP(NL/N) + UP(NU/N) < DOWN((T-F)/S) - -where UP represents the rounding-off to a higher natural number, and -DOWN the rounding-off to a lower natural number. With regard to the fact -that, for example, the last variable before the loop is not required to -equal the last variable from the loop system, into which the loop -parameter equal to F-S is substituted, when the band matrix is being -constructed, from the FORTRAN loop that corresponds to the loop from the -specification of the equation system, at least the first NL -variables-equations have to be moved to precede the FORTRAN loop, and at - - - - 31 - - - - - - -least the last NU variables-equations have to be moved to follow this -loop in order that the correspondence of the system variables in this -loop with the system variables before and after this loop will be -secured. And this move requires the above mentioned condition to be -fulfilled. As, in most cases, NL/N and NU/N are small with respect to -(T-F)/S, this condition does not represent any considerable constrain. - The loop parameters , , and can be natural numbers -or expressions that must have natural values in the run of the FORTRAN -program. - - -6.2 Choosing the numerical library - ------------------------------ - - The user can choose the routines of which numerical library will be -used in the generated FORTRAN code. The supported numerical libraries -are: LINPACK, NAG, IMSL and ESSL (IBM Engineering and Scientific -Subroutine Library) . The routines DGBFA, DGBSL (band solver) and DGTSL -(tridiagonal solver) are used from the LINPACK library, the routines -F01LBF, F04LDF (band solver) and F01LEF, F04LEF (tridiagonal solver) are -used from the NAG library, the routine LEQT1B is used from the IMSL -library and the routines DGBF, DGBS (band solver) and DGTF, DGTS -(tridiagonal solver) are used from the ESSL library. By default the - LINPACK library routines are used. The using of other libraries is -controlled by the switches NAG,IMSL and ESSL. All these switches are by -default OFF. If the switch IMSL is ON then the IMSL library routine is -used. If the switch IMSL is OFF and the switch NAG is ON then NAG -library routines are used. If the switches IMSL and NAG are OFF and the -switch ESSL is ON then the ESSL library is used. During generating the -code using LINPACK, NAG or ESSL libraries the special routines are use -for systems with tridiagonal matrices, because tridiagonal solvers are -faster than the band matrix solvers. - - -6.3 Completion of the generated code - -------------------------------- - - The GENLINBANDSOL statement generates a block of FORTRAN code ( a -block of statements of the FORTRAN language) that performs the solution -of the given system of linear algebraic equations. In order to be used, -this block of code has to be completed with some declarations and -statements, thus getting a certain envelope that enables it to be -integrated into the main program. - In order to be able to work, the generated block of code has to be -preceded by: - - 1. The declaration of arrays as described by the comments generated - into the FORTRAN code (near the calling of library routines) - - 2. The assigning the values to the integer variables describing the - real dimensions of used arrays (again as described in generated - FORTRAN comments) - - 32 - - - - - - - 3. The filling of the variables that can occur in the loop parameters. - - 4. The filling or declaration of all variables and arrays occurring in - the system equations, except for the variables of the system of linear - equations. - - 5. The definition of subroutine ERROUT the call to which is generated - after some routines found that the matrix is algorithmically singular - - The mentioned envelope for the generated block can be created -manually, or directly using the GENTRAN program package for generating -numeric programs. The LINBAND module itself uses the GENTRAN package, -and the GENLINBANDSOL statement can be applied directly in the input -files of the GENTRAN package (template processing). The GENTRAN package -has to be loaded prior to loading of the LINBAND module. - The generated block of FORTRAN code has to be linked with the -routines from chosen numerical library. - - - - - - - -References ----------- - -[1] R. Liska: Numerical Code Generation for Finite Difference Schemes - Solving. In IMACS World Congress on Computation and Applied - Mathematics. Dublin, July 22-26, 1991, Dublin,(In press). - - - - - - - - - - - - - - - - - - - - - - - - 33 - + + + + + + + + + + + + + + F I D E + ========== + + + + + A REDUCE package for automation of + + FInite difference method for partial + + Differential Equation solving + + + + + + + Version 1.1 + + + + + User's Manual + ------------- + + + + + Richard Liska + + + + + Faculty of Nuclear Science and Physical Engineering + Technical University of Prague + Brehova 7, 115 19 Prague 1, Czechoslovakia + E-mail: tjerl@cspuni12.bitnet (EARN) + Fax: (42 - 2) 84 73 54 + Tel: (42 - 2) 84 77 86 + + + + May 1991 + + + + + 1 + + + + + + + + + + Abstract + -------- + + + The FIDE package performs automation of the process of numerical +solving partial differential equations systems (PDES) by means of +computer algebra. For PDES solving finite difference method is applied. +The computer algebra system REDUCE and the numerical programming +language FORTRAN are used in the presented methodology. The main aim of +this methodology is to speed up the process of preparing numerical +programs for solving PDES. This process is quite often, especially for +complicated systems, a tedious and time consuming task. + In the process one can find several stages in which computer +algebra can be used for performing routine analytical calculations, +namely: transforming differential equations into different coordinate +systems, discretization of differential equations, analysis of +difference schemes and generation of numerical programs. The FIDE +package consists of the following modules: + + EXPRES for transforming PDES into any orthogonal coordinate system. + IIMET for discretization of PDES by integro-interpolation method. + APPROX for determining the order of approximation of difference + scheme. + CHARPOL for calculation of amplification matrix and characteristic + polynomial of difference scheme, which are needed in Fourier + stability analysis. + HURWP for polynomial roots locating necessary in verifying the von + Neumann stability condition. + LINBAND for generating the block of FORTRAN code, which solves a + system of linear algebraic equations with band matrix + appearing quite often in difference schemes. + + Version 1.1 of the FIDE package is the result of porting FIDE +package to REDUCE 3.4. In comparison with Version 1.0 some features has +been changed in the LINBAND module (possibility to interface several +numerical libraries). + + + + + +References +---------- + +[1] R. Liska, L. Drska: FIDE: A REDUCE package for automation of FInite + difference method for solving pDE. In ISSAC '90, Proceedings of + the International Symposium on Symbolic and Algebraic Computation, + Ed. S. Watanabe, M. Nagata. p. 169-176, ACM Press, Addison Wesley, + New York 1990. + + + 2 + + + + Table of contents + ================= + +1 E X P R E S 4 + +1.1 The specification of the coordinate system.......................4 +1.2 The declaration of tensor quantities.............................5 +1.3 New infix operators..............................................5 +1.4 New prefix operators.............................................5 +1.5 Tensor expressions...............................................6 +1.6 Assigning statement..............................................7 + +2 I I M E T 8 + +2.1 Specification of the coordinates and the indices + corresponding to them............................................8 +2.2 Difference grids.................................................9 +2.3 Declaring the dependence of functions on coordinates............10 +2.4 Functions and difference grids..................................11 +2.5 Equations and difference grids..................................12 +2.6 Discretization of basic terms...................................13 +2.7 Discretization of a system of equations.........................18 +2.8 Error messages..................................................20 + +3 A P P R O X 21 + +3.1 Specification of the coordinates and the indices + corresponding to them...........................................21 +3.2 Specification of the Taylor expansion...........................21 +3.3 Function declaration............................................22 +3.4 Order of accuracy determination.................................23 + +4 C H A R P O L 24 + +4.1 Commands common with the IIMET module...........................24 +4.2 Function declaration............................................24 +4.3 Amplification matrix............................................25 +4.4 Characteristic polynomial.......................................26 +4.5 Automatic denotation............................................26 + +5 H U R W P 28 + +5.1 Conformal mapping...............................................28 +5.2 Investigation of polynomial roots...............................28 + +6 L I N B A N D 30 + +6.1 Program generation..............................................30 +6.2 Choosing the numerical library..................................32 +6.3 Completion of the generated code................................32 + + + + + + + 3 + + + + + + + + + + + + + + + + 1 E X P R E S + =========== + + + + A Module for Transforming Differential + Operators and Equations into an Arbitrary Orthogonal + Coordinate System + + + + This module makes it possible to express various scalar, vector, +and tensor differential equations in any orthogonal coordinate system. +All transformations needed are executed automatically according to the +coordinate system given by the user. The module was implemented +according to the similar MACSYMA module from [1]. + + +1.1 The specification of the coordinate system + ------------------------------------------ + + The coordinate system is specified using the following statement: + + SCALEFACTORS ,,...,,,...,; + ::= 2 | 3 coordinate system dimension + ::= "algebraic expression" the expression of the i-th + Cartesian coordinate in new + coordinates + ::= "identifier" the i-th new coordinate + +All evaluated quantities are transformed into the coordinate system set +by the last SCALEFACTORS statement. By default, if this statement is not +applied, the three-dimensional Cartesian coordinate system is employed. +During the evaluation of SCALEFACTORS statement the metric coefficients, +i.e. scale factors SF(i), of a defined coordinate system are computed +and printed. If the WRCHRI switch is ON, then the nonzero Christoffel +symbols of the coordinate system are printed too. By default the WRCHRI +switch is OFF. + + + + + + + 4 + + + + + + +1.2 The declaration of tensor quantities + ------------------------------------ + + Tensor quantities are represented by identifiers. The VECTORS +declaration declares the identifiers as vectors, the DYADS declaration +declares the identifiers as dyads. i.e. two-dimensional tensors, and the +TENSOR declaration declares the identifiers as tensor variables. The +declarations have the following syntax: + + ,,...,; + ::= VECTORS | DYADS | TENSOR + ::= "identifier" + +The value of the identifier V declared as vector in the two-dimensional +coordinate system is (V(1), V(2)), where V(i) are the components of +vector V. The value of the identifier T declared as a dyad is ((T(1,1), +T(1,2)), (T(2,1), T(2,2))). The value of the tensor variable can be any +tensor (see below). Tensor variables can be used only for a single +coordinate system, after the coordinate system redefining by a new +SCALEFACTORS statement, the tensor variables have to be re-defined using +the assigning statement. + + +1.3 New infix operators + ------------------- + + For four different products between the tensor quantities, new +infix operators have been introduced (in the explaining examples, a +two-dimensional coordinate system, vectors U, V, and dyads T, W are +considered): + + . - scalar product U.V = U(1)*V(1)+U(2)*V(2) + ? - vector product U?V = U(1)*V(2)-U(2)*V(1) + & - outer product U&V = ((U(1)*V(1),U(1)*V(2)), + (U(2)*V(1),U(2)*V(2))) + # - double scalar product T#W = T(1,1)*W(1,1)+T(1,2)*W(1,2)+ + T(2,1)*W(2,1)+T(2,2)*W(2,2) + +The other usual arithmetic infix operators +, -, *, ** can be used in +all situations that have sense (e.g. vector addition, a multiplication +of a tensor by a scalar, etc.). + + +1.4 New prefix operators + -------------------- + + New prefix operators have been introduced to express tensor +quantities in its components and the differential operators over the +tensor quantities: + + VECT - the explicit expression of a vector in its components + DYAD - the explicit expression of a dyad in its components + + 5 + + + + + + + GRAD - differential operator of gradient + DIV - differential operator of divergence + LAPL - Laplace's differential operator + CURL - differential operator of curl + DIRDF - differential operator of the derivative in direction + (1st argument is the directional vector) + +The results of the differential operators are written using the DIFF +operator. DIFF(,) expresses the derivative of +with respect to the coordinate . This operator is not further +simplified. If the user wants to make it simpler as common derivatives, +he performs the following declaration: + + FOR ALL X,Y LET DIFF(X,Y) = DF(X,Y); . + +Then, however, we must realize that if the scalars or tensor quantities +do not directly explicitly depend on the coordinates, their dependencies +have to be declared using the DEPEND statements, otherwise the +derivative will be evaluated to zero. The dependence of all vector or +dyadic components (as dependence of the name of vector or dyad) has to +appear before VECTORS or DYADS declarations, otherwise after these +declarations one has to declare the dependencies of all components. For +formulating the explicit derivatives of tensor expressions, the +differentiation operator DF can be used (e.g. the differentiation of a +vector in its components). + + +1.5 Tensor expressions + ------------------ + + Tensor expressions are the input into the EXPRES module and can +have a variety of forms. The output is then the formulation of the given +tensor expression in the specified coordinate system. The most general +form of a tensor expression is described as follows (the +conditions (d=i) represent the limitation on the dimension of the +coordinate system equalling i): + + ::= | | + ::= "algebraic expression, can contain " | + "tensor variable with scalar value" | + . | # | + (d=2)? | DIV | + LAPL | (d=2) ROT | + DIRDF(,) + ::= "identifier declared by VECTORS statement" | + "tensor variable with vector value" | + VECT(,...,) | - | + + | - | + * | / | + . | . | (d=3) + ? | (d=2) ? | + (d=2) ? | GRAD | + + 6 + + + + + + + DIV | LAPL | (d=3) ROT | + DIRDF(,) | DF(,"usual + further arguments") + ::= "identifier declared by DYADS statement" | + "tensor variable with dyadic value" | + DYAD((,...,),...,(, + ...,)) | - | + | + - | * | / + | . | & | + (d=3) ? | (d=3) ? | + GRAD | DF(,"usual further arguments") + + +1.6 Assigning statement + ------------------- + + The assigning statement for tensor variables has a usual syntax, +namely: + + := + ::= "identifier declared TENSOR" . + +The assigning statement assigns the tensor variable the value of the +given tensor expression, formulated in the given coordinate system. +After a change of the coordinate system, the tensor variables have to be +redefined. + + + +References +---------- + +[1] M. C. Wirth, On the Automation of Computational Physics. PhDr + Thesis. Report UCRL-52996, Lawrence Livermore National + Laboratory, Livermore, 1980. + + + + + + + + + + + + + + + + + + + 7 + + + + + + + + + + + + + + + + 2 I I M E T + ========= + + + + A Module for Discretizing the Systems + of Partial Differential Equations + + + + This program module makes it possible to discretize the specified +system of partial differential equations using the integro-interpolation +method, minimizing the number of the used interpolations in each +independent variable. It can be used for non-linear systems and vector +or tensor variables as well. The user specifies the way of discretizing +individual terms of differential equations, controls the discretization +and obtains various difference schemes according to his own wish. + + +2.1 Specification of the coordinates and the indices corresponding + to them + -------------------------------------------------------------- + + The independent variables of differential equations will be called +coordinates. The names of the coordinates and the indices that will +correspond to the particular coordinates in the difference scheme are +defined using the COORDINATES statement: + + COORDINATES {,} [ INTO + {,}]; + ::= "identifier" - the name of the coordinate + ::= "identifier" - the name of the index + +This statement specifies that the will correspond to the +. A new COORDINATES statement cancels the definitions given by +the preceding COORDINATES statement. If the part [ INTO ... ] is not +included in the statement, the statement assigns the coordinates the +indices I, J, K, L, M, N, respectively. If it is included, the number of +coordinates and the number of indices should be the same. + + + + + + 8 + + + + + + +2.2 Difference grids + ---------------- + + In the discretization, orthogonal difference grids are employed. +In addition to the basic grid, called the integer one, there is another, +the half-integer grid in each coordinate, whose cellular boundary points +lie in the centers of the cells of the integer grid. The designation of +the cellular separating points and centers is determined by the +CENTERGRID switch: if it is ON and the index in the given coordinate is +I, the centers of the grid cells are designated by indices I, I + 1,..., +and the boundary points of the cells by indices I + 1/2,..., if, on the +contrary, the switch is OFF, the cellular centers are designated by +indices I + 1/2,..., and the boundary points by indices I, I + 1,... +(see Fig. 2.1). + + + ON CENTERGRID + I-1/2 I I+1/2 I+1 I+3/2 +---|--------|--------|--------------|--------------|---- + I I+1/2 I+1 I+3/2 I+2 + OFF CENTERGRID + + Figure 2.1 Types of grid + + +In the case of ON CENTERGRID, the indices i,i+1,i-1... thus designate +the centers of the cells of the integer grid and the boundary points of +the cells of the half-integer grid, and, similarly, in the case of OFF +CENTERGRID, the boundaries of the cells of the integer grid and the +central points of the half-integer grid. The meaning of the integer and +half-integer grids depends on the CENTERGRID switch in the described +way. After the package is loaded, the CENTERGRID is ON. Obviously, this +switch is significant only for non-uniform grids with a variable size of +each cell. + The grids can be uniform, i.e. with a constant cell size - the step +of the grid. The following statement: + + GRID UNIFORM,{,}; + +defines uniform grids in all coordinates occurring in it. Those +coordinates that do not occur in the GRID UNIFORM statement are supposed +to have non-uniform grids. + In the outputs, the grid step is designated by the identifier that +is made by putting the character H before the name of the coordinate. +For a uniform grid, this identifier (e.g. for the coordinate X the grid +step HX) has the meaning of a step of an integer or half-integer grids +that are identical. For a non-uniform grid, this identifier is an +operator and has the meaning of a step of an integer grid, i.e. the +length of a cell whose center (in the case of ON CENTERGRID) or +beginning (in the case of OFF CENTERGRID) is designated by a single +argument of this operator. For each coordinate s designated by the + + + 9 + + + + + + +identifier i, this step of the integer non-uniform grid is defined as +follows: + + Hs(i+j) = s(i+j+1/2) - s(i+j-1/2) at ON CENTERGRID + Hs(i+j) = s(i+j+1) - s(i+j) at OFF CENTERGRID + +for all integers j (s(k) designates the value of the coordinate s in the +cellular boundary point subscripted with the index k). The steps of the +half-integer non-uniform grid are not applied in outputs. + + +2.3 Declaring the dependence of functions on coordinates + ---------------------------------------------------- + + In the system of partial differential equations, two types of +functions, in other words dependent variables can occur: namely, the +given functions, whose values are known before the given system is +solved, and the sought functions, whose values are not available until +the system of equations is solved. The functions can be scalar, vector, +or tensor, for vector or tensor functions the EXPRES module has to be +applied at the same time. The names of the functions employed in the +given system and their dependence on the coordinates are specified using +the DEPENDENCE statement. + + DEPENDENCE {,}; + ::= ([],{, + }) + ::= "identifier" - the name of the function + ::= 1|2 tensor order of the function (the value of + the function is 1 - vector, 2 - dyad (two- + dimensional tensor)) + +Every in the statement determines on which +the depends. If the tensor of the function occurs in +the , the is declared as a vector or a dyad. If, +however, the has been declared by the VECTORS and DYADS +statements of the EXPRES module, the user need not present the tensor +. By default, a function without any declaration is regarded as +scalar. In the discretization, all scalar components of tensor functions +are replaced by identifiers that arise by putting successively the +function name and the individual indices of the given component (e.g. +the tensor component T(1,2), written in the EXPRES module as T(1,2), is +represented by the identifier T12). Before the DEPENDENCE statement is +executed, the coordinates have to be defined using the COORDINATES +statement. There may be several DEPENDENCE statements. The DEPENDENCE +statement cancels all preceding determinations of which grids are to be +used for differentiating the function or the equation for this function. +These determinations can be either defined by the ISGRID or GRIDEQ +statements, or computed in the evaluation of the IIM statement. + The GIVEN statement: + + GIVEN {,}; + + 10 + + + + + + + +declares all functions included in it as given functions whose values +are known to the user or can be computed. The CLEARGIVEN statement: + + CLEARGIVEN; + +cancels all preceding GIVEN declarations. If the TWOGRID switch is ON, +the given functions can be differentiated both on the integer and the +half-integer grids. If the TWOGRID switch is OFF, any given function can +be differentiated only on one grid. After the package is loaded, the +TWOGRID is ON. + + +2.4 Functions and difference grids + ------------------------------ + + Every scalar function or scalar component of a vector or a dyadic +function occurring in the discretized system can be discretized in any +of the coordinates either on the integer or half-integer grid. One of +the tasks of the IIMET module is to find the optimum distribution of +each of these dependent variables of the system on the integer and +half-integer grids in all variables so that the number of the performed +interpolations in the integro-interpolation method will be minimal. + Using the statement + + SAME {,}; + +all functions given in one of these declarations will be discretized on +the same grids in all coordinates. In each SAME statement, at least one +of these functions in one SAME statement must be the sought one. If the +given function occurs in the SAME statement, it will be discretized only +on one grid, regardless of the state of the TWOGRID switch. If a vector +or a dyadic function occurs in the SAME statement, what has been said +above relates to all its scalar components. There are several SAME +statements that can be presented. All SAME statements can be canceled by +the following statement: + + CLEARSAME; + +The SAME statement can be successfully used, for example, when the given +function depends on the function sought in a complicated manner that +cannot be included either in the differential equation or in the +difference scheme explicitly, and when both the functions are desired to +be discretized in the same points so that the user will not be forced to +execute the interpolation during the evaluation of the given function. + In some cases, it is convenient too to specify directly which +variable on which grid is to be discretized, for which case the ISGRID +statement is applied: + + ISGRID {,}; + ::= ([,]{,}) + ::= .. , + + 11 + + + + + + + ::= ONE | HALF designation of the integer + (ONE) and half-integer (HALF) + grids + ::= | for the vector + , for the dyadic + it is not presented for the + scalar + ::= *| "natural number from 1 to the space dimension + the space dimension is specified in the EXPRES + module by the SCALEFACTORS statement, * means all + components + +The statement defines that the given functions or their components will +be discretized in the specified coordinates on the specified grids, so +that, for example, the statement ISGRID U (X..ONE,Y..HALF), V(1,Z..ONE), +T(*,1,X..HALF); defines that scalar U will be discretized on the integer +grid in the coordinate X, and on the half-integer one in the coordinate +Y, the first component of vector V will be on the integer grid in the +coordinate Z, and the first column of tensor T will be on the +half-integer grid in the coordinate X. The ISGRID statement can be +applied more times. The functions used in this statement have to be +declared before by the DEPENDENCE statement. + + +2.5 Equations and difference grids + ------------------------------ + + Every equation of the system of partial differential equations is +an equation for some sought function (specified in the IIM statement). +The correspondence between the sought functions and the equations is +mutually unambiguous. The GRIDEQ statement makes it possible to +determine on which grid an individual equation will be discretized in +some or all coordinates + + GRIDEQ {,}; + ::= ({,}) + +Every equation can be discretized in any coordinate either on the +integer or half-integer grid. This statement determines the +discretization of the equations given by the functions included in it in +given coordinates, on given grids. The meaning of the fact that an +equation is discretized on a certain grid is as follows: index I used in +the DIFMATCH statements (discussed in the following section), specifying +the discretization of the basic terms, will be located in the center of +the cell of this grid, and indices I+1/2, I-1/2 from the DIFMATCH +statement on the boundaries of the cell of this grid. The actual name of +the index in the given coordinate is determined using the COORDINATES +statement, and its location on the grid is set by the CENTERGRID switch. + + + + + + 12 + + + + + + +2.6 Discretization of basic terms + ----------------------------- + + The discretization of a system of partial differential equations is +executed successively in individual coordinates. In the discretization +of an equation in one coordinate, the equation is linearized into its +basic terms first that will be discretized independently then. If D is +the designation for the discretization operator in the coordinate x, +this linearization obeys the following rules: + + 1. D(a+b) = D(a)+D(b) + 2. D(-a) = -D(a) + 3. D(p.a) = p.D(a) (p does not depend on the coordinate x) + 4. D(a/p) = D(a)/p + + The linearization lasts as long as some of these rules can be +applied. The basic terms that must be discretized after the +linearization have then the forms of the following quantities: + + 1. The actual coordinate in which the discretization is performed. + 2. The sought function. + 3. The given function. + 4. The product of the quantities 1 - 7. + 5. The quotient of the quantities 1 - 7. + 6. The natural power of the quantities 1 - 7. + 7. The derivative of the quantities 1 - 7 with respect to the + actual coordinate. + +The way of discretizing these basic terms, while the functions are on +integer and half-integer grids, is determined using the DIFMATCH +statement: + + DIFMATCH ,,{{,} + , }; + ::= ALL | "identifier" - the coordinate name from + the COORDINATES statement + ::= | + | + | * + | / | + ** | + DIFF(,[,])| + ({,}) + ::= X + ::= U | V | W + ::= F | G + ::= N | "integer greater than 1" + ::= "integer greater than 2" + ::= = + ::= | + + + 13 + + + + + + + ::= "non-negative integer" + ::= ()| + "natural number"|DI|DIM1|DIP1|DIM2|DIP2| + | - | + + | + * | + / | + () | + ** + ::= X | U | V | W | F | G + ::= | + + | + - + ::= I + = "rational number" + DIFCONST {,}; + ::= "identifier" - the constant parameter of + the difference scheme. + DIFFUNC {,}; + ::= "identifier" - prefix operator, that can + appear in discretized equations (e.g. SIN). + +The first parameter of the DIFMATCH statement determines the coordinate +for which the discretization defined in it is valid. If ALL is used, the +discretization will be valid for all coordinates, and this +discretization is accepted when it has been checked whether there has +been no other discretization defined for the given coordinate and the +given pattern term. Each pattern sought function, occurring in the +pattern term, must be included in the specification of the grids. The +pattern given functions from the pattern term can occur in the grid +specification, but in some cases (see below) need not. In the grid +specification the maximum number of 3 pattern functions may occur. The +discretization of each pattern term has to be specified in all +combinations of the pattern functions occurring in the grid +specification, on the integer and half-integer grids, that is 2**n +variants for the grid specification with n pattern functions +(n=0,1,2,3). The discretized term is the discretization of the pattern +term in the pattern coordinate X in the point X(I) on the pattern grid +(see Fig. 2.2), and the pattern functions occurring in the grid +specification are in the discretized term on the respective grids from +this specification (to the discretized term corresponds the grid +specification preceding it). + + integer grid + X(I-1) X(I) X(I+1) + | DIM1 | DIP1 | +---|------|------|-------------|-------------|-----|-----|--- + | DIM2 | DI | DIP2 | + X(I-3/2) X(I-1/2) X(I+1/2) X(I+3/2) + half-integer grid + + Figure 2.2 Pattern grid + + 14 + + + + + + + +The pattern grid steps defined as + + DIM2 = X(I - 1/2) - X(I - 3/2) + DIM1 = X(I) - X(I - 1) + DI = X(I + 1/2) - X(I - 1/2) + DIP1 = X(I + 1) - X(I) + DIP2 = X(I + 3/2) - X(I + 1/2) + +can occur in the discretized term. + In the integro-interpolation method, the discretized term is +specified by the integral + + =1/(X(I+1/2)-X(I-1/2))*DINT(X(I-1/2),X(I+1/2), + ,X), + +where DINT is operator of definite integration DINT(from, to, function, +variable). The number of interpolations determines how many +interpolations were needed for calculating this integral in the given +discrete form (the function on the integer or half-integer grid). If the +integro-interpolation method is not used, the more convenient is the +distribution of the functions on the half-integer and integer grids, the +smaller number is chosen by the user. The parameters of the difference +scheme defined by the DIFCONST statement can occur in the discretized +expression too (for example, the implicit-explicit scheme on the +implicit layer multiplied by the constant C and on the explicit one by +(1-C)). As a matter of fact, all DIFMATCH statements create a base of +pattern terms with the rules of how to discretize these terms in +individual coordinates under the assumption that the functions occurring +in the pattern terms are on the grids determined in the grid +specification (all combinations must be included). + The DIFMATCH statement does not check whether the discretized term +is actually the discretization of the pattern term or whether in the +discretized term occur the functions from the grid specification on the +grids given by this specification. An example can be the following +definition of the discretization of the first and second derivatives of +the sought function in the coordinate R on a uniform grid: + + DIFMATCH R,DIFF(U,X),U=ONE,2,(U(I+1)-U(I-1))/(2*DI); + U=HALF,0,(U(I+1/2)-U(I-1/2))/DI; + DIFMATCH R,DIFF(U,X,2),U=ONE,0,(U(I+1)-2*U(I)+U(I-1))/DI**2, + U=HALF,2,(U(I+3/2)-U(I+1/2)-U(I-1/2)+U(I-3/2))/(2*DI**2); + + All DIFMATCH statements can be cleared by the statement + + CLEARDIFMATCH; + +After this statement user has to supply its own DIFMATCH statements. + But now back to the discretizing of the basic terms obtained by the +linearization of the partial differential equation, as mentioned at the +beginning of this section. Using the method of pattern matching, for +each basic term a term representing its pattern is found in the base of + + 15 + + + + + + +pattern terms (specified by the DIFMATCH statements). The pattern +matching obeys the following rules: + + 1. The pattern for the coordinate in which the discretization is + executed is the pattern coordinate X. + + 2. The pattern for the sought function is some pattern sought + function, and this correspondence is mutually unambiguous. + + 3. The pattern for the given function is some pattern given + function, or, in case the EQFU switch is ON, some pattern sought + function, and, again, the correspondence of the pattern with the + given function is mutually unambiguous (after loading the EQFU + switch is ON). + + 4. The pattern for the products of quantities is the product of the + patterns of these quantities, irrespective of their sequence. + + 5. The pattern for the quotient of quantities is the quotient of the + patterns of these quantities. + + 6. The pattern for the natural power of a quantity is the same power + of the pattern of this quantity or the power of this quantity with + the pattern exponent N. + + 7. The pattern for the derivative of a quantity with respect to the + coordinate in which the discretization is executed is the derivative + of the pattern of this quantity with respect to the pattern + coordinate X of the same order of differentiation. + + 8. The pattern for the sum of the quantities that have the same + pattern with the identical correspondence of functions and pattern + functions is this common pattern (so that it will not be necessary + to multiply the parentheses during discretizing the products in the + second and further coordinates). + +When matching the pattern of one basic term, the program finds the +pattern term and the functions corresponding to the pattern functions, +maybe also the exponent corresponding to the pattern exponent N. After +determining on which grids the individual functions and the individual +equations will be discretized, which will be discussed in the next +section, the program finds in the pattern term base the discretized term +either with pattern functions on the same grids as are the functions +from the basic term corresponding to them in case that the given +equation is differentiated on the integer grid, or with pattern +functions on inverse grids (an inverse integer grid is a half-integer +grid, and vice versa) compared with those used for the functions from +the basic term corresponding to them in case the given equation is +differentiated on the half-integer grid (the discretized term in the +DIFMATCH statement is expressed in the point X(I), i.e. on the integer +grid, and holds for the discretizing of the equation on the integer +grid; with regard to the substitutions for the pattern index I mentioned + + 16 + + + + + + +later, it is possible to proceed in this way and not necessary to define +the discretization in the points X(I+1/2) too, i.e. on the half-integer +grid). The program replaces in the thus obtained discretized term: + + 1. The pattern coordinate X with the particular coordinate s in + which the discretization is actually performed. + + 2. The pattern index I and the grid steps DIM2, DIM1, DI, DIP1, DIP2 + with the expression given in table 2.1 according to the state of the + CENTERGRID switch and to the fact whether the given equation is + discretized on the integer or half-integer grid (i is the index + corresponding to the coordinate s according to the COORDINATES + statement, the grid steps were defined in section 2.2) + + 3. The pattern functions with the corresponding functions from the + basic term and, possibly, the pattern exponent with the + corresponding exponent from the basic term. + +-------------------------------------------------------------------- +| the equation discretized on | +| the integer grid | the half-integer grid | +| CENTERGRID |CENTERGRID|CENTERGRID| CENTERGRID | +| OFF | ON | OFF | ON | +|------------------------------------------------------------------| +| I | i | i+1/2 | +|----|-------------------------------------------------------------| +|DIM2|(Hs(i-2)+Hs(i-1))/2| Hs(i-1) |(Hs(i-1)+Hs(i))/2 | +|DIM1| Hs(i-1) | (Hs(i-1)+Hs(i))/2 | Hs(i) | +|DI |(Hs(i-1)+Hs(i))/2 | Hs(i) |(Hs(i)+Hs(i+1))/2 | +|DIP1| Hs(i) | (Hs(i)+Hs(i+1))/2 | Hs(i+1) | +|DIP2|(Hs(i)+Hs(i+1))/2 | Hs(i+1) |(Hs(i+1)+Hs(i+2))/2| +-------------------------------------------------------------------- + + Table 2.1 Values of the pattern index and + the pattern grid steps. + + More details will be given now to the discretization of the given +functions and its specification. The given function may occur in the +SAME statement, which makes it bound with some sought function, in other +words it can be discretized only on one grid. This means that all basic +terms, in which this function occurs, must have their pattern terms in +whose discretization definitions by the DIFMATCH statement the pattern +function corresponding to the mentioned given function has to occur in +the grid specification. If the given function does not occur in the SAME +statement and the TWOGRID switch is OFF, i.e. it can be discretized only +on one grid again, the same holds true. If, however, the given function +does not occur in the SAME statement and the TWOGRID switch is ON, i.e. +it can be discretized simultaneously on the integer and the half-integer +grids, then the basic terms of the equations including this function +have their pattern terms in whose discretization definitions the pattern +function corresponding to the mentioned given function need not occur in +the grid specification. If, however, in spite of all, this pattern + + 17 + + + + + + +function in the discretization definition does occur in the grid +specification, it is the alternative with a smaller number of +interpolations occurring in the DIFMATCH statement that is selected for +each particular basic term with a corresponding pattern (the given +function can be on the integer or half-integer grid). + Before the discretization is executed, it is necessary to define +using the DIFMATCH statements the discretization of all pattern terms +that are the patterns of all basic terms of all equations appearing in +the discretized system in all coordinates. The fact that the pattern +terms of the basic terms of partial equations occur repeatedly in +individual systems has made it possible to create a library of the +discretizations of the basic types of pattern terms using the +integro-interpolation method. This library is a component part of the +IIMET module (in its end) and makes work easier for those users who find +the pattern matching mechanism described here too difficult. New +DIFMATCH statements have to be created by those whose equations will +contain a basic term having no pattern in this library, or those who +need another method to perform the discretization. The described +implemented algorithm of discretizing the basic terms is sufficiently +general to enable the use of a nearly arbitrary discretization on +orthogonal grids. + + +2.7 Discretization of a system of equations + --------------------------------------- + + All statements influencing the run of the discretization that one +want use in this run have to be executed before the discretization is +initiated. The COORDINATES, DEPENDENCE, and DIFMATCH statements have to +occur in all applications. Further, if necessary, the GRID UNIFORM, +GIVEN, ISGRID, GRIDEQ, SAME, and DIFCONST statements can be used, or +some of the CENTREGRID, TWOGRID, EQFU, and FULLEQ switches can be set. +Only then the discretization of a system of partial differential +equations can be started using the IIM statement: + + IIM {,,}; + ::= "identifier" - the name of the array for storing + the result + ::= "identifier" - the name of the function + whose behavior is described by the + equation + ::= = + ::= "algebraic expression" , the derivatives are + designated by the DIFF operator + ::= "algebraic expression" + +Hence, in the IIM statement the name of the array in which the resulting +difference schemes will be stored, and the pair sought function - +equation, which describes this function, are specified. The meaning of +the relation between the sought function and its equation during the +discretization lies in the fact that the sought function is preferred in +its equation so that the interpolation is not, if possible, used in + + 18 + + + + + + +discretizing the terms of this equation that contain it. In the +equations, the functions and the coordinates appear as identifiers. The +identifiers that have not been declared as functions by the DEPENDENCE +statement or as coordinates by the COORDINATES statement are considered +constants independent of the coordinates. The partial derivatives are +expressed by the DIFF operator that has the same syntax as the standard +differentiation operator DF. The functions and the equations can also +have the vector or tensor character. If these non-scalar quantities are +applied, the EXPRES module has to be used together with the IIMET +module, and also non-scalar differential operators such as GRAD, DIV, +etc. can be employed. + The sequence performed by the program in the discretization can be +briefly summed up in the following items: + + 1. If there are non-scalar functions or equations in a system of + equations, they are automatically converted into scalar quantities + by means of the EXPRES module. + + 2. In each equation, the terms containing derivatives are + transferred to the left side, and the other terms to the right side + of the equation. + + 3. For each coordinate, with respect to the sequence in which they + occur in the COORDINATES statement, the following is executed: + + a) It is determined on which grids all functions and all equations + in the actual coordinate will be discretized, and simultaneously the + limits are kept resulting from the ISGRID, GRIDEQ, and SAME + statements if they were used. Such a distribution of functions and + equations on the grids is selected among all possible variants that + ensures the minimum sum of all numbers of the interpolations of the + basic terms (specified by the DIFMATCH statement) of all equations + if the FULLEQ switch is ON, or of all left sides of the equations if + the FULLEQ switch is OFF (after the loading the FULLEQ switch is + ON). + + b) The discretization itself is executed, as specified by the + DIFMATCH statements. + + 4. If the array name is A, then if there is only one scalar equation + in the IIM statement, the discretized left side of this equation is + stored in A(0) and the discretized right side in A(1) (after the + transfer mentioned in item 2), if there are more scalar equations + than one in the IIM statement, the discretization of the left side + of the i-th scalar equation is stored in A(i,0) and the + discretization of the right side in A(i,1). + +The IIM statement can be used more times during one program run, and +between its calls, the discretizing process can be altered using other +statements of this module. + + + + 19 + + + + + + +2.8 Error messages + -------------- + + The IIMET module provides error messages in the case of the user's +errors. Similarly as in the REDUCE system, the error reporting is marked +with five stars : "*****" on the line start. Some error messages are +identical with those of the REDUCE system. Here are given some other +error messages that require a more detailed explanation: + +***** Matching of X term not found + - the discretization of the pattern term that is the pattern of + the basic term printed on the place X has not been + defined (using the DIFMATCH statement) +***** Variable of type F not defined on grids in DIFMATCH + - in the definition of the discretizing of the pattern term + the given functions were not used in the grid + specification and are needed now +***** X Free vars not yet implemented + - in the grid specification in the DIFMATCH statement + more than 3 pattern functions were used +***** All grids not given for term X + - in the definition of the discretization of the pattern of + the basic term printed on the place X not all + necessary combinations of the grid specification + of the pattern functions were presented + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 20 + + + + + + + + + + + + + + + + 3 A P P R O X + =========== + + + + + A Module for Determining the Precision Order + of the Difference Scheme + + + + This module makes it possible to determine the differential +equation that is solved by the given difference scheme, and to determine +the order of accuracy of the solution of this scheme in the grid steps +in individual coordinates. The discrete function values are expanded +into the Taylor series in the specified point. + + +3.1 Specification of the coordinates and the indices + corresponding to them + ------------------------------------------------ + + The COORDINATES statement, described in the IIMET module manual, +specifying the coordinates and the indices corresponding to them is the +same for this program module as well. It has the same meaning and +syntax. The present module version assumes a uniform grid in all +coordinates. The grid step in the input difference schemes has to be +designated by an identifier consisting of the character H and the name +of the coordinate, e.g. the step of the coordinate X is HX. + + +3.2 Specification of the Taylor expansion + ------------------------------------- + + In the determining of the approximation order, all discrete values +of the functions are expanded into the Taylor series in all coordinates. +In order to determine the Taylor expansion, the program needs to know +the point in which it performs this expansion, and the number of terms +in the Taylor series in individual coordinates. The center of the Taylor +expansion is specified by the CENTER statement and the number of terms +in the Taylor series in individual coordinates by the MAXORDER +statement: + + + 21 + + + + + + + CENTER
{,
}; +
::= = + ::= "rational number" + MAXORDER {,}; + ::= = + ::= "natural number" + +The increment in the CENTER statement determines that the center of the +Taylor expansion in the given coordinate will be in the point specified +by the index I + , where I is the index corresponding to this +coordinate, defined using the COORDINATES statement, e.g. the following +example + + COORDINATE T,X INTO N,J; + CENTER T = 1/2, X = 1; + MAXORDER T = 2, X = 3; + +specifies that the center of the Taylor expansion will be in the point +(t(n+1/2),x(j+1)) and that until the second derivatives with respect to +t (second powers of ht) and until the third derivatives with respect to +x (third powers of hx) the expansion will be performed. The CENTER and +MAXORDER statements can be placed only after the COORDINATES statement. +If the center of the Taylor expansion is not defined in some coordinate, +it is supposed to be in the point given by the index of this coordinate +(i.e. zero increment). If the number of the terms of the Taylor +expansion is not defined in some coordinate, the expansion is performed +until the third derivatives with respect to this coordinate. + + +3.3 Function declaration + -------------------- + + All functions whose discrete values are to be expanded into the +Taylor series must be declared using the FUNCTIONS statement: + + FUNCTIONS {,}; + ::= "identifier" + +In the specification of the difference scheme, the functions are used as +operators with one or more arguments, designating the discrete values of +the functions. Each argument is the sum of the coordinate index (from +the COORDINATES statement) and a rational number. If some index is +omitted in the arguments of a function, this functional value is +supposed to lie in the point in which the Taylor expansion is performed, +as specified by the CENTER statement. In other words, if the COORDINATES +and CENTER statements, shown in the example in the previous section, are +valid, then it holds that U(N+1) = U(N+1,J+1) and U(J-1) = U(N+1/2,J-1). +The FUNCTIONS statement can declare both the sought and the known +functions for the expansion. + + + + + 22 + + + + + + +3.4 Order of accuracy determination + ------------------------------- + + The order of accuracy of the difference scheme is determined by the +APPROX statement: + + APPROX (); + ::= = + ::= "algebraic expression" + +In the difference scheme occur the functions in the form described in +the preceding section, the coordinate indices and the grid steps +described in section 3.1, and the other symbolic parameters of the +difference scheme. The APPROX statement expands all discrete values of +the functions declared in the FUNCTIONS statement into the Taylor series +in all coordinates (the point in which the Taylor expansion is performed +is specified by the CENTER statement, and the number of the expansion +terms by the MAXORDER statement), substitutes the expansions into the +difference scheme, which gives a modified differential equation. The +modified differential equation, containing the grid steps too, is an +equation that is really solved by the difference scheme (into the given +orders in the grid steps). + The partial differential equation, whose solution is approximated +by the difference scheme, is determined by replacing the grid steps by +zeros and is displayed after the following message: + + "Difference scheme approximates differential equation" + +Then the following message is displayed: + + "with orders of approximation:" + +and the lowest powers (except for zero) of the grid steps in all +coordinates, occurring in the modified differential equation are +written. If the PRAPPROX switch is ON, then the rest of the modified +differential equation is printed. If this rest is added to the left hand +side of the approximated differential equation, one obtain modified +equation. By default the PRAPPROX switch is OFF. If the grid steps are +found in some denominator in the modified equation, i.e. with a negative +exponent, the following message is written, preceding the approximated +differential equation: + + "Reformulate difference scheme, grid steps remain in denominator" + +and the approximated differential equation is not correctly determined +(one of its sides is zero). Generally, this message means that there is +a term in the difference scheme that is not a difference replacement of +the derivative, i.e. the ratio of the differences of the discrete +function values and the discrete values of the coordinates (the steps of +the difference grid). The user, however, must realize that in some cases +such a term occurs purposefully in the difference scheme (e.g. on the +grid boundary to keep the scheme conservative). + + 23 + + + + + + + + + + + + + + + + 4 C H A R P O L + ============= + + + + A Module for Calculating the Amplification Matrix + and the Characteristic Polynomial of the + Difference Scheme + + + + This program module is used for the first step of the stability +analysis of the difference scheme using the Fourier method. It +substitutes the Fourier components into the difference scheme, +calculates the amplification matrix of the scheme for transition from +one time layer to another, and computes the characteristic polynomial of +this matrix. + + +4.1 Commands common with the IIMET module + ------------------------------------- + + The COORDINATES and GRID UNIFORM statements, described in the IIMET +module manual, are applied in this module as well, having the same +meaning and syntax. The time coordinate is assumed to be designated by +the identifier T. The present module version requires all coordinates to +have uniform grids, i.e. to be declared in the GRID UNIFORM statement. +The grid step in the input difference schemes has to be designated by +the identifier consisting of the character H and the name of the +coordinate, e.g. the step of the time coordinate T is HT. + + +4.2 Function declaration + -------------------- + + The UNFUNC statement declares the names of the sought functions +used in the difference scheme: + + UNFUNC {,} + ::= "identifier" - the name of the sought function + +The functions are used in the difference schemes as operators with one +or more arguments for designating the discrete function values. Each + + 24 + + + + + + +argument is the sum of the index (from the COORDINATES statement) and a +rational number. If some index is omitted in the function arguments, +this function value is supposed to lie in the point specified only by +this index, which means that, with the indices N and J and the function +U, it holds that U(N+1) = U(N+1,J) and U(J-1) = U(N,J-1). As two-step +(in time) difference schemes may be used only, the time index may occur +either completely alone in the arguments, or in the sum with a one. + + +4.3 Amplification matrix + -------------------- + + The AMPMAT matrix operator computes the amplification matrix of a +two-step difference scheme. Its argument is an one column matrix of the +dimension (1,k), where k is the number of the equations of the +difference scheme, that contains the difference equations of this scheme +as algebraic expressions equal to the difference of the right and left +sides of the difference equations. The value of the AMPMAT matrix +operator is the square amplification matrix of the dimension (k,k). +During the computation of the amplification matrix, two new identifiers +are created for each spatial coordinate. The identifier made up of the +character K and the name of the coordinate represents the wave number in +this coordinate, and the identifier made up of the character A and the +name of the coordinate represents the product of this wave number and +the grid step in this coordinate divided by the least common multiple of +all denominators occurring in the scheme in the function argument +containing the index of this coordinate. On the output an equation is +displayed defining the latter identifier. For example, if in the case of +function U and index J in the coordinate X the expression U(J+1/2) has +been used in the scheme (and, simultaneously, no denominator higher than +2 has occurred in the arguments with J), the following equation is +displayed: AX: = (KX*HX)/2. The definition of these quantities As allows +to express every sum occurring in the argument of the exponentials as +the sum of these quantities multiplied by integers, so that after a +transformation, the amplification matrix will contain only sin(As) and +cos(As) (for all spatial coordinates s). The AMPMAT operator performs +these transformations automatically. If the PRFOURMAT switch is ON +(after the loading it is ON), the matrices H0 and H1 (the amplification +matrix is equal to -H1**(-1)*H0) are displayed during the evaluation of +the AMPMAT operator. These matrices can be used for finding a suitable +substitution for the goniometric functions in the next run for a greater +simplification. + The TCON matrix operator transforms the square matrix into a +Hermit-conjugate matrix, i.e. a transposed and complex conjugate one. +Its argument is the square matrix and its value is Hermit-conjugate +matrix of the argument. The Hermit-conjugate matrix is used for testing +the normality and unitarity of the amplification matrix in the +determining of the sufficient stability condition. + + + + + + 25 + + + + + + +4.4 Characteristic polynomial + ------------------------- + + The CHARPOL operator calculates the characteristic polynomial of +the given square matrix. The variable of the characteristic polynomial +is designated by the LAM identifier. The operator has one argument, the +square matrix, and its value is its characteristic polynomial in LAM. + + +4.5 Automatic denotation + -------------------- + + Several statements and procedures are designed for automatic +denotation of some parts of algebraic expressions by identifiers. This +denotation is namely useful when we obtain very large expressions, which +cannot fit into the available memory. We can denote subparts of an +expression from the previous step of calculation by identifiers, replace +these subparts by these identifiers and continue the analytic +calculation only with these identifiers. Every time we use this +technique we have to explicitly survive in processed expressions those +algebraic quantities which will be necessary in the following steps of +calculation. The process of denotation and replacement is performed +automatically and the algebraic values which are denoted by these new +identifiers can be written out at any time. We describe how this +automatic denotation can be used. + The statement DENOTID defines the beginning letters of newly +created identifiers. Its syntax is + + DENOTID ; + ::= "identifier" + +After this statement the new identifiers created by the operators +DENOTEPOL and DENOTEMAT will begin with the letters of the identifier + used in this statement. Without using any DENOTID statement all new +identifiers will begin with one letter A. We suggest to use this +statement every time before using operators DENOTEPOL or DENOTEMAT with +some new identifier and to choose identifiers used in this statement in +such a way that the newly created identifiers are not equal to any +identifiers used in the expressions you are working with. + The operator DENOTEPOL has one argument, a polynomial in LAM, and +denotes the real and imaginary part of its coefficients by new +identifiers. The real part of the j-th LAM power coefficient is denoted +by the identifier R0j and the imaginary part by I0j, where +is the identifier used in the last DENOTID statement. The denotation is +done only for non-numeric coefficients. The value of this operator is +the polynomial in LAM with coefficients constructed from the new +identifiers. The algebraic expressions which are denoted by these +identifiers are stored as LISP data structure standard quotient in the +LISP variable DENOTATION!* (assoc. list). + The operator DENOTEMAT has one argument, a matrix, and denotes the +real and imaginary parts of its elements. The real part of the (j,k) +matrix element is denoted by the identifier Rjk and the imaginary + + 26 + + + + + + +part by Ijk. The returned value of the operator is the original +matrix with non-numeric elements replaced by Rjk + I*Ijk. Other +matters are the same as for the DENOTEPOL operator. + The statement PRDENOT has the syntax + + PRDENOT; + +and writes from the variable DENOTATION!* the definitions of all new +identifiers introduced by the DENOTEPOL and DENOTEMAT operators since +the last call of CLEARDENOT statement (or program start) in the format +defined by the present setting of output control declarations and +switches. The definitions are written in the same order as they have +been entered, so that the definitions of the first DENOTEPOL or +DENOTEMAT operators are written first. This order guarantees that this +statement can be utilized directly to generate a semantically correct +numerical program (the identifiers from the first denotation can appear +in the second one, etc.). + The statement CLEARDENOT with the syntax + + CLEARDENOT; + +clears the variable DENOTATION!*, so that all denotations saved earlier +by the DENOTEPOL and DENOTEMAT operators in this variable are lost. The +PRDENOT statement succeeding this statement writes nothing. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 27 + + + + + + + + + + + + + + + + 5 H U R W P + ========= + + + + A Module for Polynomial Roots Locating + + + + This module is used for verifying the stability of a polynomial, +i.e. for verifying if all roots of a polynomial lie in a unit circle +with its center in the origin. By investigating the characteristic +polynomial of the difference scheme, the user can determine the +conditions of the stability of this scheme. + + +5.1 Conformal mapping + ----------------- + + The HURW operator transforms a polynomial using the conformal +mapping LAM=(z+1)/(z-1). Its argument is a polynomial in LAM and its +value is a transformed polynomial in LAM (LAM=z). If P is a polynomial +in LAM, then it holds: all roots LAM1i of the polynomial P are in their +absolute values smaller than one, i.e. |LAM1i|<1, iff the real parts of +all roots LAM2i of the HURW(P) polynomial are negative, i.e. Re +(LAM2i)<0. + The elimination of the unit polynomial roots (LAM=1), which has to +occur before the conformal transformation is performed, is made by the +TROOT1 operator. The argument of this operator is a polynomial in LAM +and its value is a polynomial in LAM not having its root equal to one +any more. Mostly, the investigated polynomial has some more parameters. +For some special values of those parameters, the polynomial may have a +unit root. During the evaluation of the TROOT1 operator, the condition +concerning the polynomial parameters is displayed, and if it is +fulfilled, the resulting polynomial has a unit root. + + +5.2 Investigation of polynomial roots + --------------------------------- + + The HURWITZP operator checks whether a polynomial is the Hurwitz +polynomial, i.e. whether all its roots have negative real parts. The +argument of the HURWITZP operator is a polynomial in LAM with real or + + 28 + + + + + + +complex coefficients, and its value is YES if the argument is the +Hurwitz polynomial. It is NO if the argument is not the Hurwitz +polynomial, and COND if it is the Hurwitz polynomial when the conditions +displayed by the HURWITZP operator during its analysis are fulfilled. +These conditions have the form of inequalities and contain algebraic +expressions made up of the polynomial coefficients. The conditions have +to be valid either simultaneously, or they are designated and a +proposition is created from them by the AND and OR logic operators that +has to be fulfilled (it is the condition concerning the parameters +occurring in the polynomial coefficient) by a polynomial to be the +Hurwitz one. This proposition is the sufficient condition, the necessary +condition is the fulfillment of all the inequalities displayed. + If the HURWITZP operator is called interactively, the user is +directly asked if the inequalities are or are not valid. The user +responds "Y" if the displayed inequality is valid, "N" if it is not, and +"?" if he does not know whether the inequality is true or not. + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 29 + + + + + + + + + + + + + + + + 6 L I N B A N D + ============= + + + + A Module for Generating the Numeric Program for + Solving a System of Linear Algebraic Equations + with Band Matrix + + + + The LINBAND module generates the numeric program in the FORTRAN +language, which solves a system of linear algebraic equations with band +matrix using the routine from the LINPACK, NAG ,IMSL or ESSL program +library. As input data only the system of equations is given to the +program. Automatically, the statements of the FORTRAN language are +generated that fill the band matrix of the system in the corresponding +memory mode of chosen library, call the solving routine, and assign the +chosen variables to the solution of the system. The module can be used +for solving linear difference schemes often having the band matrix. + + +6.1 Program generation + ------------------ + + The program in the FORTRAN language is generated by the +GENLINBANDSOL statement (the braces in this syntax definition occur +directly in the program and do not have the usual meaning of the +possibility of repetition, they designate REDUCE lists): + + GENLINBANDSOL (,,{}); + ::= "natural number" + ::= "natural number" + ::= | , + ::= {,} | + ::= "kernel" + ::= = + ::= "algebraic expression" + ::= "algebraic expression" + ::= {DO,{,,,},} + ::= "identifier" + ::= + + + 30 + + + + + + + ::= + ::= + ::= "algebraic expression" with natural value + (evaluated in FORTRAN) + ::= | , + ::= {,} + +The first and second argument of the GENLINBANDSOL statement specifies +the number of the lower (below the main diagonal) and the upper +diagonals of the band matrix of the system. The system of linear + algebraic equations is specified by means of lists expressed by braces +{ } in the REDUCE system. The variables of the equation system can be +identifiers, but most probably they are operators with an argument or +with arguments that are analogous to array in FORTRAN. The left side of +each equation has to be a linear combination of the system variables, +the right side, on the contrary, is not allowed to contain any variables +of the system. The sequence of the band matrix lines is given by the +sequence of the equations, and the sequence of the columns by the +sequence of the variables in the list describing the equation system. + The meaning of the loop in the system list is similar to that of +the DO loop of the FORTRAN language. The individual variables and +equations described by the loop are obtained as follows: + + 1. = . + 2. The value is substituted into the variables and + equations of the loop, by which further variables and + equations of the system are obtained. + 3. is increased by . + 4. If is less or equal , then go to step 2, else all + variables and equations described by the loop have already been + obtained. + +The variables and equations of the system included in the loop usually +contain the loop parameter, which mostly occur in the operator arguments +in the REDUCE language, or in the array indices in the FORTRAN language. + If NL = , NU = , and for some loop F = , T += , S = and N is the number of the equations in the loop +, it has to be true that + + UP(NL/N) + UP(NU/N) < DOWN((T-F)/S) + +where UP represents the rounding-off to a higher natural number, and +DOWN the rounding-off to a lower natural number. With regard to the fact +that, for example, the last variable before the loop is not required to +equal the last variable from the loop system, into which the loop +parameter equal to F-S is substituted, when the band matrix is being +constructed, from the FORTRAN loop that corresponds to the loop from the +specification of the equation system, at least the first NL +variables-equations have to be moved to precede the FORTRAN loop, and at + + + + 31 + + + + + + +least the last NU variables-equations have to be moved to follow this +loop in order that the correspondence of the system variables in this +loop with the system variables before and after this loop will be +secured. And this move requires the above mentioned condition to be +fulfilled. As, in most cases, NL/N and NU/N are small with respect to +(T-F)/S, this condition does not represent any considerable constrain. + The loop parameters , , and can be natural numbers +or expressions that must have natural values in the run of the FORTRAN +program. + + +6.2 Choosing the numerical library + ------------------------------ + + The user can choose the routines of which numerical library will be +used in the generated FORTRAN code. The supported numerical libraries +are: LINPACK, NAG, IMSL and ESSL (IBM Engineering and Scientific +Subroutine Library) . The routines DGBFA, DGBSL (band solver) and DGTSL +(tridiagonal solver) are used from the LINPACK library, the routines +F01LBF, F04LDF (band solver) and F01LEF, F04LEF (tridiagonal solver) are +used from the NAG library, the routine LEQT1B is used from the IMSL +library and the routines DGBF, DGBS (band solver) and DGTF, DGTS +(tridiagonal solver) are used from the ESSL library. By default the + LINPACK library routines are used. The using of other libraries is +controlled by the switches NAG,IMSL and ESSL. All these switches are by +default OFF. If the switch IMSL is ON then the IMSL library routine is +used. If the switch IMSL is OFF and the switch NAG is ON then NAG +library routines are used. If the switches IMSL and NAG are OFF and the +switch ESSL is ON then the ESSL library is used. During generating the +code using LINPACK, NAG or ESSL libraries the special routines are use +for systems with tridiagonal matrices, because tridiagonal solvers are +faster than the band matrix solvers. + + +6.3 Completion of the generated code + -------------------------------- + + The GENLINBANDSOL statement generates a block of FORTRAN code ( a +block of statements of the FORTRAN language) that performs the solution +of the given system of linear algebraic equations. In order to be used, +this block of code has to be completed with some declarations and +statements, thus getting a certain envelope that enables it to be +integrated into the main program. + In order to be able to work, the generated block of code has to be +preceded by: + + 1. The declaration of arrays as described by the comments generated + into the FORTRAN code (near the calling of library routines) + + 2. The assigning the values to the integer variables describing the + real dimensions of used arrays (again as described in generated + FORTRAN comments) + + 32 + + + + + + + 3. The filling of the variables that can occur in the loop parameters. + + 4. The filling or declaration of all variables and arrays occurring in + the system equations, except for the variables of the system of linear + equations. + + 5. The definition of subroutine ERROUT the call to which is generated + after some routines found that the matrix is algorithmically singular + + The mentioned envelope for the generated block can be created +manually, or directly using the GENTRAN program package for generating +numeric programs. The LINBAND module itself uses the GENTRAN package, +and the GENLINBANDSOL statement can be applied directly in the input +files of the GENTRAN package (template processing). The GENTRAN package +has to be loaded prior to loading of the LINBAND module. + The generated block of FORTRAN code has to be linked with the +routines from chosen numerical library. + + + + + + + +References +---------- + +[1] R. Liska: Numerical Code Generation for Finite Difference Schemes + Solving. In IMACS World Congress on Computation and Applied + Mathematics. Dublin, July 22-26, 1991, Dublin,(In press). + + + + + + + + + + + + + + + + + + + + + + + + 33 + Index: r36/doc/FPS.TEX ================================================================== --- r36/doc/FPS.TEX +++ r36/doc/FPS.TEX @@ -1,188 +1,188 @@ -\documentstyle[11pt,reduce]{article} -\title{{\tt FPS}\\ -A Package for the\\ -Automatic Calculation \\ -of Formal Power Series} -\date{} -\author{Wolfram Koepf\\ - ZIB Berlin \\ - Email: {\tt Koepf@ZIB-Berlin.de} -\\ -\\ - Present \REDUCE{} form by \\ - Winfried Neun \\ - ZIB Berlin \\ - Email: {\tt Neun@ZIB-Berlin.de}} -\begin{document} -\maketitle - -\section{Introduction} -This package can expand functions of certain type into -their corresponding Laurent-Puiseux series as a sum of terms of the form -\begin{displaymath} -\sum_{k=0}^{\infty} a_{k} (x-x_{0})^{m k/n + s} -\end{displaymath} -where $m$ is the `symmetry number', $s$ is the `shift number', -$n$ is the `Puiseux number', -and $x_0$ is the `point of development'. The following types are -supported: -\begin{itemize} -\item -{\bf functions of `rational type'}, which are either rational or have a -rational derivative of some order; -\item -{\bf functions of `hypergeometric type'} where $a(k+m)/a(k)$ is a rational -function for some integer $m$; -\item -{\bf functions of `explike type'} which satisfy a linear homogeneous -differential equation with constant coefficients. -\end{itemize} - -The FPS package is an implementation of the method -presented in \cite{Koepf:92}. The implementations of this package -for {\sc Maple} (by D.\ Gruntz) and {\sc Mathematica} (by W.\ Koepf) -served as guidelines for this one. - -Numerous examples can be found in \cite{Koepf:93a}--\cite{Koepf:93b}, -most of which are contained in the test file {\tt fps.tst}. Many -more examples can be found in the extensive bibliography of Hansen \cite{Han}. - - -\section{\REDUCE{} operator {\tt FPS}} -The FPS Package must be loaded first by: -\begin{verbatim} -load FPS; -\end{verbatim} -{\tt FPS(f,x,x0)} tries to find a formal power -series expansion for {\tt f} with respect to the variable {\tt x} -at the point of development {\tt x0}. -It also works for formal Laurent (negative exponents) and Puiseux series -(fractional exponents). If the third -argument is omitted, then {\tt x0:=0} is assumed. - -Examples: {\tt FPS(asin(x)\verb+^+2,x)} results in -\begin{verbatim} - - 2*k 2*k 2 2 - x *2 *factorial(k) *x -infsum(----------------------------,k,0,infinity) - factorial(2*k + 1)*(k + 1) -\end{verbatim} -{\tt FPS(sin x,x,pi)} gives -\begin{verbatim} - 2*k k - ( - pi + x) *( - 1) *( - pi + x) -infsum(------------------------------------,k,0,infinity) - factorial(2*k + 1) -\end{verbatim} -and {\tt FPS(sqrt(2-x\verb+^+2),x)} yields -\begin{verbatim} - 2*k - - x *sqrt(2)*factorial(2*k) -infsum(--------------------------------,k,0,infinity) - k 2 - 8 *factorial(k) *(2*k - 1) -\end{verbatim} -Note: The result contains one or more {\tt infsum} terms such that it does -not interfere with the {\REDUCE} operator {\tt sum}. In graphical oriented -REDUCE interfaces this operator results in the usual $\sum$ notation. - -If possible, the output is given using factorials. In some cases, the -use of the Pochhammer symbol {\tt pochhammer(a,k)}$:=a(a+1)\cdots(a+k-1)$ -is necessary. - -The operator {\tt FPS} uses the operator {\tt SimpleDE} of the next section. - -If an error message of type -\begin{verbatim} -Could not find the limit of: -\end{verbatim} -occurs, you can set the corresponding limit yourself and try a -recalculation. In the computation of {\tt FPS(atan(cot(x)),x,0)}, -REDUCE is not able to find the value for the limit -{\tt limit(atan(cot(x)),x,0)} since the {\tt atan} function is multi-valued. -One can choose the branch of {\tt atan} such that this limit equals -$\pi/2$ so that we may set -\begin{verbatim} -let limit(atan(cot(~x)),x,0)=>pi/2; -\end{verbatim} -and a recalculation of {\tt FPS(atan(cot(x)),x,0)} -yields the output {\tt pi - 2*x} which is -the correct local series representation. - -\section{\REDUCE{} operator {\tt SimpleDE}} - -{\tt SimpleDE(f,x)} tries to find a homogeneous linear differential -equation with polynomial coefficients for $f$ with respect to $x$. -Make sure that $y$ is not a used variable. -The setting {\tt factor df;} is recommended to receive a nicer output form. - -Examples: {\tt SimpleDE(asin(x)\verb+^+2,x)} then results in -\begin{verbatim} - 2 -df(y,x,3)*(x - 1) + 3*df(y,x,2)*x + df(y,x) -\end{verbatim} -{\tt SimpleDE(exp(x\verb+^+(1/3)),x)} gives -\begin{verbatim} - 2 -27*df(y,x,3)*x + 54*df(y,x,2)*x + 6*df(y,x) - y -\end{verbatim} -and {\tt SimpleDE(sqrt(2-x\verb+^+2),x)} yields -\begin{verbatim} - 2 -df(y,x)*(x - 2) - x*y -\end{verbatim} -The depth for the search of a differential equation for {\tt f} is -controlled by the variable {\tt fps\verb+_+search\verb+_+depth}; -higher values for {\tt fps\verb+_+search\verb+_+depth} -will increase the chance to find the solution, but increases the -complexity as well. The default value for {\tt fps\verb+_+search\verb+_+depth} -is 5. For {\tt FPS(sin(x\verb+^+(1/3)),x)}, or -{\tt SimpleDE(sin(x\verb+^+(1/3)),x)} e.\ g., a setting -{\tt fps\verb+_+search\verb+_+depth:=6} is necessary. - -The output of the FPS package can be influenced by the -switch {\tt tracefps}. Setting {\tt on tracefps} causes various -prints of intermediate results. - -\section{Problems in the current version} -The handling of logarithmic singularities is not yet implemented. - -The rational type implementation is not yet complete. - -The support of special functions \cite{Koepf:94} -will be part of the next version. - -\begin{thebibliography}{9} - -\bibitem{Han} -E.\ R. Hansen, {\em A table of series and products.} -Prentice-Hall, Englewood Cliffs, NJ, 1975. - -\bibitem{Koepf:92} Wolfram Koepf, -{\em Power Series in Computer Algebra}, -J.\ Symbolic Computation 13 (1992) - -\bibitem{Koepf:93a} Wolfram Koepf, -{\em Examples for the Algorithmic Calculation of Formal -Puiseux, Laurent and Power series}, -SIGSAM Bulletin 27, 1993, 20-32. - -\bibitem{Koepf:93b} Wolfram Koepf, -{\em Algorithmic development of power series.} In: -Artificial intelligence and symbolic mathematical computing, -ed.\ by J.\ Calmet and J.\ A.\ Campbell, -International Conference AISMC-1, Karlsruhe, Germany, August 1992, Proceedings, -Lecture Notes in Computer Science {\bf 737}, Springer-Verlag, -Berlin--Heidelberg, 1993, 195--213. - -\bibitem{Koepf:94} Wolfram Koepf, -{\em Algorithmic work with orthogonal polynomials and special functions.} -Konrad-Zuse-Zentrum Berlin (ZIB), Preprint SC 94-5, 1994. - -\end{thebibliography} - -\end{document} - - - +\documentstyle[11pt,reduce]{article} +\title{{\tt FPS}\\ +A Package for the\\ +Automatic Calculation \\ +of Formal Power Series} +\date{} +\author{Wolfram Koepf\\ + ZIB Berlin \\ + Email: {\tt Koepf@ZIB-Berlin.de} +\\ +\\ + Present \REDUCE{} form by \\ + Winfried Neun \\ + ZIB Berlin \\ + Email: {\tt Neun@ZIB-Berlin.de}} +\begin{document} +\maketitle + +\section{Introduction} +This package can expand functions of certain type into +their corresponding Laurent-Puiseux series as a sum of terms of the form +\begin{displaymath} +\sum_{k=0}^{\infty} a_{k} (x-x_{0})^{m k/n + s} +\end{displaymath} +where $m$ is the `symmetry number', $s$ is the `shift number', +$n$ is the `Puiseux number', +and $x_0$ is the `point of development'. The following types are +supported: +\begin{itemize} +\item +{\bf functions of `rational type'}, which are either rational or have a +rational derivative of some order; +\item +{\bf functions of `hypergeometric type'} where $a(k+m)/a(k)$ is a rational +function for some integer $m$; +\item +{\bf functions of `explike type'} which satisfy a linear homogeneous +differential equation with constant coefficients. +\end{itemize} + +The FPS package is an implementation of the method +presented in \cite{Koepf:92}. The implementations of this package +for {\sc Maple} (by D.\ Gruntz) and {\sc Mathematica} (by W.\ Koepf) +served as guidelines for this one. + +Numerous examples can be found in \cite{Koepf:93a}--\cite{Koepf:93b}, +most of which are contained in the test file {\tt fps.tst}. Many +more examples can be found in the extensive bibliography of Hansen \cite{Han}. + + +\section{\REDUCE{} operator {\tt FPS}} +The FPS Package must be loaded first by: +\begin{verbatim} +load FPS; +\end{verbatim} +{\tt FPS(f,x,x0)} tries to find a formal power +series expansion for {\tt f} with respect to the variable {\tt x} +at the point of development {\tt x0}. +It also works for formal Laurent (negative exponents) and Puiseux series +(fractional exponents). If the third +argument is omitted, then {\tt x0:=0} is assumed. + +Examples: {\tt FPS(asin(x)\verb+^+2,x)} results in +\begin{verbatim} + + 2*k 2*k 2 2 + x *2 *factorial(k) *x +infsum(----------------------------,k,0,infinity) + factorial(2*k + 1)*(k + 1) +\end{verbatim} +{\tt FPS(sin x,x,pi)} gives +\begin{verbatim} + 2*k k + ( - pi + x) *( - 1) *( - pi + x) +infsum(------------------------------------,k,0,infinity) + factorial(2*k + 1) +\end{verbatim} +and {\tt FPS(sqrt(2-x\verb+^+2),x)} yields +\begin{verbatim} + 2*k + - x *sqrt(2)*factorial(2*k) +infsum(--------------------------------,k,0,infinity) + k 2 + 8 *factorial(k) *(2*k - 1) +\end{verbatim} +Note: The result contains one or more {\tt infsum} terms such that it does +not interfere with the {\REDUCE} operator {\tt sum}. In graphical oriented +REDUCE interfaces this operator results in the usual $\sum$ notation. + +If possible, the output is given using factorials. In some cases, the +use of the Pochhammer symbol {\tt pochhammer(a,k)}$:=a(a+1)\cdots(a+k-1)$ +is necessary. + +The operator {\tt FPS} uses the operator {\tt SimpleDE} of the next section. + +If an error message of type +\begin{verbatim} +Could not find the limit of: +\end{verbatim} +occurs, you can set the corresponding limit yourself and try a +recalculation. In the computation of {\tt FPS(atan(cot(x)),x,0)}, +REDUCE is not able to find the value for the limit +{\tt limit(atan(cot(x)),x,0)} since the {\tt atan} function is multi-valued. +One can choose the branch of {\tt atan} such that this limit equals +$\pi/2$ so that we may set +\begin{verbatim} +let limit(atan(cot(~x)),x,0)=>pi/2; +\end{verbatim} +and a recalculation of {\tt FPS(atan(cot(x)),x,0)} +yields the output {\tt pi - 2*x} which is +the correct local series representation. + +\section{\REDUCE{} operator {\tt SimpleDE}} + +{\tt SimpleDE(f,x)} tries to find a homogeneous linear differential +equation with polynomial coefficients for $f$ with respect to $x$. +Make sure that $y$ is not a used variable. +The setting {\tt factor df;} is recommended to receive a nicer output form. + +Examples: {\tt SimpleDE(asin(x)\verb+^+2,x)} then results in +\begin{verbatim} + 2 +df(y,x,3)*(x - 1) + 3*df(y,x,2)*x + df(y,x) +\end{verbatim} +{\tt SimpleDE(exp(x\verb+^+(1/3)),x)} gives +\begin{verbatim} + 2 +27*df(y,x,3)*x + 54*df(y,x,2)*x + 6*df(y,x) - y +\end{verbatim} +and {\tt SimpleDE(sqrt(2-x\verb+^+2),x)} yields +\begin{verbatim} + 2 +df(y,x)*(x - 2) - x*y +\end{verbatim} +The depth for the search of a differential equation for {\tt f} is +controlled by the variable {\tt fps\verb+_+search\verb+_+depth}; +higher values for {\tt fps\verb+_+search\verb+_+depth} +will increase the chance to find the solution, but increases the +complexity as well. The default value for {\tt fps\verb+_+search\verb+_+depth} +is 5. For {\tt FPS(sin(x\verb+^+(1/3)),x)}, or +{\tt SimpleDE(sin(x\verb+^+(1/3)),x)} e.\ g., a setting +{\tt fps\verb+_+search\verb+_+depth:=6} is necessary. + +The output of the FPS package can be influenced by the +switch {\tt tracefps}. Setting {\tt on tracefps} causes various +prints of intermediate results. + +\section{Problems in the current version} +The handling of logarithmic singularities is not yet implemented. + +The rational type implementation is not yet complete. + +The support of special functions \cite{Koepf:94} +will be part of the next version. + +\begin{thebibliography}{9} + +\bibitem{Han} +E.\ R. Hansen, {\em A table of series and products.} +Prentice-Hall, Englewood Cliffs, NJ, 1975. + +\bibitem{Koepf:92} Wolfram Koepf, +{\em Power Series in Computer Algebra}, +J.\ Symbolic Computation 13 (1992) + +\bibitem{Koepf:93a} Wolfram Koepf, +{\em Examples for the Algorithmic Calculation of Formal +Puiseux, Laurent and Power series}, +SIGSAM Bulletin 27, 1993, 20-32. + +\bibitem{Koepf:93b} Wolfram Koepf, +{\em Algorithmic development of power series.} In: +Artificial intelligence and symbolic mathematical computing, +ed.\ by J.\ Calmet and J.\ A.\ Campbell, +International Conference AISMC-1, Karlsruhe, Germany, August 1992, Proceedings, +Lecture Notes in Computer Science {\bf 737}, Springer-Verlag, +Berlin--Heidelberg, 1993, 195--213. + +\bibitem{Koepf:94} Wolfram Koepf, +{\em Algorithmic work with orthogonal polynomials and special functions.} +Konrad-Zuse-Zentrum Berlin (ZIB), Preprint SC 94-5, 1994. + +\end{thebibliography} + +\end{document} + + + Index: r36/doc/GENTRAN.BIB ================================================================== --- r36/doc/GENTRAN.BIB +++ r36/doc/GENTRAN.BIB @@ -1,85 +1,85 @@ -@BOOK{FORTRAN, - KEY = "American National Standards Institute", - TITLE = "American National Standard Programming Language {FORTRAN}", - PUBLISHER = "American National Standards Institute", - SERIES = "{ANS X3.9}", - ADDRESS = "New York", - YEAR = 1978} - -@INPROCEEDINGS{Gates:84, - AUTHOR = "Barbara L. Gates and Paul S. Wang", - TITLE = "A {LISP}-Based {RATFOR} Code Generator", - BOOKTITLE = "Proceedings of the 1984 {MACSYMA} User's Conference", - ADDRESS = "Schenectady, New York", MONTH = "July", YEAR = 1984} - -@INPROCEEDINGS{Gates:85, - AUTHOR = "Barbara L. Gates and J. A. van Hulzen", - TITLE = "Automatic Generation of Optimized Programs", - BOOKTITLE = "Proc. {EUROCAL} '85", YEAR = 1985, - MONTH = "April"} - -@ARTICLE{Gates:85a, - AUTHOR = "Barbara L. Gates", - TITLE = "Gentran: An Automatic Code Generation Facility -for {REDUCE}", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "24-42", MONTH = "August"} - -@TECHREPORT{Gates:85b, - AUTHOR = "Barbara L. Gates", - TITLE = "Gentran User's Manual - {REDUCE} Version", - INSTITUTION = "Twente University of Technology, Department of -Computer Science, The Netherlands", TYPE = "Memorandum", - YEAR = 1985, NUMBER = "INF-85-11", MONTH = "June"} - -@INPROCEEDINGS{Gates:86, - AUTHOR = "Barbara L. Gates", - TITLE = "A Numerical Code Generation Facility for {REDUCE}", - BOOKTITLE = "Proc. {SYMSAC} '86", - YEAR = 1986, PAGES = "94-99", MONTH = "July"} - -@MANUAL{Kernighan:79, - AUTHOR = "B. W. Kernighan", - TITLE = "{RATFOR} -- A Preprocessor for a Rational Fortran", - SERIES = "{UNIX} Programmer's Manual", - VOLUME = "2B", EDITION = "Seventh", - PUBLISHER = "Bell Telephone Laboratories, Inc.", - ADDRESS = "Murray Hill, New Jersey", - YEAR = 1979} - -@BOOK{Kernighan:78, - AUTHOR = "B. W. Kernighan and Dennis M. Ritchie", - TITLE = "The {C} Programming Language", - PUBLISHER = "Prentice-Hall", - ADDRESS = "Englewood Cliffs, New Jersey", - YEAR = 1978} - -@ARTICLE{Wang:86, - AUTHOR = "Payl S. Wang", - TITLE = "{FINGER}: A Symbolic System for Automatic Generation of -Numerical Programs in Finite Element Analysis", - JOURNAL = "Journal of Symbolic Computation", - VOLUME = 2, YEAR = 1986} - -@MASTERSTHESIS{vandenHeuvel:86ms, - AUTHOR = "Pim van den Heuvel", - TITLE = "Aspects of Program Generation Related to Automatic -Differentiation", - SCHOOL = "Twente University of Technology", - ADDRESS = "Department of Computer Science, Enschede, The Netherlands", - MONTH = "December", YEAR = 1986} - -@INPROCEEDINGS{vanHulzen:89, - AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof and B. L. Gates and -M. C. Van Heerwaarden", - TITLE = "A Code Optimization Package for {REDUCE}", - BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", - YEAR = 1989, PAGES = "163-170", - COMMENT = {Lecture Notes.}} - -@INPROCEEDINGS{Wang:84, - AUTHOR = "Paul S. Wang and T. Y. P. Chang and J. A. van Hulzen", - TITLE = "Code Generation and Optimization for Finite Element Analysis", - BOOKTITLE = "{EUROSAM} '84 Conference Proceedings", - PUBLISHER = "Springer-Verlag", SERIES = "{LNCS} Series", YEAR = 1984} - +@BOOK{FORTRAN, + KEY = "American National Standards Institute", + TITLE = "American National Standard Programming Language {FORTRAN}", + PUBLISHER = "American National Standards Institute", + SERIES = "{ANS X3.9}", + ADDRESS = "New York", + YEAR = 1978} + +@INPROCEEDINGS{Gates:84, + AUTHOR = "Barbara L. Gates and Paul S. Wang", + TITLE = "A {LISP}-Based {RATFOR} Code Generator", + BOOKTITLE = "Proceedings of the 1984 {MACSYMA} User's Conference", + ADDRESS = "Schenectady, New York", MONTH = "July", YEAR = 1984} + +@INPROCEEDINGS{Gates:85, + AUTHOR = "Barbara L. Gates and J. A. van Hulzen", + TITLE = "Automatic Generation of Optimized Programs", + BOOKTITLE = "Proc. {EUROCAL} '85", YEAR = 1985, + MONTH = "April"} + +@ARTICLE{Gates:85a, + AUTHOR = "Barbara L. Gates", + TITLE = "Gentran: An Automatic Code Generation Facility +for {REDUCE}", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1985, VOLUME = 19, NUMBER = 3, PAGES = "24-42", MONTH = "August"} + +@TECHREPORT{Gates:85b, + AUTHOR = "Barbara L. Gates", + TITLE = "Gentran User's Manual - {REDUCE} Version", + INSTITUTION = "Twente University of Technology, Department of +Computer Science, The Netherlands", TYPE = "Memorandum", + YEAR = 1985, NUMBER = "INF-85-11", MONTH = "June"} + +@INPROCEEDINGS{Gates:86, + AUTHOR = "Barbara L. Gates", + TITLE = "A Numerical Code Generation Facility for {REDUCE}", + BOOKTITLE = "Proc. {SYMSAC} '86", + YEAR = 1986, PAGES = "94-99", MONTH = "July"} + +@MANUAL{Kernighan:79, + AUTHOR = "B. W. Kernighan", + TITLE = "{RATFOR} -- A Preprocessor for a Rational Fortran", + SERIES = "{UNIX} Programmer's Manual", + VOLUME = "2B", EDITION = "Seventh", + PUBLISHER = "Bell Telephone Laboratories, Inc.", + ADDRESS = "Murray Hill, New Jersey", + YEAR = 1979} + +@BOOK{Kernighan:78, + AUTHOR = "B. W. Kernighan and Dennis M. Ritchie", + TITLE = "The {C} Programming Language", + PUBLISHER = "Prentice-Hall", + ADDRESS = "Englewood Cliffs, New Jersey", + YEAR = 1978} + +@ARTICLE{Wang:86, + AUTHOR = "Payl S. Wang", + TITLE = "{FINGER}: A Symbolic System for Automatic Generation of +Numerical Programs in Finite Element Analysis", + JOURNAL = "Journal of Symbolic Computation", + VOLUME = 2, YEAR = 1986} + +@MASTERSTHESIS{vandenHeuvel:86ms, + AUTHOR = "Pim van den Heuvel", + TITLE = "Aspects of Program Generation Related to Automatic +Differentiation", + SCHOOL = "Twente University of Technology", + ADDRESS = "Department of Computer Science, Enschede, The Netherlands", + MONTH = "December", YEAR = 1986} + +@INPROCEEDINGS{vanHulzen:89, + AUTHOR = "J. A. van Hulzen and B. J. A. Hulshof and B. L. Gates and +M. C. Van Heerwaarden", + TITLE = "A Code Optimization Package for {REDUCE}", + BOOKTITLE = "Proc. of {ISSAC} '89", PUBLISHER = "{ACM} Press, New York", + YEAR = 1989, PAGES = "163-170", + COMMENT = {Lecture Notes.}} + +@INPROCEEDINGS{Wang:84, + AUTHOR = "Paul S. Wang and T. Y. P. Chang and J. A. van Hulzen", + TITLE = "Code Generation and Optimization for Finite Element Analysis", + BOOKTITLE = "{EUROSAM} '84 Conference Proceedings", + PUBLISHER = "Springer-Verlag", SERIES = "{LNCS} Series", YEAR = 1984} + Index: r36/doc/GENTRAN.TEX ================================================================== --- r36/doc/GENTRAN.TEX +++ r36/doc/GENTRAN.TEX @@ -1,5732 +1,5732 @@ -\documentstyle[11pt,reduce]{article} -\title{GENTRAN User's Manual \\ REDUCE Version} -\date{} -\author{Barbara L. Gates \\ RAND \\ -Santa Monica CA 90407-2138 USA \\[0.05in] -{\em Updated for {\REDUCE} 3.4 by} \\[0.05in] -Michael C. Dewar \\ -The University of Bath \\ -Email: miked@nag.co.uk} -\begin{document} -\maketitle - -\index{GENTRAN ! package} \index{GENTRAN package !} - -\begin{center} February 1991 \end{center} - -GENTRAN is an automatic code GENerator and TRANslator which runs under -REDUCE and VAXIMA\index{VAXIMA}. It constructs complete numerical -programs based on sets of algorithmic specifications and symbolic -expressions. Formatted FORTRAN, RATFOR or C code can be generated -through a series of interactive commands or under the control of a -template processing routine. Large expressions can be automatically -segmented into subexpressions of manageable size, and a special -file-handling mechanism maintains stacks of open I/O channels to allow -output to be sent to any number of files simultaneously and to -facilitate recursive invocation of the whole code generation process. -GENTRAN provides the flexibility necessary to handle most code -generation applications. This manual describes usage of the GENTRAN -package for REDUCE. - -\subsection*{Acknowledgements} - -The GENTRAN package was created at Kent State University to generate -numerical code for computations in finite element analysis. I would -like to thank Prof. Paul Wang for his guidance and many suggestions -used in designing the original package for VAXIMA. - -The second version of GENTRAN was implemented at Twente University of -Technology to run under REDUCE. It was designed to be interfaced with -a code optimization facility created by Dr. J. A. van Hulzen. I would -like to thank Dr. van Hulzen for all of his help in the implementation -of GENTRAN in RLISP during a stay at his university in The -Netherlands. - -Finally, I would like to thank Dr. Anthony Hearn of the RAND -Corporation for his help in better integrating GENTRAN into the REDUCE -environment. - -\section{INTRODUCTION} - -Solving a problem in science or engineering is often a two-step -process. First the problem is modeled mathematically and derived -symbolically to provide a set of formulas which describe how to solve -the problem numerically. Next numerical programs are written based on -this set of formulas to efficiently compute specific values for given -sets of input. Computer algebra systems such as REDUCE -provide powerful tools for use in the formula-derivation phase but -only provide primitive program-coding tools. The GENTRAN -package~\cite{Gates:85,Gates:85a,Gates:85b,Gates:86} -has been constructed to automate the tedious, -time consuming and error-prone task of writing numerical programs -based on a set of symbolic expressions. - -\subsection{The GENTRAN Code Generator and Translator} -The GENTRAN code GENeration and TRANslation package, originally -implemented in Franz LISP to run under VAXIMA~\cite{Gates:84}, is now also -implemented in RLISP to run under REDUCE. Although GENTRAN -was originally created specifically to generate numerical -code for use with an existing FORTRAN-based finite element analysis -package~\cite{Wang:86,Wang:84}, it was designed -to provide the flexibility required to handle most code generation -applications. GENTRAN contains code generation commands, file-handling -commands, mode switches, and global variables, all of which are -accessible from both the algebraic and symbolic modes of REDUCE to -give the user maximal control over the code generation process. Formatted -\index{FORTRAN} \index{RATFOR} \index{C} -FORTRAN~\cite{FORTRAN}, RATFOR~\cite{Kernighan:79}, C~\cite{Kernighan:78}, -or PASCAL code can be generated from algorithmic specifications, -i.e., descriptions of the behaviour of the target numerical program expressed -in the REDUCE programming language, and from symbolically derived expressions -and formulas. - -In addition to arithmetic expressions and assignment statements, -GENTRAN can also generate type declarations and control-flow -structures. Code generation can be guided by user-supplied -template file(s) to insert generated code into pre-existing program -skeletons, or it can be accomplished interactively through a series -of translation commands without the use of template files. Special -mode switches enable the user to turn on or off specific features such as -automatic segmentation of large expressions, and global variables -allow the user to modify the code formatting process. Generated -code can be sent to one or more files and, optionally, to -the user's terminal. Stacks of open I/O channels facilitate temporary -output redirection and recursive invocation of the code generation process. - -\subsection{Code Optimization} -\index{optimization, code} -A code optimizer~\cite{vanHulzen:89}, which runs under REDUCE, has -been constructed to reduce the arithmetic complexity of a set of -symbolic expressions (see the SCOPE package on -page~\pageref{SCOPE:intro}). It optimizes them by extracting common -subexpressions and assigning them to temporary variables which are -inserted in their places. The optimization technique is based on -mapping the expressions onto a matrix of coefficients and exponents -which are searched for patterns corresponding to the common -subexpressions. Due to this process the size of the expressions is -often considerably reduced. - -GENTRAN and the Code Optimizer have been interfaced to make it -possible to generate optimized numerical programs directly -\index{GENTRANOPT switch} from REDUCE. Setting the switch {\tt -GENTRANOPT} {\bf ON} specifies that all sequences of assignment -statements are to be optimized before being converted to numerical -code. - -\subsection{Organization of the Manual} -The remainder of this manual is divided into five sections. Sections -\ref{GENTRAN:inter} and \ref{GENTRAN:template} describe code -generation. Section \ref{GENTRAN:inter} explains interactive code -generation, the expression segmentation facility, and how temporary -variables can be generated; then section \ref{GENTRAN:template} -explains how code generation can be guided by a user-supplied template -file. Section \ref{GENTRAN:output} describes methods of output -redirection, and section \ref{GENTRAN:mod} describes user-accessible -global variables and mode switches which alter the code generation -process. Finally section \ref{GENTRAN:examples} presents three -complete examples. - -\subsubsection{Typographic Conventions} -The following conventions are used in the syntactic definitions of -commands in this manual: -\begin{itemize} -\item[{-}] -Command parts which must be typed exactly as shown are given in -{\bf BOLD PRINT}. -\item[{-}] -User-supplied arguments are {\it emphasized}. -\item[{-}] -[ ... ] indicate optional command parts. -\end{itemize} -The syntax of each GENTRAN command is shown terminated with a {\bf ;}. -However, either {\bf ;} or {\bf \$} can be used to terminate any -command with the usual REDUCE meaning: {\bf ;} indicates that the -returned value is to be printed, while {\bf \$} indicates that printing -of the returned value is to be suppressed. - -Throughout this manual it is stated that file name arguments must be -atoms. The exact type of atom (e.g., identifier or string) is -system and/or site dependent. The instructions for the implementation -being used should therefore be consulted. - -\section{Interactive Code Generation}\label{GENTRAN:inter} -GENTRAN generates numerical programs based on algorithmic specifications -in the REDUCE programming language and derived symbolic expressions -\index{FORTRAN} \index{RATFOR} \index{PASCAL} \index{C} -produced by REDUCE evaluations. FORTRAN, RATFOR, PASCAL or C code can -be produced. Type declarations can be generated, and comments and -other literal strings can be inserted into the generated code. In -addition, large arithmetic expressions can be automatically segmented -into a sequence of subexpressions of manageable size. - -This section explains how to select the target language, generate -code, control expression segmentation, and how to generate temporary -variable names. - -\subsection{Target Language Selection} -\label{gentranlang} -Before generating code, the target numerical language must be -selected. GENTRAN is currently able to generate FORTRAN, RATFOR, -PASCAL and C \ttindex{GENTRANLANG"!*} code. The global variable {\bf -GENTRANLANG!*} determines which type of code is produced. {\bf -GENTRANLANG!*} can be set in algebraic or symbolic mode. It can be -set to any value, but only four atoms have special meaning: {\bf -FORTRAN}, {\bf RATFOR}, {\bf PASCAL} and {\bf C}. Any other value is -assumed to mean {\bf FORTRAN}. {\bf GENTRANLANG!*} is always -initialized to {\bf FORTRAN}. - - -\subsection{Translation} -\label{translation} -\index{GENTRAN ! command} -The {\bf GENTRAN} (GENerate/TRANslate) command is used to generate -numerical code and also to translate code from algorithmic -specifications in the REDUCE programming language to code in the -target numerical language. Section~\ref{generation} explains code -{\em generation}. This section explains code {\em translation}. - -A substantial subset of all expressions and statements in the REDUCE -programming language can be translated directly into numerical code. -The {\bf GENTRAN} command takes a REDUCE expression, statement, or -procedure definition, and translates it into code in the target -language. - -\begin{describe}{Syntax:} -{\bf GENTRAN} {\it stmt} [ {\bf OUT} {\it f1,f2,\dots\ ,fn} ]{\it ;} -\end{describe} - -\begin{describe}{Arguments:} -{\it stmt} is any REDUCE expression, statement (simple, compound, or -group), or procedure definition that can be translated by GENTRAN into the -target language\footnote{See~\ref{appa} for a complete listing of REDUCE -expressions and statements that can be translated.} -{\it stmt} may contain any number of calls -to the special functions {\bf EVAL}, {\bf DECLARE}, and {\bf LITERAL} -(see sections~\ref{translation}~--~\ref{comments}). - -{\it f1,f2,\dots\ ,fn } is an optional argument list containing one or more -{\it f}'s, where each {\it f} is one of: -\par -\begin{tabular}{lll} -{\it an atom} &= &an output file\\ -{\bf T} &= &the terminal\\ -{\bf NIL} &= &the current output file(s)\\ -\ttindex{ALL"!*} {\bf ALL!*} &= &all files currently open for output \\ -& & by GENTRAN (see section~\ref{GENTRAN:output})\\ -\end{tabular} -\end{describe} -\index{side effects} -\begin{describe}{Side Effects:} -{\bf GENTRAN} translates {\it stmt} into formatted code in the target language. - -If the optional part of the command is not given, generated code is simply -written to the current output file. However, if it is -given, then the current output file is temporarily overridden. Generated -code is written to each file represented by -{\it f1,f2,\dots\ ,fn} for this command only. Files which were open prior -to the call to {\bf GENTRAN} will remain open after the call, and files -which did not exist prior to the call will be created, opened, written to, -and closed. The output stack will be exactly the same both before and -after the call. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRAN} returns the name(s) of the file(s) to which code was written. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** OUTPUT FILE ALREADY EXISTS - OVERWRITE FILE? (Y/N) -\end{verbatim} -\begin{verbatim} -***** WRONG TYPE OF ARG -\end{verbatim} -exp -\begin{verbatim} -***** CANNOT BE TRANSLATED -\end{verbatim} -\end{describe} -\begin{describe}{\example\footnote{When the {\bf PERIOD} flag (default -setting: ON) is turned on, all \ttindex{PERIOD} -integers are automatically printed as real numbers except exponents, -subscripts in subscripted variables, and index values in DO-type loops.}} -\index{GENTRAN package ! example} -\begin{verbatim} -1: GENTRANLANG!* := 'FORTRAN$ - -2: GENTRAN -2: FOR I:=1:N DO -2: V(I) := 0$ - - DO 25001 I=1,N - V(I)=0.0 -25001 CONTINUE - -3: GENTRANLANG!* := 'RATFOR$ - -4: GENTRAN -4: FOR I:=1:N DO -4: FOR J:=I+1:N DO -4: << -4: X(J,I) := X(I,J); -4: Y(J,I) := Y(I,J) -4: >>$ - -DO I=1,N - DO J=I+1,N - { - X(J,I)=X(I,J) - Y(J,I)=Y(I,J) - } - -5: GENTRANLANG!* := 'C$ - -6: GENTRAN -6: P := FOR I:=1:N PRODUCT I$ - -{ - P=1; - for (I=1;I<=N;++I) - P*=I; -} - -7: GENTRANLANG!* := 'PASCAL$ - -8: GENTRAN -8: S := FOR I := 1:10 SUM V(I)$ -BEGIN - S:=0; - FOR I:=1 TO 10 DO - S:=S+V(I) -END; -\end{verbatim} -\end{describe} - - -\index{numeric code} Translation is a convenient method of producing -numerical code when the exact behaviour of the resultant code is -known. It gives the REDUCE user who is familiar with the syntax of -statements in the REDUCE programming language the ability to write -code in a numerical programming language without knowing the exact -syntactical requirements of the language. However the {\em real} -power of the {\bf GENTRAN} command lies in its ability to generate -code: it can produce numerical code from symbolic expressions derived -in REDUCE in addition to translating statements directly. This aspect -is described in section~\ref{generation}. - -\subsection{Precision} -\label{precision} -\index{precision} \index{DOUBLE switch} -By default {\bf GENTRAN} generates constants and type declarations in -single precision form. If the user requires double precision output -then the switch {\bf DOUBLE} must be set {\bf ON}. This does the -following: - -\begin{itemize} -\item Declarations of appropriate type are converted to their double -precision counterparts. In FORTRAN and RATFOR this means that objects of type -{\it REAL\/} are converted to objects of type {\it DOUBLE PRECISION\/} -and objects of type {\it COMPLEX\/} are converted to {\it COMPLEX*16\/} -\footnote{This is not part of the ANSI FORTRAN standard. Some compilers -accept {\it DOUBLE COMPLEX\/} as well as, or instead of, {\it COMPLEX*16\/}, -and some accept neither.}. \index{DOUBLE PRECISION} \index{COMPLEX} -\index{COMPLEX*16} -In C the counterpart of {\it float\/} is {\it double\/}, and of {\it int\/} -is {\it long\/}. There is no complex data type and trying to translate complex -objects causes an error. -\item Similarly subprograms are given their correct type where appropriate. -\item In FORTRAN and RATFOR {\it REAL\/} and {\it COMPLEX\/} numbers are -printed with the correct double precision format. -\item Intrinsic functions are converted to their double precision counterparts -(e.g. in FORTRAN $SIN \rightarrow DSIN$ etc.). -\end{itemize} - -\subsubsection{Intrinsic FORTRAN and RATFOR functions.} -An attempt is made to convert the arguments of intrinsic functions to -the correct type. For example: -\begin{verbatim} -5: GENTRAN f:=sin(1)$ - F=SIN(1.0) - -6: GENTRAN f:=sin(x)$ - F=SIN(REAL(X)) - -7: GENTRAN DECLARE <>$ - -8: GENTRAN f:=sin(x)$ - F=SIN(X) -\end{verbatim} -Which function is used to coerce the argument may, of course, depend on the -setting of the switch {\bf DOUBLE}. - -\subsubsection{Number of printed floating point digits.} -\index{PRECISION command} \index{PRINT"!-PRECISION command} -To ensure the correct number of floating point digits are -generated it may be necessary to use either the {\bf PRECISION} or -{\bf PRINT!-PRECISION} commands. The former alters the number of -digits REDUCE calculates, the latter only the number of digits REDUCE -prints. Each takes an integer argument. It is not possible to set -the printed precision higher than the actual precision. Calling {\bf -PRINT!-PRECISION} with a negative argument causes the printed -precision to revert to the actual precision. - -\begin{verbatim} -1: on rounded$ - -2: precision 16$ - -3: 1/3; - -0.333 33333 33333 333 - -4: print!-precision 6$ - -5: 1/3; - -0.333333 - -6: print!-precision(-1)$ - -7: 1/3; - -0.333 33333 33333 333 -\end{verbatim} - -\subsection{Code Generation: Evaluation Prior to Translation} -\label{generation} -Section~\ref{translation} showed how REDUCE statements and expressions -can be translated directly into the target language. This section -shows how to indicate that parts of those statements and expressions -are to be handed to REDUCE to be evaluated before being translated. -In other words, this section explains how to generate numerical code -from algorithmic specifications (in the REDUCE programming language) -and symbolic expressions. Each of the following four subsections -describes a special function or operator that can be used to request -partial or full evaluation of expressions prior to translation. Note -that these functions and operators have the described effects {\it -only} when applied to arguments to the {\bf GENTRAN} function and that -evaluation is done in algebraic or symbolic mode, depending on the -value of the REDUCE variable {\bf !*MODE}.\ttindex{"!*MODE} - -\subsubsection{The EVAL Function} -\label{eval} -\begin{describe}{Syntax:} -{\bf EVAL} {\it exp} -\end{describe} \ttindex{EVAL} -\begin{describe}{Argument:} -{\it exp} is any REDUCE expression or statement which, after evaluation -by REDUCE, results in an expression that can be translated by -GENTRAN into the target language. -\end{describe} -\begin{describe}{Side Effect:} -When {\bf EVAL} is called on an expression which is to be translated, it -tells {\bf GENTRAN} to give the expression to REDUCE -for evaluation first, and then to translate the result of that evaluation. -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -The following formula, F, has been derived symbolically: -\begin{verbatim} - 2 -2*X - 5*X + 6 -\end{verbatim} -We wish to generate an assignment statement for the quotient -of F and its derivative. -\begin{verbatim} -1: GENTRAN -1: Q := EVAL(F)/EVAL(DF(F,X))$ - - Q=(2.0*X**2-(5.0*X)+6.0)/(4.0*X-5.0) -\end{verbatim} -\end{describe} - -\subsubsection{The :=: Operator} -\index{:=:} -\label{rsetq} \index{GENTRAN ! preevaluation} \index{rsetq operator} -In many applications, assignments must be generated in which the -left-hand side is some known variable name, but the -right-hand side is an expression that must be evaluated. For -this reason, a special operator is provided to indicate that the expression -on the right-hand side is to be evaluated prior to translation. This -special operator is {\bf :=:} (i.e., the usual REDUCE assignment operator -with an extra ``:'' on the right). -\begin{describe}{\example} \index{GENTRAN package ! example} -\begin{verbatim} -1: GENTRAN -1: DERIV :=: DF(X^4-X^3+2*x^2+1,X)$ - - DERIV=4.0*X**3-(3.0*X**2)+4.0*X -\end{verbatim} -\end{describe} -Each built-in operator in REDUCE has an alternative alphanumeric identifier -associated with it. Similarly, the GENTRAN {\bf :=:} operator has a -special identifier associated with it: {\bf RSETQ} may be used \ttindex{RSETQ} -interchangeably with {\bf :=:} on input. -\subsubsection{The ::= Operator} -\label{lsetq} -\index{matrices ! in GENTRAN} -When assignments to matrix or array elements must be generated, many -times the indices of the element must be evaluated first. The special operator -\index{::=} \index{lsetq operator} -{\bf ::=} can be used within a call to {\bf GENTRAN} -to indicate that the indices of the matrix or -array element on the left-hand side of the assignment are to -be evaluated prior to translation. (This is the usual REDUCE -assignment operator with an extra ``:'' on the left.) -\begin{describe}{\example}\index{GENTRAN package ! example} -We wish to generate assignments which assign zeros to all elements -on the main diagonal of M, an n x n matrix. -\begin{verbatim} -10: FOR j := 1 : 8 DO -10: GENTRAN -10: M(j,j) ::= 0$ - - M(1,1)=0.0 - M(2,2)=0.0 - : - : - M(8,8)=0.0 -\end{verbatim} -\end{describe} - -{\bf LSETQ} may be used interchangeably with {\bf ::=} on input.\ttindex{LSETQ} -\subsubsection{The ::=: Operator} -\label{lrsetq} -\index{::=:} \index{lrsetq operator} -In applications in which evaluated expressions are to be assigned to -array elements with evaluated subscripts, the {\bf ::=:} operator can be -used. It is a combination of the {\bf ::=} and {\bf :=:} operators described -in sections~\ref{rsetq} and ~\ref{lsetq}. -\index{matrices ! in GENTRAN} - -\newpage -\begin{describe}{\example}\index{GENTRAN package ! example} -The following matrix, M, has been derived symbolically: -\begin{verbatim} -( A 0 -1 1) -( ) -( 0 B 0 0) -( ) -( -1 0 C -1) -( ) -( 1 0 -1 D) -\end{verbatim} -We wish to generate assignment statements for those elements -on the main diagonal of the matrix. -\begin{verbatim} -10: FOR j := 1 : 4 DO -10: GENTRAN -10: M(j,j) ::=: M(j,j)$ - - M(1,1)=A - M(2,2)=B - M(3,3)=C - M(4,4)=D -\end{verbatim} -\end{describe} -The alternative alphanumeric identifier associated with {\bf ::=:} is -{\bf LRSETQ}.\ttindex{LRSETQ} - -\subsection{Explicit Type Declarations} -\label{explicit:type} -Type declarations are automatically generated each time a subprogram -heading is generated. Type declarations are constructed -from information stored in the GENTRAN symbol table. The user -can place entries into the symbol table explicitly through calls -to the special GENTRAN function {\bf DECLARE}. \index{DECLARE function} -\begin{describe}{Syntax:} -{\bf \ \ DECLARE} {\it v1,v2,\dots\ ,vn} {\bf :} {\it type;} - - or - -\begin{tabular}{ll} -{\bf DECLARE}\\ -{\bf $<$$<$}\\ -&{\it v11,v12,\dots\ ,v1n} {\bf :} {\it type1;}\\ -&{\it v21,v22,\dots\ ,v2n} {\bf :} {\it type2;}\\ -& :\\ -& :\\ -&{\it vn1,vnn,\dots\ ,vnn} {\bf :} {\it typen;}\\ -{\bf $>$$>$}{\it ;} -\end{tabular} -\end{describe} -\begin{describe}{Arguments:} -Each {\it v1,v2,\dots\ ,vn} is a list of one or more variables -(optionally subscripted to indicate array dimensions), or -variable ranges (two letters separated by a ``-''). {\it v}'s are -not evaluated unless given as arguments to {\bf EVAL}. - -Each {\it type} is a variable type in the target language. Each -must be an atom, optionally preceded by the atom {\bf IMPLICIT}. -\index{IMPLICIT option} -{\it type}'s are not evaluated unless given as arguments to {\bf EVAL}. -\end{describe} -\begin{describe}{Side Effect:} -Entries are placed in the symbol table for each variable or -variable range declared in the call to this function. The function -call itself is removed from the statement group being -translated. Then after translation, type declarations are -generated from these symbol table entries before the resulting -executable statements are printed. -\end{describe} -\begin{describe}{Diagnostic Message:} -\begin{verbatim} -***** INVALID SYNTAX -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -\begin{verbatim} -1: GENTRAN -1: << -1: DECLARE -1: << -1: A-H, O-Z : IMPLICIT REAL; -1: M(4,4) : INTEGER -1: >>; -1: FOR I:=1:4 DO -1: FOR J:=1:4 DO -1: IF I=J -1: THEN M(I,J):=1 -1: ELSE M(I,J):=0; -1: DECLARE I, J : INTEGER; -1: >>$ - - IMPLICIT REAL (A-H,O-Z) - INTEGER M(4,4),I,J - DO 25001 I=1,4 - DO 25002 J=1,4 - IF (I.EQ.J) THEN - M(I,J)=1.0 - ELSE - M(I,J)=0.0 - ENDIF -25002 CONTINUE -25001 CONTINUE -\end{verbatim} -\end{describe} -The {\bf DECLARE} statement can also be used to declare subprogram types (i.e. -{\bf SUBROUTINE} or {\bf FUNCTION}) for \index{SUBROUTINE} \index{FUNCTION} -FORTRAN and RATFOR code, and function types for all four languages. -\begin{describe}{\example}\index{GENTRAN package ! example} -\begin{verbatim} -1: GENTRANLANG!* := 'RATFOR$ - -2: GENTRAN -2: PROCEDURE FAC N; -2: BEGIN -2: DECLARE -2: << -2: FAC : FUNCTION; -2: FAC, N : INTEGER -2: >>; -2: F := FOR I:=1:N PRODUCT I; -2: DECLARE F, I : INTEGER; -2: RETURN F -2: END$ - -INTEGER FUNCTION FAC(N) -INTEGER N,F,I -{ - F=1 - DO I=1,N - F=F*I -} -RETURN(F) -END - -3: GENTRANLANG!* := 'C$ -4: GENTRAN -4: PROCEDURE FAC N; -4: BEGIN -4: DECLARE FAC, N, I, F : INTEGER; -4: F := FOR I:=1:N PRODUCT I; -4: RETURN F -4: END$ - -int FAC(N) -int N; -{ - int I,F; - { - F=1; - for (I=1;I<=N;++I) - F*=I; - } - return(F); -} -\end{verbatim} -\end{describe} - -When generating code for subscripted variables (i.e., matrix and -array elements), it is important to keep several things in mind. First -of all, when a REDUCE array is declared with a declaration such as -\index{ARRAY} -\begin{center} -{\bf ARRAY A(}{\it n}{\bf )\$} -\end{center} -where {\it n} is a positive integer, {\bf A} is actually being declared -to be of size {\bf n}+1. Each of the elements {\bf A(0), A(1), \dots\ , A(n)} -can be used. However, a FORTRAN or RATFOR declaration such as -\begin{center} -{\bf DIMENSION A(}{\it n}{\bf )} -\end{center} -declares {\bf A} only to be of size {\bf n}. Only the elements -{\bf A(1), A(2), \dots\ , A(n)} can be used. Furthermore, a C declaration -such as -\begin{center} -{\bf float A[}{\it n}{\bf ];} -\end{center} -declares {\bf A} to be of size {\bf n} with elements referred to as -{\bf A[0], A[1], \dots\ , A[}{\it n-1}{\bf ]}. - -To resolve these array size and subscripting conflicts, the user should -remember the following: -\index{subscripts ! in GENTRAN} -\begin{itemize} -\item {\it All REDUCE array subscripts are translated literally.} -Therefore it is the user's responsibility to be sure that array elements with -subscript 0 are not translated into FORTRAN or RATFOR. -\item Since C and PASCAL -arrays allow elements with a subscript of 0, when an array is -declared to be of size {\it n} by the user, {\it the actual generated type -declaration will be of size n+1} so that the user can translate -elements with subscripts from 0, and up to and including {\it n}. -\end{itemize} - -If the user is generating C code, it is possible to produce declarations -for arrays with unknown bounds: -\begin{verbatim} -5: gentran declare <>$ - -6: gendecs nil; -float X[ ][ ]; -int Y[ ]; -\end{verbatim} - - -\subsection{Implicit Type Declarations} -\label{implicit:type} \index{GETDECS switch} -Some type declarations can be made automatically if the switch {\bf GETDECS} -is {\bf ON}. In this case: -\begin{enumerate} -\item The indices of loops are automatically declared to be integers. -\index{loop indices ! in GENTRAN} -\item There is a global variable {\bf DEFTYPE!*}, which is the default -type given to objects. Subprograms, their parameters, and local scalar -objects are automatically assigned this type. \ttindex{DEFTYPE"!*} -\index{REAL*8} \index{DOUBLE PRECISION} -Note that types such as REAL*8 or DOUBLE PRECISION should not -be used as, if {\bf DOUBLE} is on, then a default type of REAL -will in fact be DOUBLE PRECISION anyway. -\item If GENTRAN is used to translate a REDUCE procedure, then it assigns -objects declared {\bf SCALAR} the type given by {\bf DEFTYPE!*}. Note that -\index{INTEGER declaration} \index{REAL declaration} -it is legal to use the commands {\bf INTEGER} and {\bf REAL} in the place -of {\bf SCALAR}, which allows the user to specify an actual type. The -procedure may also be given a return type, in which case that is used as -the default. For example: -\begin{verbatim} - -2: on getdecs,gendecs$ - -3: GENTRAN -3: real procedure f(x); -3: begin integer n;real y; -3: n := 4; -3: y := n/(1+x)^2; -3: return y; -3: end; - REAL FUNCTION F(X) - INTEGER N - REAL X,Y - N=4 - Y=N/(1.0+X)**2 - F=Y - RETURN - END - -\end{verbatim} -\end{enumerate} - -\subsection{More about Type Declarations} -\label{more:type} -A check is made on output to ensure that all types generated are legal ones. -This is necessary since {\bf DEFTYPE!*} can be set to anything. -Note that {\bf DEFTYPE!*} ought normally to be given a simple -type as its \ttindex{DEFTYPE"!*} -value, such as REAL, INTEGER, or COMPLEX, -since this will always be translated into the corresponding type in the -target language on output. - -An entry is removed from the symbol table once a declaration has been -generated for it. The {\bf KEEPDECS} switch (by default {\bf OFF}) -disables this, allowing a user to check the types of objects -\index{KEEPDECS switch} which GENTRAN has generated (useful if they -are being generated automatically) - -\subsection{Comments and Literal Strings} -\label{comments} \index{comments ! in GENTRAN} -Comments and other strings of characters can be inserted directly into -the stream of generated code through a call to the special function -{\bf LITERAL}. -\begin{describe}{Syntax:} -{\bf LITERAL} {\it arg1,arg2,\dots\ ,argn;} -\end{describe} -\begin{describe}{Arguments:} -{\it arg1,arg2,\dots\ ,argn} is an argument list containing one or more -{\it arg}'s, where each {\it arg} either is, or evaluates to, an atom. The -\ttindex{TAB"!*} \ttindex{CR"!*} -atoms {\bf TAB!*} and {\bf CR!*} have special meanings. {\it arg}'s are -not evaluated unless given as arguments to {\bf EVAL}. -\end{describe} -\begin{describe}{Side Effect:} -This statement is replaced by the character sequence resulting from -concatenation of the given atoms. Double quotes are stripped from -all string type {\it arg}'s, and the reserved atoms {\bf TAB!*} and -{\bf CR!*} are replaced by a tab to the current level of indentation, and -an end-of-line character, respectively. -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -Suppose N has value 10. -\begin{verbatim} -1: GENTRANLANG!* := 'FORTRAN$ - -2: GENTRAN -2: << -2: LITERAL -2: "C",TAB!*,"--THIS IS A FORTRAN COMMENT--",CR!*, -2: "C",CR!*; -2: LITERAL -2: TAB!*,"DATA N/",EVAL(N),"/",CR!* -2: >>$ - -C --THIS IS A FORTRAN COMMENT-- -C - DATA N/10/ - -3: GENTRANLANG!* := 'RATFOR$ -4: GENTRAN -4: FOR I:=1:N DO -4: << -4: LITERAL -4: TAB!*,"# THIS IS A RATFOR COMMENT",CR!*; -4: LITERAL -4: TAB!*,"WRITE(6,10) (M(I,J),J=1,N)",CR!*, -4: 10,TAB!*,"FORMAT(1X,10(I5,3X))",CR!* -4: >>$ - -DO I=1,N - { - # THIS IS A RATFOR COMMENT - WRITE(6,10) (M(I,J),J=1,N) -10 FORMAT(1X,10(I5,3X)) - } - -5: GENTRANLANG!* := 'C$ -6: GENTRAN -6: << -6: X:=0; -6: LITERAL "/* THIS IS A",CR!*, -6: " C COMMENT */",CR!* -6: >>$ - -{ - X=0.0; -/* THIS IS A - C COMMENT */ -} - -7: GENTRANLANG!* := 'PASCAL$ - -8: GENTRAN -8: << -8: X := SIN(Y); -8: LITERAL "{ THIS IS A PASCAL COMMENT }", CR!* -8: >>$ -BEGIN - X:=SIN(Y) -{ THIS IS A PASCAL COMMENT } -END; - -\end{verbatim} -\end{describe} -\subsection{Expression Segmentation} -\label{segmentation} \index{segmenting expressions} -Symbolic derivations can easily produce formulas that can be anywhere -from a few lines to several pages in length. Such formulas -can be translated into numerical assignment statements, but unless they -are broken into smaller pieces they may be too long for a compiler -to handle. (The maximum number of continuation lines for one statement -allowed by most FORTRAN compilers is only 19.) Therefore GENTRAN -\index{continuation lines} -contains a segmentation facility which automatically {\it segments}, -or breaks down unreasonably large expressions. - -The segmentation facility generates a sequence of assignment -statements, each of which assigns a subexpression to an automatically -generated temporary variable. This sequence is generated in such a -way that temporary variables are re-used as soon as possible, thereby -keeping the number of automatically generated variables to a minimum. -The facility can be turned on or off by setting the mode -\index{GENTRANSEG switch} switch {\bf GENTRANSEG} accordingly (i.e., -by calling the REDUCE function {\bf ON} or {\bf OFF} on it). The user -can control the maximum allowable expression size by setting the -\ttindex{MAXEXPPRINTLEN"!*} -variable {\bf MAXEXPPRINTLEN!*} to the maximum number of characters -allowed in an expression printed in the target language (excluding -spaces automatically printed by the formatter). The {\bf GENTRANSEG} -switch is on initially, and {\bf MAXEXPPRINTLEN!*} is initialized to -800. -\begin{describe}{\example}\index{GENTRAN package ! example} -\begin{verbatim} -1: ON EXP$ - -2: JUNK1 := (A+B+C+D)^2$ - -3: MAXEXPPRINTLEN!* := 24$ - -4: GENTRAN VAL :=: JUNK1$ - - T0=A**2+2.0*A*B - T0=T0+2.0*A*C+2.0*A*D - T0=T0+B**2+2.0*B*C - T0=T0+2.0*B*D+C**2 - VAL=T0+2.0*C*D+D**2 - -5: JUNK2 := JUNK1/(E+F+G)$ - -6: MAXEXPPRINTLEN!* := 23$ - -7: GENTRANLANG!* := 'C$ - -8: GENTRAN VAL :=: JUNK2$ - -{ - T0=power(A,2)+2.0*A*B; - T0+=2.0*A*C; - T0=T0+2.0*A*D+power(B,2); - T0+=2.0*B*C; - T0=T0+2.0*B*D+power(C,2); - T0=T0+2.0*C*D+power(D,2); - VAL=T0/(exp(1.0)+F+G); -} -\end{verbatim} -\end{describe} -\subsubsection{Implicit Type Declarations}\label{GENTRAN:itd} -When the segmentation routine generates temporary variables, it places -type declarations in the symbol table for those variables if -possible. It uses the following rules to determine their type: -\index{implicit type declarations} \index{temporary variables ! type} -\begin{itemize} -\item[{(1)}] -If the type of the variable to which the large expression is being -assigned is already known (i.e., has been declared by the user), -then the temporary variables will be declared to be of that same type. -\item[{(2)}] \ttindex{TEMPVARTYPE"!*} -If the global variable {\bf TEMPVARTYPE!*} has a non-NIL value, then the -temporary variables are declared to be of that type. -\item[{(3)}] -Otherwise, the variables are not declared. -\end{itemize} - -\newpage -\begin{describe}{\example} \index{GENTRAN package ! example} - -\begin{verbatim} -1: MAXEXPPRINTLEN!* := 20$ - -2: TEMPVARTYPE!* := 'REAL$ - -3: GENTRAN -3: << -3: DECLARE ISUM : INTEGER; -3: ISUM := II+JJ+2*KK+LL+10*MM+NN; -3: PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2) -3: >>$ - - INTEGER ISUM,T0 - REAL T1 - T0=II+JJ+2.0*KK+LL - ISUM=T0+10.0*MM+NN - T1=V(X,Y)*SIN(X)*COS(Y**2) - PROD=T1*(X+Y+Z**2) -\end{verbatim} -\end{describe} -\subsection{Generation of Temporary Variable Names} -\label{tempvars} \index{temporary variables ! names} -As we have just seen, GENTRAN's segmentation module generates -temporary variables and places type declarations in the symbol table -for them whenever possible. Various other modules also generate -variables and corresponding declarations. All of these modules call -one special GENTRAN function each time they need a temporary -variable name. This function is {\bf TEMPVAR}. There are situations -in which it may be convenient for the user to be able to generate -temporary variable names directly.\footnote{One such example is suppression -of the simplification process to generate numerical code which is more -efficient. See the example in section~\ref{tempvar:example} on -page~\pageref{tempvar:example}.} -Therefore {\bf TEMPVAR} \ttindex{TEMPVAR} -is a user-accessible function which may be called from both -the algebraic and symbolic modes of REDUCE. -\begin{describe}{Syntax:} -{\bf TEMPVAR} {\it type} -\end{describe} -\begin{describe}{Argument:} -{\it type} is an atom which either indicates the variable type in the -target language (INTEGER, REAL, etc.), or is {\bf NIL} if the variable -type is unknown. -\end{describe} -\begin{describe}{Side Effects:} -{\bf TEMPVAR} creates temporary variable names by repeatedly concatenating -the values of the global variables {\bf TEMPVARNAME!*} (which has a -\ttindex{TEMPVARNUM"!*} -default value of {\bf T}) and {\bf TEMPVARNUM!*} (which is initially set -to 0) and incrementing {\bf TEMPVARNUM!*} until a variable name is created -which satisfies one of the following conditions: -\begin{itemize} -\item[{(1)}] -It was not generated previously, and it has not been declared by the user. -\item[{(2)}] -It was previously generated to hold the same type of value that it -must hold this time (e.g. INTEGER, REAL, etc.), and the value assigned -to it previously is no longer needed. -\end{itemize} -If {\it type} is a non-NIL argument, or if {\it type} is {\bf NIL} -and the global variable {\bf TEMPVARTYPE!*} (initially NIL) has been -\ttindex{TEMPVARTYPE"!*} -set to a non-NIL value, then a type entry for the generated variable name -is placed in the symbol table. -\end{describe} -\begin{describe}{Returned Value:} -{\bf TEMPVAR} returns an atom which can be used as a variable. -\end{describe} -Note: It is the user's responsibility to set {\bf TEMPVARNAME!*} and -{\bf TEMPVARNUM!*} to values such that generated variable -names will not clash with variables used elsewhere in the -program unless those variables have been declared. - -\subsubsection{Marking Temporary Variables} -In section~\ref{tempvars} we saw that a temporary variable name (of a certain -type) can be regenerated when the value previously assigned to it -is no longer needed. This section describes a function which {\it marks} -a variable to indicate that it currently holds a -significant value, and the next section describes functions which -{\it unmark} variables to indicate that the values they hold are no -\index{temporary variables ! marking} -\index{marking temporary variables} -longer significant.\ttindex{MARKVAR} -\begin{describe}{Syntax:} -{\bf MARKVAR} {\it var} -\end{describe} -\begin{describe}{Argument:} -{\it var} is an atom. -\end{describe} -\begin{describe}{Side Effects:} -{\bf MARKVAR} sets a flag on {\it var}'s property list to indicate that -{\it var} currently holds a significant value. -\end{describe} -\begin{describe}{Returned Value:} -{\bf MARKVAR} returns {\it var}. -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -The following matrix, M has been derived symbolically: -\begin{verbatim} -(X*(Y+Z) 0 X*Z) -( ) -( -X X+Y 0) -( ) -( X*Z 0 Z**2) -\end{verbatim} -We wish to replace each non-zero element by a generated variable name -to prevent these expressions from being resubstituted into further -calculations. (We will also record these substitutions in the -numerical program we are constructing by generating assignment -statements.)\footnote{ Note: {\bf MARKVAR} is a symbolic mode -procedure. Therefore, the name of each variable whose value is to be -passed to it from algebraic mode must appear in a {\bf SHARE} -\index{SHARE command} declaration. This tells REDUCE to share the -variable's value between algebraic and symbolic modes.} -\begin{verbatim} -9: SHARE var$ - -10: FOR j := 1 : 3 DO -10: FOR k := 1 : 3 DO -10: IF M(j,k) NEQ 0 THEN -10: << -10: var := TEMPVAR(NIL); -10: MARKVAR var; -10: GENTRAN -10: EVAL(var) :=: M(j,k); -10: M(j,k) := var -10: >>$ - - T0=X*(Y+Z) - T1=X*Z - T2=-X - T3=X+Y - T4=X*Z - T5=Z**2 -\end{verbatim} -Now matrix M contains the following entries: -\begin{verbatim} -(T0 0 T1) -( ) -(T2 T3 0) -( ) -(T4 0 T5) -\end{verbatim} -\end{describe} - -\subsubsection{Unmarking Temporary Variables} -\index{unmarking temporary variables} \index{temporary variables ! unmarking} -After the value assigned to a temporary variable has been used -in the numerical program and is no longer needed, the variable name can be \ -\ttindex{UNMARKVAR} -{\it unmarked} with the {\bf UNMARKVAR} function. -\begin{describe}{Syntax:} -{\bf UNMARKVAR} {\it var;} -\end{describe} -\begin{describe}{Argument:} -{\it var} is an atom (variable name) or an expression containing one or more -variable names. -\end{describe} -\begin{describe}{Side Effect:} -{\bf UNMARKVAR} resets flags on the property lists of all variable names in -{\it var} to indicate that they do not hold significant values any longer. -\end{describe} - -\subsection{Enabling and Disabling Generation of Type Declarations} -\label{control:type} -GENTRAN maintains a symbol table of variable type and dimension -information. It adds information to the symbol table by processing -user-supplied calls to the {\bf DECLARE} function (see -Section~\ref{explicit:type}) and as a -side effect of generating temporary variable names -(see Sections~\ref{segmentation} and \ref{tempvars}). -All information is stored in the symbol table until GENTRAN is ready -to print formatted numerical code. Since programming languages such as -FORTRAN require that type declarations appear before executable statements, -GENTRAN automatically extracts all relevant type information and prints it -in the form of type declarations before printing executable -statements. This feature is useful when the entire body of a (sub)program is -generated at one time: in this case, type declarations are printed -before any executable code. However, if the user chooses to generate code -in pieces, the resulting code may have type declarations interleaved -\index{GENDECS switch} -with executable code. For this reason, the user may turn the {\bf GENDECS} -mode switch on or off, depending on whether or not s/he chooses to use -this feature. - -In the following we re-examine the example of Section~\ref{GENTRAN:itd}. -\begin{describe}{\example}\index{GENTRAN package ! example} -\begin{verbatim} -1: MAXEXPPRINTLEN!* := 20$ - -2: TEMPVARTYPE!* := 'REAL!*8$ - -3: GENTRAN -3: << -3: DECLARE ISUM : INTEGER; -3: ISUM := II+JJ+2*KK+LL+10*MM+NN -3: >>$ - - INTEGER ISUM,T0 - T0=II+JJ+2*KK+LL - ISUM=T0+10*MM+NN - -4: GENTRAN PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2)$ - - REAL*8 T2 - T2=V(X,Y)*SIN(REAL(X))*COS(REAL(Y**2)) - PROD=T2*(X+Y+Z**2) - -5: OFF GENDECS$ - -6: GENTRAN -6: << -6: DECLARE ISUM : INTEGER; -6: ISUM := II+JJ+2*KK+LL+10*MM+NN -6: >>$ - - T0=II+JJ+2*KK+LL - ISUM=T0+10*MM+NN - -7: GENTRAN PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2)$ - - T2=V(X,Y)*SIN(REAL(X))*COS(REAL(Y**2)) - PROD=T2*(X+Y+Z**2) -\end{verbatim} -\end{describe} - -In Section~\ref{template:type} we will explain how to further control -the generation of type declarations. - -\subsection{Complex Numbers} -\label{complex} \index{complex numbers} \index{COMPLEX} -With the switch {\bf COMPLEX} set {\bf ON}, GENTRAN will generate the -correct representation for a complex number in the given precision -provided that: - -\begin{enumerate} -\item The current language supports a complex data type (if it doesn't then -an error results); -\item The complex quantity is evaluated by REDUCE -to give an object of the correct -domain; i.e. -\begin{verbatim} - GENTRAN x:=: 1+i; - - GENTRAN x:= eval 1+i; - - z := 1+i; - GENTRAN x:=: z; -\end{verbatim} -will all generate the correct result, as will their Symbolic mode equivalents, -while: -\begin{verbatim} - GENTRAN x := 1+i; -\end{verbatim} -will not. -\end{enumerate} - -\subsection{Intrinsic Functions} -\label{intrinsic} \index{intrinsic functions} -A warning is issued if a standard REDUCE function is encountered which -does not have an intrinsic counterpart in the target language (e.g. - {\it cot\/}, -{\it sec\/} etc.). -Output is not halted in case this is a user--supplied function, either via -a REDUCE definition or within a GENTRAN template. - -The types of intrinsic FORTRAN functions are coerced to reals (in the correct -precision) as the following examples demonstrate: -\begin{verbatim} -19: GENTRAN x:=sin(0)$ - X=SIN(0.0) - -20: GENTRAN x:=cos(A)$ - X=COS(REAL(A)) - -21: ON DOUBLE$ - -22: GENTRAN x := log(1)$ - X=DLOG(1.0D0) - -23: GENTRAN x := exp(B)$ - X=DEXP(DBLE(B)) - -24: GENTRAN DECLARE <>$ - -25: GENTRAN x := exp(B)$ - X=DEXP(B) - -\end{verbatim} - -\subsection{Miscellaneous} - -\subsubsection{MAKECALLS} -A statement like: -\begin{verbatim} - GENTRAN x^2+1$ -\end{verbatim} -will yield the result: -\begin{verbatim} - X**2+1 -\end{verbatim} -but, under normal circumstances, a statement like: -\begin{verbatim} - GENTRAN sin(x)$ -\end{verbatim} -will yield the result: -\begin{verbatim} - CALL SIN(X) -\end{verbatim} -\index{MAKECALLS switch} -The switch {\bf MAKECALLS} (OFF by default) will make GENTRAN yield -\begin{verbatim} - SIN(X) -\end{verbatim} -This is useful if you don't know in advance what the form of the expression -which you are translating is going to be. - -\subsubsection{E} -\index{e} \index{EXP} -When GENTRAN encounters $e$ it translates it into EXP(1), and when GENTRAN -encounters -$e^x$ it is translated to EXP(X). This is then translated -into the correct statement in the given language and precision. Note that -it is still possible to do something like: -\begin{verbatim} - GENTRAN e:=:e; -\end{verbatim} -and get the correct result. - -\subsection{Booleans} -\index{booleans} \index{true} \index{false} -Some languages, like Fortran-77, have a boolean data type. Others, like -C, do not. When translating Reduce code into a language with a boolean -data type, GENTRAN will recognise the special identifiers $true$ and -$false$. For example: -\begin{verbatim} -3: gentran <>; - LOGICAL T - T=.TRUE. -\end{verbatim} - - -\section{Template Processing}\label{GENTRAN:template} - -\index{GENTRAN ! templates} \index{templates !} \index{code templates} -In some code generation applications pieces of the target numerical -program are known in advance. A {\it template} file containing a -program outline is supplied by the user, and formulas are derived in -REDUCE, converted to numerical code, and inserted in the corresponding -places in the program outline to form a complete numerical program. A -template processor is provided by GENTRAN for use in these -applications. - -\subsection{The Template Processing Command} -\label{templates} \index{GENTRANIN command} -\begin{describe}{Syntax:} -{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm} [{\bf OUT} {\it f1,f2,\dots\ - ,fn\/}]{\it ;} -\end{describe} -\begin{describe}{Arguments:} -{\it f1,f2,\dots\ ,fm\/} is an argument list containing one or more -{\it f\/}'s, -where each {\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom}& = &a template (input) file\\ -{\bf T}& = &the terminal\\ -\end{tabular} -\end{center} -{\it f1,f2,\dots\ ,fn\/} is an optional argument list containing one or more -{\it f\/}'s, where each {\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom}& = &an output file\\ -{\bf T}& = &the terminal\\ -{\bf NIL}& = &the current output file(s)\\ -{\bf ALL!*}& = &all files currently open for output \\ -& & by GENTRAN (see section~\ref{GENTRAN:output}) \\ -\end{tabular} -\end{center} -\end{describe} -\begin{describe}{Side Effects:} -{\bf GENTRANIN} processes each template file {\it f1,f2,\dots\ ,fm} -sequentially. - -A template file may contain any number of parts, each of which -is either an active or an inactive part. All active parts start with -the character sequence {\bf ;BEGIN;} and end with {\bf ;END;}. The end -of the template file is indicated by an extra {\bf ;END;} character -sequence. \index{;BEGIN; marker} \index{;END; marker} - -Inactive parts of template files are assumed to contain code in the -target language (FORTRAN, RATFOR, PASCAL or C, depending on the value -\ttindex{GENTRANLANG"!*} -of the global variable {\bf GENTRANLANG!*}). All inactive parts are -copied to the output. Comments delimited by the appropriate characters, -\index{comments ! in GENTRAN} -\begin{center} -\begin{tabular}{lll} -&{\bf C} \dots\ $<$cr$>$ & FORTRAN (beginning in column 1)\\ -&{\bf \#} \dots\ $<$cr$>$ & RATFOR \\ -&{\bf /*} \dots\ {\bf */} & C \\ -&{\bf \{} \dots\ {\bf \}} or {\bf *(} \dots\ {\bf )*} & PASCAL\\ -\end{tabular} -\end{center} -are also copied in their entirety to the output. Thus the character -sequences {\bf ;BEGIN;} and {\bf ;END;} have no special meanings -within comments. - -Active parts may contain any number of REDUCE expressions, statements, -and commands. They are not copied directly to the output. Instead, -they are given to REDUCE for evaluation in algebraic mode\footnote{ -Active parts are evaluated in algebraic mode unless the mode is -explicitly changed to symbolic from within the active part itself. -This is true no matter which mode the system was in when the template -processor was called.}. All output generated by each evaluation is -sent to the output file(s). Returned values are only printed on the -terminal.\index{GENTRAN ! preevaluation} - -Active parts will most likely contain calls to {\bf GENTRAN} to -generate code. This means that the result of processing a -template file will be the original template file with all active -parts replaced by generated code. - -If {\bf OUT} {\it f1,f2,\dots\ ,fn} is not given, generated code is simply -written to the current-output file. - -However, if {\bf OUT} {\it f1,f2,\dots\ ,fn} -is given, then the current-output file -is temporarily overridden. Generated code is written to each file represented -by {\it f1,f2,\dots\ ,fn} for this command only. Files which were -open prior to the call to {\bf GENTRANIN} will remain open after the -call, and files which did not exist prior to the call will be -created, opened, written to, and closed. The output-stack will be -exactly the same both before and after the call. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRANIN} returns the names of all files written to by this -command. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** OUTPUT FILE ALREADY EXISTS - OVERWRITE FILE? (Y/N) - -***** NONEXISTENT INPUT FILE - -***** TEMPLATE FILE ALREADY OPEN FOR INPUT - -***** WRONG TYPE OF ARG -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -Suppose we wish to generate a FORTRAN subprogram to compute the -determinant of a 3 x 3 matrix. We can construct a template -file with an outline of the FORTRAN subprogram and REDUCE and -GENTRAN commands to fill it in: -\index{matrices ! in GENTRAN} - -Contents of file {\tt det.tem}: -\end{describe} -\begin{framedverbatim} - REAL FUNCTION DET(M) - REAL M(3,3) -;BEGIN; - OPERATOR M$ - MATRIX MM(3,3)$ - MM := MAT( (M(1,1),M(1,2),M(1,3)), - (M(2,1),M(2,2),M(2,3)), - (M(3,1),M(3,2),M(3,3)) )$ - GENTRAN DET :=: DET(MM)$ -;END; - RETURN - END -;END; -\end{framedverbatim} - -\begin{describe}{} -Now we can generate a FORTRAN subprogram with the following -REDUCE session: -\begin{verbatim} -1: GENTRANLANG!* := 'FORTRAN$ - -2: GENTRANIN -2: "det.tem" -2: OUT "det.f"$ -\end{verbatim} -Contents of file det.f: -\end{describe} -\begin{framedverbatim} - REAL FUNCTION DET(M) - REAL M(3,3) - DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) - . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1 - . ,2)-(M(3,1)*M(2,2)*M(1,3)) - RETURN - END -\end{framedverbatim} - -\subsection{Copying Files into Template Files} -\label{copy:template} - -\index{GENTRANIN command} \index{files ! in GENTRAN} -Template files can be copied into other template files with recursive -calls to {\bf GENTRANIN} ; i.e., by calling {\bf GENTRANIN} from the -active part of a template file. - -For example, suppose we wish to copy the contents of a file containing -a subprogram into a file containing a main program. We will call -{\bf GENTRANIN} to do the copying, so the subprogram file must -have {\bf ;END;} on its last line: - -Contents of file {\tt det.tem}: -\begin{framedverbatim} - REAL FUNCTION DET(M) - REAL M(3,3) - DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) - . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1 - . ,2)-(M(3,1)*M(2,2)*M(1,3)) - RETURN - END -;END; -\end{framedverbatim} - -Now the template file for the main program can be constructed -with an active part which will include file det.tem: - -Contents of file {\tt main.tem}: -\begin{framedverbatim} -C -C MAIN PROGRAM -C - REAL M(3,3),DET - WRITE(6,*) 'ENTER 3 x 3 MATRIX' - DO 100 I=1,3 - READ(5,*) (M(I,J),J=1,3) -100 CONTINUE - WRITE(6,*) ' DET = ', DET(M) - STOP - END -C -C DETERMINANT CALCULATION -C -;BEGIN; - GENTRANIN "det.tem"$ -;END; -;END; -\end{framedverbatim} - -The following REDUCE session will create the file {\tt main.f}: -\begin{verbatim} -1: GENTRANIN -1: "main.tem" -1: OUT "main.f"$ -\end{verbatim} - -Contents of file {\tt main.f}: -\begin{framedverbatim} -C -C MAIN PROGRAM -C - REAL M(3,3),DET - WRITE(6,*) 'ENTER 3 x 3 MATRIX' - DO 100 I=1,3 - READ(5,*) (M(I,J),J=1,3) -100 CONTINUE - WRITE(6,*) ' DET = ', DET(M) - STOP - END -C -C DETERMINANT CALCULATION -C - REAL FUNCTION DET(M) - REAL M(3,3) - DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) - . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)* - . M(1,2)-(M(3,1)*M(2,2)*M(1,3)) - RETURN - END -\end{framedverbatim} - -\subsection{The Template File Stack} -\label{template:stack} - -\index{templates ! file stack} -The REDUCE {\bf IN} command takes one or more file names as -arguments. REDUCE reads each of the given files and executes all -statements and commands, any of which may be another {\bf IN} -command. A stack of input file names is maintained by -REDUCE to allow recursive invocation of the {\bf IN} command. Similarly, -a stack of template file names is maintained by GENTRAN to facilitate -recursive invocation of the template processor. Section~\ref{copy:template} -showed that the {\bf GENTRANIN} command can be -\index{GENTRANIN command} -called recursively to copy files into other files. This section shows -that template files which are copied into other template files can also -contain active parts, and thus the whole code generation process can -be invoked recursively. - -We can generalize the example of section~\ref{copy:template} by -generating code recursively. We can extend it to generate code which -will compute entries of the inverse matrix, also. Suppose -we have created the file init.red, which contains REDUCE commands to -create an {\it n}x{\it n} matrix MM and initialize its entries -to M(1,1), M(1,2),~\dots~, M({\it n}, {\it n}), for some user-entered -value of {\it n}: - -Contents of file {\tt init.red}: -\begin{framedverbatim} -OPERATOR M$ -MATRIX MM(n,n)$ -FOR J := 1 : n DO - FOR K := 1 : n DO - MM(J,K) := M(J,K)$ -END$ -\end{framedverbatim} - -We have also created template files {\tt det.tem} and {\tt inv.tem} which -contain outlines of FORTRAN subprograms to compute the -determinant and inverse of an {\it n}x{\it n} matrix, respectively: - -Contents of file {\tt det.tem}: -\begin{framedverbatim} - REAL FUNCTION DET(M) -;BEGIN; - GENTRAN - << - DECLARE M(EVAL(n),EVAL(n)) : REAL; - DET :=: DET(MM) - >>$ -;END; - RETURN - END -;END; -\end{framedverbatim} -Contents of file {\tt inv.tem}: -\begin{framedverbatim} - SUBROUTINE INV(M,MINV) -;BEGIN; - GENTRAN - << - DECLARE M(EVAL(n),EVAL(n)), - MINV(EVAL(n),EVAL(n)) : REAL; - MINV :=: MM^(-1) - >>$ -;END; - RETURN - END -;END; -\end{framedverbatim} - -Now we can construct a template file with a generalized version of the main -program given in section~\ref{copy:template} -and can place {\bf GENTRANIN} commands -in this file to generate code recursively from the template files det.tem -and inv.tem: - -Contents of file {\tt main.tem}: -\begin{framedverbatim} -C -C MAIN PROGRAM -C -;BEGIN; - GENTRAN - << - DECLARE - << - M(EVAL(n),EVAL(n)), - DET, - MINV(EVAL(n),EVAL(n)) : REAL; - N : INTEGER - >>; - LITERAL TAB!*, "DATA N/", EVAL(n), "/", CR!* - >>$ -;END; - WRITE(6,*) 'ENTER ', N, 'x', N, ' MATRIX' - DO 100 I=1,N - READ(5,*) (M(I,J),J=1,N) -100 CONTINUE - WRITE(6,*) ' DET = ', DET(M) - WRITE(6,*) ' INVERSE MATRIX:' - CALL INV(M,MINV) - DO 200 I=1,N - WRITE(6,*) (MINV(I,J),J=1,N) -200 CONTINUE - STOP - END -C -C DETERMINANT CALCULATION -C -;BEGIN; - GENTRANIN "det.tem"$ -;END; -C -C INVERSE CALCULATION -C -;BEGIN; - GENTRANIN "inv.tem"$ -;END; -;END; -\end{framedverbatim} - -The following REDUCE session will create the file {\tt main.f}: -\begin{verbatim} -1: n := 3$ - -2: IN "init.red"$ - -3: GENTRANLANG!* := 'FORTRAN$ - -4: GENTRANIN -4: "main.tem" -4: OUT "main.f"$ -\end{verbatim} -Contents of file {\tt main.f}: -\begin{framedverbatim} -C -C MAIN PROGRAM -C - REAL M(3,3),DET,MINV(3,3) - INTEGER N - DATA N/3/ - WRITE(6,*) 'ENTER ', N, 'x', N, ' MATRIX' - DO 100 I=1,N - READ(5,*) (M(I,J),J=1,N) -100 CONTINUE - WRITE(6,*) ' DET = ', DET(M) - WRITE(6,*) ' INVERSE MATRIX:' - CALL INV(M,MINV) - DO 200 I=1,N - WRITE(6,*) (MINV(I,J),J=1,N) -200 CONTINUE - STOP - END -C -C DETERMINANT CALCULATION -C - REAL FUNCTION DET(M) - REAL M(3,3) - DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) - . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3) - . *M(1,2)-(M(3,1)*M(2,2)*M(1,3)) - RETURN - END -C -C INVERSE CALCULATION -C - SUBROUTINE INV(M,MINV) - REAL M(3,3),MINV(3,3) - MINV(1,1)=(M(3,3)*M(2,2)-(M(3,2)*M(2,3)))/(M(3,3)*M(2,2 - . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) - . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 - . ,2)*M(1,3))) - MINV(1,2)=(-(M(3,3)*M(1,2))+M(3,2)*M(1,3))/(M(3,3)*M(2, - . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) - . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( - . 2,2)*M(1,3))) - MINV(1,3)=(M(2,3)*M(1,2)-(M(2,2)*M(1,3)))/(M(3,3)*M(2,2 - . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) - . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 - . ,2)*M(1,3))) - MINV(2,1)=(-(M(3,3)*M(2,1))+M(3,1)*M(2,3))/(M(3,3)*M(2, - . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) - . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( - . 2,2)*M(1,3))) - MINV(2,2)=(M(3,3)*M(1,1)-(M(3,1)*M(1,3)))/(M(3,3)*M(2,2 - . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) - . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 - . ,2)*M(1,3))) - MINV(2,3)=(-(M(2,3)*M(1,1))+M(2,1)*M(1,3))/(M(3,3)*M(2, - . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) - . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( - . 2,2)*M(1,3))) - MINV(3,1)=(M(3,2)*M(2,1)-(M(3,1)*M(2,2)))/(M(3,3)*M(2,2 - . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) - . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 - . ,2)*M(1,3))) - MINV(3,2)=(-(M(3,2)*M(1,1))+M(3,1)*M(1,2))/(M(3,3)*M(2, - . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) - . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( - . 2,2)*M(1,3))) - MINV(3,3)=(M(2,2)*M(1,1)-(M(2,1)*M(1,2)))/(M(3,3)*M(2,2 - . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) - . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 - . ,2)*M(1,3))) - RETURN - END -\end{framedverbatim} - -This is an example of a modular approach to code generation; separate -subprogram templates are given in separate files. Furthermore, the template -files are general; they can be used for matrices of any predetermined -size. Therefore, we can easily generate different subprograms to -handle matrices of different sizes from the same template files -simply by assigning different values to {\it n}, and reloading the -file init.red. - -\subsection{Template Processing and Generation of Type Declarations} -\label{template:type} -\index{GENDECS switch} \index{type declarations} -In Section~\ref{control:type} we described the {\bf GENDECS} flag. We -explained that type declarations are not generated when this flag is -turned off. Now that the concept of template processing has been -explained, it is appropriate to continue our discussion of generation -of type declarations. - -When the {\bf GENDECS} flag is off, type declaration information is not -simply discarded --- it is still maintained in the symbol table. Only the -automatic extraction of this information in the form of declarations is -disabled. When the {\bf GENDECS} flag is turned off, all type -information associated with a specific subprogram can be retrieved in the -form of generated declarations by calling the {\bf GENDECS} function with -the subprogram name as argument. The template processor recognizes -function and subroutine headings. It always keeps track of the name of -the subprogram it is processing. Therefore, the declarations associated with -a particular subprogram {\it subprogname} can be generated with a call to -{\bf GENDECS} as follows: -\begin{center} -{\bf GENDECS} {\it subprogname}\$ -\end{center} - -By using the {\bf GENDECS} flag and function together with the template -processing facility, it is possible to have type information -inserted into the symbol table during a first pass over a template file, and -then to have it extracted during a second pass. Consider the following -example in which the original template file is transformed into an -intermediate template during the first pass, and then into the final file -of FORTRAN code during the second pass: - -Contents of file {\tt junk.tem}: -\begin{framedverbatim} -;BEGIN; -MAXEXPPRINTLEN!* := 50$ -OFF GENDECS$ -;END; - SUBROUTINE CALC(X,Y,Z,A,B,RES) -;BEGIN; -GENTRAN LITERAL ";BEGIN;", CR!*, - "GENDECS CALC$", CR!*, - ";END;", CR!*$ -;END; - X=3.75 - Y=-10.2 - Z=16.473 -;BEGIN; -GENTRAN -<< - DECLARE X,Y,Z,A,B,RES : REAL; - RES :=: (X + Y + Z)^3*(A + B)^2 ->>$ -;END; - RETURN - END -;BEGIN; -GENTRAN LITERAL ";END;", CR!*$ -;END; -;END; -\end{framedverbatim} - -Invocation of the template processor on this file produces an -intermediate template file: -\begin{verbatim} -1: GENTRANIN -1: "junk.tem" -1: OUT "#junk.tem"$ -\end{verbatim} -Contents of file {\tt \#junk.tem}: -\begin{framedverbatim} - SUBROUTINE CALC(X,Y,Z,A,B,RES) -;BEGIN; -GENDECS CALC$ -;END; - X=3.75 - Y=-10.2 - Z=16.473 - T0=A**2*X**3+3.0*A**2*X**2*Y - T0=T0+3.0*A**2*X**2*Z+3.0*A**2*X*Y**2 - T0=T0+6.0*A**2*X*Y*Z+3.0*A**2*X*Z**2 - T0=T0+A**2*Y**3+3.0*A**2*Y**2*Z - T0=T0+3.0*A**2*Y*Z**2+A**2*Z**3 - T0=T0+2.0*A*B*X**3+6.0*A*B*X**2*Y - T0=T0+6.0*A*B*X**2*Z+6.0*A*B*X*Y**2 - T0=T0+12.0*A*B*X*Y*Z+6.0*A*B*X*Z**2 - T0=T0+2.0*A*B*Y**3+6.0*A*B*Y**2*Z - T0=T0+6.0*A*B*Y*Z**2+2.0*A*B*Z**3 - T0=T0+B**2*X**3+3.0*B**2*X**2*Y - T0=T0+3.0*B**2*X**2*Z+3.0*B**2*X*Y**2 - T0=T0+6.0*B**2*X*Y*Z+3.0*B**2*X*Z**2 - T0=T0+B**2*Y**3+3.0*B**2*Y**2*Z - RES=T0+3.0*B**2*Y*Z**2+B**2*Z**3 - RETURN - END -;END; -\end{framedverbatim} -Another pass of the template processor produced the final file of FORTRAN -code: -\begin{verbatim} -2: GENTRANIN -2: "#junk.tem" -2: OUT "junk.f"$ -\end{verbatim} -Contents of file {\tt junk.f}: -\begin{framedverbatim} - SUBROUTINE CALC(X,Y,Z,A,B,RES) - REAL X,Y,Z,A,B,RES,T0 - X=3.75 - Y=-10.2 - Z=16.473 - T0=A**2*X**3+3.0*A**2*X**2*Y - T0=T0+3.0*A**2*X**2*Z+3.0*A**2*X*Y**2 - T0=T0+6.0*A**2*X*Y*Z+3.0*A**2*X*Z**2 - T0=T0+A**2*Y**3+3.0*A**2*Y**2*Z - T0=T0+3.0*A**2*Y*Z**2+A**2*Z**3 - T0=T0+2.0*A*B*X**3+6.0*A*B*X**2*Y - T0=T0+6.0*A*B*X**2*Z+6.0*A*B*X*Y**2 - T0=T0+12.0*A*B*X*Y*Z+6.0*A*B*X*Z**2 - T0=T0+2.0*A*B*Y**3+6.0*A*B*Y**2*Z - T0=T0+6.0*A*B*Y*Z**2+2.0*A*B*Z**3 - T0=T0+B**2*X**3+3.0*B**2*X**2*Y - T0=T0+3.0*B**2*X**2*Z+3.0*B**2*X*Y**2 - T0=T0+6.0*B**2*X*Y*Z+3.0*B**2*X*Z**2 - T0=T0+B**2*Y**3+3.0*B**2*Y**2*Z - RES=T0+3.0*B**2*Y*Z**2+B**2*Z**3 - RETURN - END -\end{framedverbatim} - -\subsection{Referencing Subprogram and Parameter Names} -\index{"!\$n parameters} \index{"!\$0 subprogram name} -In some code generation applications in which template processing is used, -it is useful to be able to reference the names of the parameters -given in the subprogram header. For this reason, the special -symbols {\bf !\$1}, {\bf !\$2},~\dots, {\bf !\${\it n}}, where {\it n} -is the number -of parameters, can be used in computations and code generation commands in -active parts of template files. Each of these symbols will be replaced by -the corresponding parameter name when code is generated. In addition, the -special symbol {\bf !\$0} will be replaced by the subprogram name. This is -useful when FORTRAN or RATFOR functions are being generated. Finally, the -\index{"!\$"!\# in GENTRAN} -special global variable {\bf !\$!\#} is bound to the number of parameters in -the subprogram header. - -\section{Output Redirection}\label{GENTRAN:output} -\index{GENTRAN ! file output} -Many examples given thus far in this manual have sent all generated code to -the terminal screen. In actual code generation applications, however, -code must be sent to a file which will be compiled at a later -time. This section explains methods of redirecting code to a -file as it is generated. Any number of output files can be open -simultaneously, and generated code can be sent to any combination -of these open files. - -\subsection{File Selection Commands} -\label{file:selection} -\index{OUT command} \index{SHUT command} -REDUCE provides the user with two file handling commands for output -redirection: {\bf OUT} and {\bf SHUT}. The {\bf OUT} command takes a -single file name as argument and directs all REDUCE output to that -file from then on, until another {\bf OUT} changes the output file, or -{\bf SHUT} closes it. Output can go to only one file at a time, -although many can be open. If the file has previously been used for -output during the current job and not {\bf SHUT}, then the new output -is appended onto the end of the file. Any existing file is erased -before its first use for output in a job. To output on the terminal -without closing the output file, the reserved file name {\bf T} (for -terminal) may be used. - -The REDUCE {\bf SHUT} command takes a list of names of files which -have been previously opened via an {\bf OUT} command and closes them. -Most systems require this action by the user before he ends the REDUCE -job; otherwise the output may be lost. If a file is {\bf SHUT} and a -further {\bf OUT} command is issued for the same file, the file is -erased before the new output is written. If it is the current output -file that is {\bf SHUT}, output will switch to the terminal. - -These commands are suitable for most applications in which REDUCE -output must be saved. However, they have two deficiencies when -considered for use in code generation applications. First, they are -inconvenient. {\bf OUT} tells REDUCE to direct {\it all\/} output to -a specified file. Thus in addition to output written as side effects -of functions, returned values are also written to the file (unless the -user is careful to terminate all statements and commands with a {\bf -\$}, in which case only output produced by side effects is written). -If code generation is to be accomplished interactively; i.e., if -algebraic computations and code generation commands are interleaved, -then {\bf OUT} {\it filename\/}{\bf \$} must be issued before every -group of code generation requests, and {\bf OUT T\$} must be issued -after every group. Secondly, the {\bf OUT} command does not allow -output to be sent to two or more files without reissuing the {\bf OUT} -with another file name. In an effort to remove these deficiencies and -make the code generation commands flexible and easy to use, separate -file handling commands are provided by GENTRAN which redirect -generated code {\it only}. - -\index{GENTRANOUT command} \index{GENTRANSHUT command} -The {\bf GENTRANOUT} and {\bf GENTRANSHUT} commands are identical to -the REDUCE {\bf OUT} and {\bf SHUT} commands with the following -exceptions: - -\begin{itemize} -\item {\bf GENTRANOUT} and {\bf GENTRANSHUT} redirect {\it only\/} code which -is printed as a side effect of GENTRAN commands. -\item {\bf GENTRANOUT} allows more than one file name to be given -to indicate that generated code is to be sent to two or more -files. (It is particularly convenient to be able to -have generated code sent to -the terminal screen and one or more file simultaneously.) -\item {\bf GENTRANOUT} does not automatically erase existing files; it prints -a warning message on the terminal and asks the user whether the existing -file should be erased or the whole command be aborted. -\end{itemize} -The next two subsections describe these commands in detail. - -\index{GENTRANOUT command} -\subsubsection{GENTRANOUT} -\begin{describe}{Syntax:} -{\bf GENTRANOUT} {\it f1,f2,\dots\ ,fn;} -\end{describe} -\begin{describe}{Arguments:} -{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each -{\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom} & = & an output file\\ -{\bf T} & = & the terminal\\ -{\bf NIL} & = & the current output file(s)\\ -{\bf ALL!*} & = & all files currently open for output \\ -& & by GENTRAN\\ -\end{tabular} -\end{center} -\end{describe} -\begin{describe}{Side Effects:} -GENTRAN maintains a list of files currently open for output by -GENTRAN {\it only}. {\bf GENTRANOUT} inserts each file name represented by -{\it f1,f2,\dots\ ,fn\/} into that list and opens each one for output. It -also resets the current output file(s) to be all files in {\it f1,f2,\dots\ - ,fn}. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRANOUT} returns the list of files represented by -{\it f1,f2,\dots\ ,fn\/}; -i.e., the current output file(s) after the command has been executed. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** OUTPUT FILE ALREADY EXISTS - OVERWRITE FILE? (Y/N) - -***** WRONG TYPE OF ARG -\end{verbatim} -\end{describe} -\begin{describe}{\example} -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(5,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(.75,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(.7,1.5) {\vector(0,-1){.75}} -\end{picture}} - -\begin{verbatim} -1: GENTRANOUT "f1"; - -"f1" -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(5,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(2.25,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(2.2,1.5) {\vector(0,-1){.75}} -\end{picture}} - -\begin{verbatim} -2: GENTRANOUT "f2"; - -"f2" -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(5,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(3,0) {\framebox(1.5,.75){"f2"}} -\put(3.75,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(3.7,1.5) {\vector(0,-1){.75}} -\end{picture}} - - -\begin{verbatim} -3: GENTRANOUT T,"f3"; - -{T,"f3"} -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(3,0) {\framebox(1.5,.75){"f2"}} -\put(4.5,0) {\framebox(1.5,.75){"f3"}} -\put(5.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(5.25,1.5) {\vector(0,-1){.75}} -\put(5.45,1.5) {\line(-1,0){4.70}} -\put(.75,1.5) {\vector(0,-1){.75}} -\end{picture}} - - -\begin{verbatim} -4: GENTRANOUT "f1"; - -"f1" -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(3,0) {\framebox(1.5,.75){"f2"}} -\put(4.5,0) {\framebox(1.5,.75){"f3"}} -\put(2.25,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(2.2,1.5) {\vector(0,-1){.75}} -\end{picture}} - -\begin{verbatim} -5: GENTRANOUT NIL,"f4"; - -{"f1","f4"} -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(3,0) {\framebox(1.5,.75){"f2"}} -\put(4.5,0) {\framebox(1.5,.75){"f3"}} -\put(6,0) {\framebox(1.5,.75){"f4"}} -\put(7.5,1.5) {\makebox(0,0)[bl]{\tt current-output}} -\put(6.75,1.5) {\vector(0,-1){.75}} -\put(2.25,1.5) {\vector(0,-1){.75}} -\put(7.45,1.5) {\line(-1,0){5.2}} -\end{picture}} - - -\ttindex{ALL"!*} -\begin{verbatim} -6: GENTRANOUT ALL!*; - -{"f1","f2","f3","f4"} -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1.5,.75){T}} -\put(1.5,0) {\framebox(1.5,.75){"f1"}} -\put(3,0) {\framebox(1.5,.75){"f2"}} -\put(4.5,0) {\framebox(1.5,.75){"f3"}} -\put(6,0) {\framebox(1.5,.75){"f4"}} -\put(7.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(6.75,1.5) {\vector(0,-1){.75}} -\put(5.25,1.5) {\vector(0,-1){.75}} -\put(3.75,1.5) {\vector(0,-1){.75}} -\put(2.25,1.5) {\vector(0,-1){.75}} -\put(7.45,1.5) {\line(-1,0){5.2}} -\end{picture}} - -\end{describe} - -\subsubsection{GENTRANSHUT} -\index{GENTRANSHUT command} -\begin{describe}{Syntax:} -{\bf GENTRANSHUT} {\it f1,f2,\dots\ ,fn;\/} -\end{describe} -\begin{describe}{Arguments:} -{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each -{\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom} & = & an output file\\ -{\bf NIL} & = & the current output file(s)\\ -{\bf ALL!*} & = & all files currently open for output \\ -& & by GENTRAN\\ -\end{tabular} -\end{center} -\end{describe} -\begin{describe}{Side Effects:} -{\bf GENTRANSHUT} creates a list of file names from {\it f1,f2,\dots\ ,fn}, -deletes each from the output file list, and closes the -corresponding files. If (all of) the current output file(s) are -closed, then the current output file is reset to the terminal. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRANSHUT} returns the current output file(s) after the command has -been executed. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** FILE NOT OPEN FOR OUTPUT - -***** WRONG TYPE OF ARG -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1,.75){T}} -\put(1,0) {\framebox(1,.75){"f1"}} -\put(2,0) {\framebox(1,.75){"f2"}} -\put(3,0) {\framebox(1,.75){"f3"}} -\put(4,0) {\framebox(1,.75){"f4"}} -\put(5,0) {\framebox(1,.75){"f5"}} -\put(6,0) {\framebox(1,.75){"f6"}} -\put(7,0) {\framebox(1,.75){"f7"}} -\put(2,1.5) {\makebox(0,0) [br]{\tt current-output}} -\put(3.5,1.5) {\vector(0,-1){.75}} -\put(4.5,1.5) {\vector(0,-1){.75}} -\put(7.5,1.5) {\vector(0,-1){.75}} -\put(2.05,1.5) {\line(1,0){5.45}} -\end{picture}} - -\begin{verbatim} -1: GENTRANSHUT "f1","f2","f7"; - -{"f3","f4"} -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1,.75){T}} -\put(1,0) {\framebox(1,.75){"f3"}} -\put(2,0) {\framebox(1,.75){"f4"}} -\put(3,0) {\framebox(1,.75){"f5"}} -\put(4,0) {\framebox(1,.75){"f6"}} -\put(4.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(1.5,1.5) {\vector(0,-1){.75}} -\put(2.5,1.5) {\vector(0,-1){.75}} -\put(4.45,1.5) {\line(-1,0){2.95}} -\end{picture}} - -\begin{verbatim} -2: GENTRANSHUT NIL; - -T -\end{verbatim} -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1,.75){T}} -\put(1,0) {\framebox(1,.75){"f5"}} -\put(2,0) {\framebox(1,.75){"f6"}} -\put(.55,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(.5,1.5) {\vector(0,-1){.75}} -\end{picture}} - -\begin{verbatim} -3: GENTRANSHUT ALL!*; - -T -\end{verbatim} - -Output file list: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(1,.75){T}} -\put(.55,1.5) {\makebox(0,0) [bl]{\tt current-output}} -\put(.5,1.5) {\vector(0,-1){.75}} -\end{picture}} - -\end{describe} - -\subsection{The Output File Stack} -Section~\ref{file:selection} -\index{files ! in GENTRAN} -explained the {\bf GENTRANOUT} and {\bf GENTRANSHUT} -commands which are very similar to the REDUCE {\bf OUT} and {\bf SHUT} -commands but redirect {\it only code generated as side effects of GENTRAN -commands\/} to files. This section describes another pair of file -handling commands provided by GENTRAN. - -In some code generation applications it may be convenient to be -able to send generated code to one (set of) file(s), then -temporarily send code to another (set of) file(s), and later -resume sending generated code to the first (set of) file(s). In -other words, it is convenient to think of the output files as -being arranged in a stack which can be pushed whenever new -files are to be written to temporarily, and popped whenever -previously written-to files are to be appended onto. {\bf GENTRANPUSH} -\index{GENTRANPUSH command} \index{GENTRANPOP command} -and {\bf GENTRANPOP} enable the user to manipulate a stack of open -output files in these ways. - -{\bf GENTRANPUSH} simply pushes a (set of) file(s) onto -the stack and opens each one that is not already open for -output. {\bf GENTRANPOP} deletes the top-most occurrence of -the given file(s) from the stack and closes each one that is no -longer in the stack. The stack is initialized to one element: the -terminal. This element is always on the bottom of the stack, and thus, -is the default output file. The current output file is always the -file(s) on top of the stack. - -\subsubsection{GENTRANPUSH} -\index{GENTRANPUSH command} -\begin{describe}{Syntax:} -{\bf GENTRANPUSH} {\it f1,f2,\dots\ ,fn;} -\end{describe} -\begin{describe}{Arguments:} -{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each -{\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom} & = & an output file\\ -{\bf T} & = & the terminal\\ -{\bf NIL} & = & the current output file(s)\\ -{\bf ALL!*} & = & all files currently open for output \\ -& & by GENTRAN\\ -\end{tabular} -\end{center} -\end{describe} -\begin{describe}{Side Effects:} -{\bf GENTRANPUSH} creates a list of file name(s) represented by -{\it f1,f2,\dots\ ,fn\/} and pushes that list onto the output stack. Each file -in the list that is not already open for output is opened at this time. The -current output file is reset to this new element on the top of the stack. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRANPUSH} returns the list of files represented by -{\it f1,f2,\dots\ ,fn\/}; -i.e., the current output file(s) after the command has been executed. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** OUTPUT FILE ALREADY EXISTS - OVERWRITE FILE? (Y/N) - -***** WRONG TYPE OF ARG -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,1)(0,0) -\put(0,0) {\framebox(3,1){}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,.5) {\vector(-1,0){1}} -\put(4.1,.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - - -\begin{verbatim} -1: GENTRANPUSH "f1"; - -"f1" -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,1.5)(0,0) -\put(0,0) {\framebox(3,1.5){}} -\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,1) {\vector(-1,0){1}} -\put(4.1,1) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -2: GENTRANPUSH "f2","f3"; - -{"f2","f3"} -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2)(0,0) -\put(0,0) {\framebox(3,2){}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,1.5) {\vector(-1,0){1}} -\put(4.1,1.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -3: GENTRANPUSH NIL,T; - -{"f2","f3",T} -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2.5)(0,0) -\put(0,0) {\framebox(3,2.5){}} -\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,2) {\vector(-1,0){1}} -\put(4.1,2) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -4: GENTRANPUSH "f1"; - -"f1" -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,3)(0,0) -\put(0,0) {\framebox(3,3){}} -\put(0.25,2.5) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,2.5) {\vector(-1,0){1}} -\put(4.1,2.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -5: GENTRANPUSH ALL!*; - -{"f1","f2","f3"} -\end{verbatim} - -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,3.5)(0,0) -\put(0,0) {\framebox(3,3.5){}} -\put(0.25,3) {\makebox(0,0)[cl]{"f1" "f2" "f3"}} -\put(0.25,2.5) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,3) {\vector(-1,0){1}} -\put(4.1,3) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\end{describe} - -\subsubsection{GENTRANPOP} -\index{GENTRANPOP command} -\begin{describe}{Syntax:} -{\bf GENTRANPOP} {\it f1,f2,\dots\ ,fn;} -\end{describe} -\begin{describe}{Arguments:} -{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each -{\it f\/} is one of: -\begin{center} -\begin{tabular}{lll} -{\it an atom} & = & an output file\\ -{\bf T} & = & the terminal\\ -{\bf NIL} & = & the current output file(s)\\ -{\bf ALL!*} & = & all files currently open for output \\ -& & by GENTRAN\\ -\end{tabular} -\end{center} -\end{describe} -\begin{describe}{Side Effects:} -{\bf GENTRANPOP} deletes the top-most occurrence of the single element -containing the file name(s) represented by {\it f1,f2,\dots\ ,fn\/} -from the output stack. Files whose names have been completely removed from -the output stack are closed. The current output file is reset to the -(new) element on the top of the output stack. -\end{describe} -\begin{describe}{Returned Value:} -{\bf GENTRANPOP} returns the current output file(s) after this command -has been executed. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** FILE NOT OPEN FOR OUTPUT - -***** WRONG TYPE OF ARG -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,4)(0,0) -\put(0,0) {\framebox(3,4){}} -\put(0.25,3.5) {\makebox(0,0)[cl]{"f4"}} -\put(0.25,3) {\makebox(0,0)[cl]{"f4" "f2" T}} -\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} -\put(0.25,2) {\makebox(0,0)[cl]{T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,3.5) {\vector(-1,0){1}} -\put(4.1,3.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -1: GENTRANPOP NIL; - -{"f4","f2",T} -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,3.5)(0,0) -\put(0,0) {\framebox(3,3.5){}} -\put(0.25,3) {\makebox(0,0)[cl]{"f4" "f2" T}} -\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} -\put(0.25,2) {\makebox(0,0)[cl]{T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,3) {\vector(-1,0){1}} -\put(4.1,3) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -2: GENTRANPOP NIL; - -"f4" -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,3)(0,0) -\put(0,0) {\framebox(3,3){}} -\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} -\put(0.25,2) {\makebox(0,0)[cl]{T}} -\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} -\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,2.5) {\vector(-1,0){1}} -\put(4.1,2.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -3: GENTRANPOP "f2","f1"; - -"f4" -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,2.5)(0,0) -\put(0,0) {\framebox(3,2.5){}} -\put(0.25,2) {\makebox(0,0)[cl]{"f4"}} -\put(0.25,1.5) {\makebox(0,0)[cl]{T}} -\put(0.25,1) {\makebox(0,0)[cl]{"f3"}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,2) {\vector(-1,0){1}} -\put(4.1,2) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\begin{verbatim} -4: GENTRANPOP ALL!*; - -T -\end{verbatim} -Output stack: - -{\setlength{\unitlength}{1cm} -\begin{picture}(10,1)(0,0) -\put(0,0) {\framebox(3,1){}} -\put(0.25,.5) {\makebox(0,0)[cl]{T}} -\put(4,.5) {\vector(-1,0){1}} -\put(4.1,.5) {\makebox(0,0)[cl]{\tt current-output}} -\end{picture}} - -\end{describe} - -\subsection{Temporary Output Redirection} -Sections~\ref{translation} and ~\ref{templates} -explain how to use the code generation and -template processing commands. The syntax for these two commands -is: -\index{output redirection (temporary)} -\index{GENTRAN command} \index{GENTRANIN command} - -\begin{tabular}{lll} -&\multicolumn{2}{l}{{\bf GENTRAN} {\it stmt\/} [{\bf OUT} {\it f1,f2,\dots\ - ,fn\/}]{\it ;}}\\ -&&and\\ -&\multicolumn{2}{l}{{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm\/} [{\bf OUT} - {\it f1,f2,\dots\ ,fn\/}]{\it ;}}\\ -\end{tabular} - -The optional parts of these two commands can be used for {\it temporary} -output redirection; they can be used when the current output -file is to be temporarily reset, for this command only. - -Thus the following two sequences of commands are equivalent: -\begin{verbatim} -10: GENTRANPUSH "f1",T$ - -11: GENTRAN ... $ - -12: GENTRANPOP NIL$ -\end{verbatim} - -and - -\begin{verbatim} -10: GENTRAN -10: ... -10: OUT "f1",T$ -\end{verbatim} - -\section{Modification of the Code Generation Process}\label{GENTRAN:mod} - -GENTRAN is designed to be flexible enough to be used in a variety of -code generation applications. For this reason, several mode -switches and variables are provided to enable the user to tailor the -code generation process to meet his or her particular needs. - -\subsection{Mode Switches} -\index{GENTRAN package ! switches} -The following GENTRAN mode switches can be turned on and off with the -REDUCE {\bf ON} and {\bf OFF} commands. - -\begin{describe}{DOUBLE} -\index{DOUBLE switch} \index{precision} -\begin{itemize} -\item When turned on, causes (where appropriate): -\begin{itemize} -\item floating point numbers to be printed in double precision format; -\item intrinsic functions to be replaced by their double precision -counterparts; -\item generated type declarations to be of double precision form. -\end{itemize} -See also section~\ref{precision} on page~\pageref{precision}. -\item default setting: off -\end{itemize} -\end{describe} - -\begin{describe}{GENDECS} -\index{GENDECS switch} -\begin{itemize} -\item when turned on, allows type declarations to be generated automatically; -otherwise, type information is stored in but not automatically retrieved -from the symbol table. See also sections~\ref{explicit:type} on -page~\pageref{explicit:type}, \ref{more:type} on page~\pageref{more:type}, -and \ref{template:type} on page~\pageref{template:type}. -\item default setting: on -\end{itemize} -\end{describe} - -\begin{describe}{GENTRANOPT} -\index{GENTRANOPT switch} -\begin{itemize} -\item when turned on, replaces each block of straightline code by -an optimized sequence of assignments. -The Code Optimizer takes a sequence of assignments and replaces common -subexpressions with temporary variables. It returns the resulting assignment -statements with common-subexpression-to-temporary-variable assignment -statements preceding them -\item default setting: off -\end{itemize} -\end{describe} - -\begin{describe}{GENTRANSEG} -\index{GENTRANSEG switch} -\begin{itemize} -\item when turned on, checks the print length of expressions and breaks -those expressions that are longer than {\bf MAXEXPPRINTLEN!*} down -\ttindex{MAXEXPPRINTLEN"!*} -into subexpressions which are assigned to temporary variables. -See also section~\ref{segmentation} on page~\pageref{segmentation}. -\item default setting: on -\end{itemize} -\end{describe} - -\begin{describe}{GETDECS} -\index{GETDECS switch} -\begin{itemize} -\item when on, causes: -\begin{itemize} -\item the indices of loops to be declared integer; -\item objects without an explicit type declaration to be declared of the type -given by the variable {\bf DEFTYPE!*}. \ttindex{DEFTYPE"!*} -\end{itemize} -See also section~\ref{implicit:type} on page~\pageref{implicit:type}. -\item default setting: off -\end{itemize} -\end{describe} - -\begin{describe}{KEEPDECS} -\index{KEEPDECS switch} -\begin{itemize} -\item when on, prevents declarations being removed from the symbol table when -type declarations are generated. -\item default: off -\end{itemize} -\end{describe} - -\begin{describe}{MAKECALLS} -\index{MAKECALLS switch} -\begin{itemize} -\item when turned on, causes GENTRAN to translate functional expressions as -subprogram calls. -\item default setting: on -\end{itemize} -\end{describe} - -\begin{describe}{PERIOD} -\index{PERIOD switch} -\begin{itemize} -\item when turned on, causes all integers to be printed out as floating point -numbers except: -\begin{itemize} -\item exponents; -\item variable subscripts; -\item index values in DO-type loops; -\item those which have been declared to be integers. -\end{itemize} -\item default setting: on -\end{itemize} -\end{describe} - - -\subsection{Variables} -\index{GENTRAN package ! variables} -Several global variables are provided in GENTRAN to enable the -user to -\begin{itemize} -\item select the target language -\item control expression segmentation -\item change automatically generated variable names and statement numbers -\item modify the code formatter -\end{itemize} - -The following four subsections describe these variables\footnote{ -Note that when an atomic value (other than an integer) is assigned to a -variable, that value must be quoted. For example, -{\bf GENTRANLANG!* := 'FORTRAN\$} -assigns the atom {\bf FORTRAN} to the variable {\bf GENTRANLANG!*}.}. - -\subsubsection{Target Language Selection} -\begin{describe}{GENTRANLANG!*} -\ttindex{GENTRANLANG"!*} -\begin{itemize} -\item target language (FORTRAN, RATFOR, PASCAL or C) -See also section~\ref{gentranlang} on page~\pageref{gentranlang}. -\item value type: atom -\item default value: FORTRAN -\end{itemize} -\end{describe} - -\subsubsection{Expression Segmentation Control} -\begin{describe}{MAXEXPPRINTLEN!*} -\ttindex{MAXEXPPRINTLEN"!*} -\begin{itemize} -\item value used to determine whether or not an expression should be -segmented; maximum number of characters permitted in an expression -in the target language (excluding spaces printed for formatting). -See also section~\ref{segmentation} on page~\pageref{segmentation}. -\item value type: integer -\item default value: 800 -\end{itemize} -\end{describe} - -\subsubsection{Variable Names \& Statement Numbers} -\begin{describe}{TEMPVARNAME!*} -\ttindex{TEMPVARNAME"!*} -\begin{itemize} -\item name used as prefix in generating temporary variable names. -See also section~\ref{tempvars} on page~\pageref{tempvars}. -\item value type: atom -\item default value: T -\end{itemize} -\end{describe} - -\begin{describe}{TEMPVARNUM!*} -\ttindex{TEMPVARNUM"!*} -\begin{itemize} -\item number appended to {\bf TEMPVARNAME!*} to create a temporary variable -name. If the temporary variable name resulting from appending -{\bf TEMPVARNUM!*} onto {\bf TEMPVARNAME!*} has already been generated -and still holds a useful value, then {\bf TEMPVARNUM!*} is incremented -and temporary variable names are compressed until one is found which -was not previously generated or does not still hold a significant value. -See also section~\ref{tempvars} on page~\pageref{tempvars}. -\item value type: integer -\item default value: 0 -\end{itemize} -\end{describe} - -\begin{describe}{TEMPVARTYPE!*} -\ttindex{TEMPVARTYPE"!*} -\begin{itemize} -\item target language variable type (e.g., INTEGER, REAL!*8, FLOAT, etc) used -as a default for automatically generated variables whose type cannot be -determined otherwise. If {\bf TEMPVARTYPE!*} is NIL, then generated -temporary variables whose type cannot be determined are not automatically -declared. See also section~\ref{tempvars} on page~\pageref{tempvars}. -\item value type: atom -\item default value: NIL -\end{itemize} -\end{describe} - -\begin{describe}{GENSTMTNUM!*} -\ttindex{GENSTMTNUM"!*} -\begin{itemize} -\item number used when a statement number must be generated -\item value type: integer -\item default value: 25000 -\end{itemize} -\end{describe} - -\begin{describe}{GENSTMTINCR!*} -\ttindex{GENSTMTINCR"!*} -\begin{itemize} -\item number by which {\bf GENSTMTNUM!*} is increased each time a new -statement number is generated. -\item value type: integer -\item default value: 1 -\end{itemize} -\end{describe} - -\begin{describe}{DEFTYPE!*} -\ttindex{DEFTYPE"!*} -\begin{itemize} -\item default type for objects when the switch {\bf GETDECS} is on. See also -section~\ref{implicit:type} on page~\pageref{implicit:type}. -\item value type: atom -\item default value: real -\end{itemize} -\end{describe} - -\subsubsection{Code Formatting} -\begin{describe}{FORTCURRIND!*} -\ttindex{FORTCURRIND"!*} -\begin{itemize} -\item number of blank spaces printed at the beginning of each line of -generated FORTRAN code beyond column 6 -\item value type: integer -\item default value: 0 -\end{itemize} -\end{describe} - -\begin{describe}{RATCURRIND!*} -\ttindex{RATCURRIND"!*} -\begin{itemize} -\item number of blank spaces printed at the beginning of each line of -generated RATFOR code. -\item value type: integer -\item default value: 0 -\end{itemize} -\end{describe} - -\begin{describe}{CCURRIND!*} -\ttindex{CCURRIND"!*} -\begin{itemize} -\item number of blank spaces printed at the beginning of each line of -generated C code. -\item value type: integer -\item default value: 0 -\end{itemize} -\end{describe} - -\begin{describe}{PASCCURRIND!*} -\ttindex{PASCCURRIND"!*} -\begin{itemize} -\item number of blank spaces printed at the beginning of each line of -generated PASCAL code. -\item value type: integer -\item default value: 0 -\end{itemize} -\end{describe} - -\begin{describe}{TABLEN!*} -\ttindex{TABLEN"!*} -\begin{itemize} -\item number of blank spaces printed for each new level of indentation. -\item value type: integer -\item default value: 4 -\end{itemize} -\end{describe} - -\begin{describe}{FORTLINELEN!*} -\ttindex{FORTLINELEN"!*} -\begin{itemize} -\item maximum number of characters printed on each line of generated FORTRAN -code. -\item value type: integer -\item default value: 72 -\end{itemize} -\end{describe} - -\begin{describe}{RATLINELEN!*} -\ttindex{RATLINELEN"!*} -\begin{itemize} -\item maximum number of characters printed on each line of generated RATFOR -code. -\item value type: integer -\item default value: 80 -\end{itemize} -\end{describe} - -\begin{describe}{CLINELEN!*} -\ttindex{CLINELEN"!*} -\begin{itemize} -\item maximum number of characters printed on each line of generated C code. -\item value type: integer -\item default value: 80 -\end{itemize} -\end{describe} - -\begin{describe}{PASCLINELEN!*} -\ttindex{PASCLINELEN"!*} -\begin{itemize} -\item maximum number of characters printed on each line of generated PASCAL -code. -\item value type: integer -\item default value: 70 -\end{itemize} -\end{describe} - -\begin{describe}{MINFORTLINELEN!*} -\ttindex{MINFORTLINELEN"!*} -\begin{itemize} -\item minimum number of characters printed on each line of generated FORTRAN -code after indentation. -\item value type: integer -\item default value: 40 -\end{itemize} -\end{describe} - -\begin{describe}{MINRATLINELEN!*} -\ttindex{MINRATLINELEN"!*} -\begin{itemize} -\item minimum number of characters printed on each line of generated RATFOR -code after indentation. -\item value type: integer -\item default value: 40 -\end{itemize} -\end{describe} - -\begin{describe}{MINCLINELEN!*} -\ttindex{MINCLINELEN"!*} -\begin{itemize} -\item minimum number of characters printed on each line of generated C -code after indentation. -\item value type: integer -\item default value: 40 -\end{itemize} -\end{describe} - -\begin{describe}{MINPASCLINELEN!*} -\ttindex{MINPASCLINELEN"!*} -\begin{itemize} -\item minimum number of characters printed on each line of generated PASCAL -code after indentation. -\item value type: integer -\item default value: 40 -\end{itemize} -\end{describe} - -\section{Examples}\label{GENTRAN:examples} -\index{GENTRAN package ! example} - -Short examples have been given throughout this manual to illustrate -usage of the GENTRAN commands. This section gives complete code -generation examples. - -\subsection{Interactive Code Generation} \index{GENTRAN package ! example} -\index{interactive code generation} -Suppose we wish to generate a FORTRAN subprogram which can be used for -\index{Graeffe's Root-Squaring Method} -computing the roots of a polynomial by Graeffe's Root-Squaring Method\footnote{ -This is for instance convenient for ill-conditioned polynomials. More -details are given in {\it Introduction to Numerical Analysis\/} by -C. E. Froberg, Addison-Wesley Publishing Company, 1966.}. This -method states that the roots $x_i$ of a polynomial -$$P_n(x) = \sum_{i=0}^{n}{a_i x^{n-i}} $$ -can be found by constructing the polynomial -$$P^{*}_n\left({x^2}\right) = \left( a_0x^n + a_2x^{n-2} + \dots\right)^2 - -\left( a_1x^{n-1} + a_3x^{n-3} + \dots\right)^2$$ -with roots $x_i^2$ -When read into REDUCE, the following file of REDUCE statements -will place the coefficients of $P^{*}_n$ -into the list B for some user-entered value of n greater than zero. - -Contents of file {\tt graeffe.red}:\footnote{ -In accordance with section~\ref{explicit:type}, -the subscripts of A are I+1 instead of I.} -\begin{framedverbatim} -OPERATOR A$ -Q := FOR I := 0 STEP 2 UNTIL n SUM (A(I+1)*X^(n-I))$ -R := FOR I := 1 STEP 2 UNTIL n-1 SUM (A(I+1)*X^(n-I))$ -P := Q^2 - R^2$ -LET X^2 = Y$ -B := COEFF(P,Y)$ -END$ -\end{framedverbatim} - -Now a numerical subprogram can be generated with assignment -statements for the coefficients of $P^{*}_n$ (now stored in list B in -REDUCE). Since these coefficients are given in terms of the coefficients -of $P_n$ (i.e., operator A in REDUCE), the subprogram will need two -parameters: A and B, each of which must be arrays of size n+1. - -The following REDUCE session will create subroutine GRAEFF for a polynomial -of degree n=10 and write it to file {\tt graeffe.f}: -{\small -\begin{verbatim} -1: n := 10$ - -2: IN "graeffe.red"$ - -3: GENTRANLANG!* := 'FORTRAN$ - -4: ON DOUBLE$ - -5: GENTRAN -5: ( -5: PROCEDURE GRAEFF(A,B); -5: BEGIN -5: DECLARE -5: << -5: GRAEFF : SUBROUTINE; -5: A(11),B(11) : REAL -5: >>; -5: LITERAL -5: "C",CR!*, -5: "C",TAB!*,"GRAEFFE ROOT-SQUARING METHOD TO FIND",CR!*, -5: "C",TAB!*,"ROOTS OF A POLYNOMIAL",CR!*, -5: "C",CR!*; -5: B(1) :=: PART (B,1); -5: B(2) :=: PART (B,2); -5: B(3) :=: PART (B,3); -5: B(4) :=: PART (B,4); -5: B(5) :=: PART (B,5); -5: B(6) :=: PART (B,6); -5: B(7) :=: PART (B,7); -5: B(8) :=: PART (B,8); -5: B(9) :=: PART (B,9); -5: B(10) :=: PART (B,10); -5: B(11) :=: PART (B,11) -5: END -5: ) -5: OUT "graeffe.f"$ -\end{verbatim} -} - -Contents of file {\tt graeffe.f}: -\begin{framedverbatim} - SUBROUTINE GRAEFF(A,B) - DOUBLE PRECISION A(11),B(11) -C -C GRAEFFE ROOT-SQUARING METHOD TO FIND -C ROOTS OF A POLYNOMIAL -C - B(1)=A(11)**2 - B(2)=2.0D0*A(11)*A(9)-A(10)**2 - B(3)=2.0D0*A(11)*A(7)-(2.0D0*A(10)*A(8))+A(9)**2 - B(4)=2.0D0*A(11)*A(5)-(2.0D0*A(10)*A(6))+2.0D0*A(9)*A(7 - . )-A(8)**2 - B(5)=2.0D0*A(11)*A(3)-(2.0D0*A(10)*A(4))+2.0D0*A(9)*A(5 - . )-(2.0D0*A(8)*A(6))+A(7)**2 - B(6)=2.0D0*A(11)*A(1)-(2.0D0*A(10)*A(2))+2.0D0*A(9)*A(3 - . )-(2.0D0*A(8)*A(4))+2.0D0*A(7)*A(5)-A(6)**2 - B(7)=2.0D0*A(9)*A(1)-(2.0D0*A(8)*A(2))+2.0D0*A(7)*A(3)- - . (2.0D0*A(6)*A(4))+A(5)**2 - B(8)=2.0D0*A(7)*A(1)-(2.0D0*A(6)*A(2))+2.0D0*A(5)*A(3)- - . A(4)**2 - B(9)=2.0D0*A(5)*A(1)-(2.0D0*A(4)*A(2))+A(3)**2 - B(10)=2.0D0*A(3)*A(1)-A(2)**2 - B(11)=A(1)**2 - RETURN - END -\end{framedverbatim} - -\subsection{Code Generation, Segmentation \& Temporary Variables} -\index{GENTRAN package ! example} -The following 3 x 3 inertia matrix M was derived in the course of -some research \footnote{For details see: -Bos, A. M. and M. J. L. Tiernego. ``Formula Manipulation in the -Bond Graph Modelling and Simulation of Large Mechanical Systems'', -{\it Journal of the Franklin Institute} , Pergamon Press Ltd., -Vol. 319, No. 1/2, pp. 51-65, January/February 1985.}: -\begin{eqnarray*} -M(1,1) & = & 18*\cos (q_3)*\cos (q_2)*m_{30}*p^2 - \sin ^2(q_3) *j_{30}y + - \sin ^2(q_3) \\ - & & *j_{30}z - 9*\sin ^2(q_3) *m_{30}*p^2 + j_{10}y + j_{30}y + - m_{10}*p^2 + \\ - & & 18*m_{30}*p^2\\ -M(1,2) & = & 9*\cos (q_3)*\cos (q_2)*m_{30}*p^2 - \sin ^2(q_3) *j_{30}y - +\sin ^2(q_3) \\ - & & *j_{30}z - 9*\sin ^2(q_3) *m_{30}*p^2 + j_{30}y + 9* m_{30}*p^2\\ -M(2,1) & = & M(1,2)\\ -M(1,3) & = & - 9*\sin (q_3)*\sin (q_2)*m_{30}*p^2\\ -M(3,1) & = & M(1,3)\\ -M(2,2) & = & - \sin ^2(q_3) *j_{30}y + \sin ^2(q_3) *j_{30}z - - 9*\sin ^2(q_3)*m_{30}*p^2 \\ -& & + j_{30}y + 9*m_{30}*p^2\\ -M(2,3) & = & 0\\ -M(3,2) & = & M(2,3)\\ -M(3,3) & = & 9*m_{30}*p^2 + j_{30}x\\ -\end{eqnarray*} -We know M is symmetric. We wish to generate numerical code -to compute values for M and its inverse matrix. - -\subsubsection{Code Generation} -\label{code:example} -Generating code for matrix M and its inverse matrix is -straightforward. We can simply generate an assignment statement -for each element of M, compute the inverse matrix MIV, and generate -an assignment statement for each element of MIV. Since we -know M is symmetric, we know that MIV will also be symmetric. To -avoid duplicate computations, we will not generate assignments -for elements below the main diagonals of these matrices. Instead, -we will copy elements across the main diagonal by generating -nested loops. The following REDUCE session will write to the file {\tt m1.f}: - -\begin{verbatim} -1: IN "m.red"$ % Initialize M - -2: GENTRANOUT "m1.f"$ - -3: GENTRANLANG!* := 'FORTRAN$ - -4: ON DOUBLE$ - -5: FOR J := 1 : 3 DO -5: FOR K := J : 3 DO -5: GENTRAN M(J,K) ::=: M(J,K)$ - -6: MIV := M^(-1)$ - -7: FOR J := 1 : 3 DO -7: FOR K := J : 3 DO -7: GENTRAN MIV(J,K) ::=: MIV(J,K)$ - -8: GENTRAN -8: FOR J := 1 : 3 DO -8: FOR K := J+1 : 3 DO -8: << -8: M(K,J) := M(J,K); -8: MIV(K,J) := MIV(J,K) -8: >>$ - -9: GENTRANSHUT "m1.f"$ -\end{verbatim} -The contents of {\tt m1.f} are reproduced in~\ref{appc} on page~\pageref{appc}. - -This code was generated with the segmentation facility turned off. However, -most FORTRAN compilers cannot handle statements more than 20 lines -long. The next section shows how to generate segmented assignments. - -\subsubsection{Segmentation} -\label{seg:example} -\index{segmented assignments} -Large arithmetic expressions can be broken into pieces of manageable -size with the expression segmentation facility. The following REDUCE -session will write segmented assignment statements to the -file {\tt m2.f}. Large arithmetic expressions will be broken into -subexpressions of approximately 300 characters in length. - -\begin{verbatim} -1: IN "m.red"$ % Initialize M - -2: GENTRANOUT "m2.f"$ - -3: ON DOUBLE$ - -4: ON GENTRANSEG$ - -5: MAXEXPPRINTLEN!* := 300$ - -6: FOR J := 1 : 3 DO -6: FOR K := J : 3 DO -6: GENTRAN M(J,K) ::=: M(J,K)$ - -7: MIV := M^(-1)$ - -8: FOR J := 1 : 3 DO -8: FOR K := J : 3 DO -8: GENTRAN MIV(J,K) ::=: MIV(J,K)$ - -9: GENTRAN -9: FOR J := 1 : 3 DO -9: FOR K := J+1 : 3 DO -9: << -9: M(K,J) := M(J,K); -9: MIV(K,J) := MIV(J,K) -9: >>$ - -10: GENTRANSHUT "m2.f"$ -\end{verbatim} - -The contents of file {\tt m2.f} are reproduced in~\ref{appc} on -page~\pageref{appc}. - -\subsubsection{Generation of Temporary Variables to Suppress Simplification} -\label{tempvar:example} -We can dramatically improve the efficiency of the code generated -in sections~\ref{code:example} on page~\pageref{code:example} and -\ref{seg:example} on page~\pageref{seg:example} -by replacing expressions by temporary variables before computing the -inverse matrix. This effectively suppresses simplification; these -expressions will not be substituted into later computations. We -will replace each non-zero element of the REDUCE matrix M by a -generated variable name, and generate a numerical assignment statement -to reflect that substitution in the numerical program being generated. - -The following REDUCE session will write to the file {\tt m3.f}: -\begin{verbatim} -1: in "m.red"$ % Initialize M - -2: GENTRANOUT "m3.f"$ - -3: GENTRANLANG!* := 'FORTRAN$ - -4: ON DOUBLE$ - -5: FOR J := 1 : 3 DO -5: FOR K := J : 3 DO -5: GENTRAN M(J,K) ::=: M(J,K)$ - -6: SHARE VAR$ - -7: FOR J := 1 : 3 DO -7: FOR K := J : 3 DO -7: IF M(J,K) NEQ 0 THEN -7: << -7: VAR := TEMPVAR(NIL)$ -7: MARKVAR VAR$ -7: M(J,K) := VAR$ -7: M(K,J) := VAR$ -7: GENTRAN -7: EVAL(VAR) := M(EVAL(J),EVAL(K)) -7: >>$ - -8: COMMENT ** Contents of matrix M: **$ - -9: M; - -[T0 T1 T2] -[ ] -[T1 T3 0 ] -[ ] -[T2 0 T4] - - -10: MIV := M^(-1)$ - -11: FOR J := 1 : 3 DO -11: FOR K := J : 3 DO -11: GENTRAN MIV(J,K) ::=: MIV(J,K)$ - -12: GENTRAN -12: FOR J := 1 : 3 DO -12: FOR K := J+1 : 3 DO -12: << -12: M(K,J) := M(J,K); -12: MIV(K,J) := MIV(J,K) -12: >>$ - -13: GENTRANSHUT "m3.f"$ -\end{verbatim} - -Contents of file {\tt m3.f}: - -\begin{framedverbatim} - M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE - . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 - . +J30Y+J10Y - M(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*DCOS(DBLE( - . Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+J30Y - M(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30) - M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ - . J30Y - M(2,3)=0.0D0 - M(3,3)=9.0D0*P**2*M30+J30X - T0=M(1,1) - T1=M(1,2) - T2=M(1,3) - T3=M(2,2) - T4=M(3,3) - MIV(1,1)=-(T4*T3)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) - MIV(1,2)=(T4*T1)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) - MIV(1,3)=(T2*T3)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) - MIV(2,2)=(-(T4*T0)+T2**2)/(T4*T1**2-(T4*T3*T0)+T2**2* - . T3) - MIV(2,3)=-(T1*T2)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) - MIV(3,3)=(T1**2-(T3*T0))/(T4*T1**2-(T4*T3*T0)+T2**2*T3) - DO 25009 J=1,3 - DO 25010 K=J+1,3 - M(K,J)=M(J,K) - MIV(K,J)=MIV(J,K) -25010 CONTINUE -25009 CONTINUE -\end{framedverbatim} - -\subsection{Template Processing} \index{template processing} -\index{GENTRAN package ! example} \index{Automatic Circuitry Code Generator} -Circuit simulation plays a vital role in computer hardware -development. A recent paper\footnote{Loe, K. F., N. Ohsawa, and E. -Goto. ``Design of an Automatic Circuitry Code Generator (ACCG)'', -{\it RSYMSAC Proceedings}, Wako-shi, Saitama, Japan. 1984.} describes -the design of an Automatic Circuitry Code Generator (ACCG), which -generates circuit simulation programs based on user-supplied circuit -specifications. The actual code generator consists of a series of -REDUCE {\bf WRITE} statements, each of which writes one line of -FORTRAN code. - -This section presents an alternative implementation for the ACCG -which uses GENTRAN's template processor to generate code. Template -processing is a much more natural method of code generation than the -REDUCE {\bf WRITE} statement method. - -First we will put all REDUCE calculations into two files: {\tt rk.red} and -{\tt ham.red}. - -Contents of file {\tt rk.red}:\footnote{ -Line 11 of procedure RUNGEKUTTA was changed from -\begin{center} -{\tt K41 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2);} -\end{center} -as given in (Loe84), to -\begin{center} -{\tt K42 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2);} -\end{center} -} -\begin{framedverbatim} -COMMENT -- RUNGE-KUTTA METHOD --$ -PROCEDURE RUNGEKUTTA(P1, P2, P, Q, TT); -BEGIN -SCALAR K11,K12,K21,K22,K31,K32,K41,K42; -K11 := HH*P1; -K12 := HH*P2; -K21 := HH*SUB(TT=TT+HH/2, P=P+K11/2, Q=Q+K12/2, P1); -K22 := HH*SUB(TT=TT+HH/2, P=P+K11/2, Q=Q+K12/2, P2); -K31 := HH*SUB(TT=TT+HH/2, P=P+K21/2, Q=Q+K22/2, P1); -K32 := HH*SUB(TT=TT+HH/2, P=P+K21/2, Q=Q+K22/2, P2); -K41 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P1); -K42 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2); -PN := P + (K11 + 2*K21 + 2*K31 + K41)/6; -QN := Q + (K12 + 2*K22 + 2*K32 + K42)/6 -END$ -END$ -\end{framedverbatim} - -Contents of file {\tt ham.red}: - -\begin{framedverbatim} -COMMENT -- HAMILTONIAN CALCULATION --$ -DIFQ := DF(H,P)$ -DIFP := -DF(H,Q) - SUB(QDOT=P/M, DF(D,QDOT))$ -RUNGEKUTTA(DIFP, DIFQ, P, Q, TT)$ -END$ -\end{framedverbatim} - -Next we will create a template file with an outline of the target -FORTRAN program and GENTRAN commands. - -Contents of file {\tt runge.tem}: - -\begin{framedverbatim} - PROGRAM RUNGE - IMPLICIT DOUBLE PRECISION (K,M) -C -C INPUT -C - WRITE(6,*) 'INITIAL VALUE OF P' - READ(5,*) P - WRITE(6,*) ' P = ', P - WRITE(6,*) 'INITIAL VALUE OF Q' - READ(5,*) Q - WRITE(6,*) ' Q = ', Q - WRITE(6,*) 'VALUE OF M' - READ(5,*) M - WRITE(6,*) ' M = ', M - WRITE(6,*) 'VALUE OF K0' - READ(5,*) K0 - WRITE(6,*) ' K0 = ', K0 - WRITE(6,*) 'VALUE OF B' - READ(5,*) B - WRITE(6,*) ' B = ', B - WRITE(6,*) 'STEP SIZE OF T' - READ(5,*) HH - WRITE(6,*) ' STEP SIZE OF T = ', HH - WRITE(6,*) 'FINAL VALUE OF T' - READ(5,*) TP - WRITE(6,*) ' FINAL VALUE OF T = ', TP -C -C INITIALIZATION -C - TT=0.0D0 -;BEGIN; - GENTRAN - LITERAL - TAB!*, "WRITE(9,*) ' H = ", EVAL(H), "'", CR!*, - TAB!*, "WRITE(9,*) ' D = ", EVAL(D), "'", CR!*$ -;END; - WRITE(9,901) C -901 FORMAT(' C= ',D20.10) - WRITE(9,910) TT, Q, P -910 FORMAT(' '3D20.10) -C -C LOOP -C -;BEGIN; - GENTRAN - REPEAT - << - PN :=: PN; - Q :=: QN; - P := PN; - TT := TT + HH; - LITERAL - TAB!*, "WRITE(9,910) TT, QQ, P", CR!* - >> - UNTIL TT >= TF$ -;END; - STOP - END -;END; -\end{framedverbatim} - -Now we can generate a circuit simulation program simply by starting -a REDUCE session and following three steps: -\begin{enumerate} -\item Enter circuit specifications. -\item Perform calculations. -\item Call the GENTRAN template processor. -\end{enumerate} -For example, the following REDUCE session will write a simulation -program to the file {\tt runge.f}: -\begin{verbatim} -1: COMMENT -- INPUT --$ - -2: K := 1/(2*M)*P^2$ % kinetic energy - -3: U := K0/2*Q^2$ % potential energy - -4: D := B/2*QDOT$ % dissipating function - -5: H := K + U$ % hamiltonian - -6: COMMENT -- CALCULATIONS --$ - -7: IN "rk.red", "ham.red"$ - -8: COMMENT -- FORTRAN CODE GENERATION --$ - -9: GENTRANLANG!* := 'FORTRAN$ - -10: ON DOUBLE$ - -11: GENTRANIN "runge.tem" OUT "runge.f"$ -\end{verbatim} - -Contents of file {\tt runge.f}: -\begin{framedverbatim} - PROGRAM RUNGE - IMPLICIT DOUBLE PRECISION (K,M) -C -C INPUT -C - WRITE(6,*) 'INITIAL VALUE OF P' - READ(5,*) P - WRITE(6,*) ' P = ', P - WRITE(6,*) 'INITIAL VALUE OF Q' - READ(5,*) Q - WRITE(6,*) ' Q = ', Q - WRITE(6,*) 'VALUE OF M' - READ(5,*) M - WRITE(6,*) ' M = ', M - WRITE(6,*) 'VALUE OF K0' - READ(5,*) K0 - WRITE(6,*) ' K0 = ', K0 - WRITE(6,*) 'VALUE OF B' - READ(5,*) B - WRITE(6,*) ' B = ', B - WRITE(6,*) 'STEP SIZE OF T' - READ(5,*) HH - WRITE(6,*) ' STEP SIZE OF T = ', HH - WRITE(6,*) 'FINAL VALUE OF T' - READ(5,*) TP - WRITE(6,*) ' FINAL VALUE OF T = ', TP -C -C INITIALIZATION -C - TT=0.0D0 - WRITE(9,*) ' H = (M*Q**2*K0+P**2)/(2.0D0*M)' - WRITE(9,*) ' D = (B*QDOT)/2.0D0' - WRITE(9,901) C -901 FORMAT(' C= ',D20.10) - WRITE(9,910) TT, Q, P -910 FORMAT(' '3D20.10) -C -C LOOP -C -25001 CONTINUE - PN=(-(12.0D0*B*M**2*HH)+2.0D0*B*M*K0*HH**3+24.0D0* - . M**2*P-(24.0D0*M**2*Q*K0*HH)-(12.0D0*M*P*K0*HH**2) - . +4.0D0*M*Q*K0**2*HH**3+P*K0**2*HH**4)/(24.0D0*M**2 - . ) - Q=(-(12.0D0*B*M*HH**2)+B*K0*HH**4+48.0D0*M**2*Q+ - . 48.0D0*M*P*HH-(24.0D0*M*Q*K0*HH**2)-(8.0D0*P*K0*HH - . **3)+2.0D0*Q*K0**2*HH**4)/(48.0D0*M**2) - P=PN - TT=TT+HH - WRITE(9,910) TT, QQ, P - IF (.NOT.TT.GE.TF) GOTO 25001 - STOP - END -\end{framedverbatim} - -\section{Symbolic Mode Functions} -\index{symbolic mode ! in GENTRAN} - -Thus far in this manual, commands have been presented which are meant -to be used primarily in the algebraic mode of REDUCE. These commands -are designed to be used interactively. However, many code generation -applications require code to be generated under program control\footnote{ -\cite{vandenHeuvel:86ms} contains one such example.}. In these -applications, it is generally more convenient to generate code from -(computed) prefix forms. Therefore, GENTRAN provides code generation -and file handling functions designed specifically to be used in the -symbolic mode of REDUCE. This section presents the symbolic functions -which are analogous to the code generation, template processing, and -output file handling commands presented in sections \ref{GENTRAN:inter}, - \ref{GENTRAN:template}, and \ref{GENTRAN:output}. - -\subsection{Code Generation and Translation} -Sections~\ref{translation} through \ref{comments} -describe interactive commands and functions which -generate and translate code, declare variables to be of -specific types, and insert literal strings of characters into the -stream of generated code. This section describes analogous symbolic -mode code generation functions. - -\subsubsection{Translation of Prefix Forms} -In algebraic mode, the {\bf GENTRAN} command translates algorithmic -specifications supplied in the form of REDUCE statements into -numerical code. Similarly, the symbolic function {\bf SYM!-GENTRAN} -\index{SYM"!-GENTRAN command} -translates algorithmic specifications supplied in the form of REDUCE -prefix forms into numerical code. - -\begin{describe}{Syntax:} -{\bf SYM!-GENTRAN} {\it form\/}; -\end{describe} -\begin{describe}{Function Type:} -expr -\end{describe} -\begin{describe}{Argument:} -{\it form\/} is any LISP prefix form that evaluates to a -REDUCE prefix form that can be translated by GENTRAN into the target -language\footnote{ -See~\ref{appa} on page~\pageref{appa} for a complete listing of REDUCE -prefix forms that can be translated.}. -{\it form\/} may contain any number of occurrences of the special forms -\ttindex{EVAL} \ttindex{LSETQ} \ttindex{RSETQ} \ttindex{LRSETQ} -\ttindex{DECLARE} \ttindex{LITERAL} -{\bf EVAL}, {\bf LSETQ}, {\bf RSETQ}, {\bf LRSETQ}, {\bf DECLARE}, and -{\bf LITERAL} (see sections~\ref{sym:cg} through \ref{special} on -pages~\pageref{sym:cg}--\pageref{special}). -\end{describe} -\begin{describe}{Side Effects:} -{\bf SYM!-GENTRAN} translates {\it form\/} into formatted code in the target -language and writes it to the file(s) currently selected for output. -\end{describe} -\begin{describe}{Returned Value:} -{\bf SYM!-GENTRAN} returns the name(s) of the file(s) to which code -was written. If code was written to one file, the returned value is an atom; -otherwise, it is a list. -\end{describe} -\begin{describe}{Diagnostic Messages:} -\begin{verbatim} -*** OUTPUT FILE ALREADY EXISTS - - OVERWRITE FILE? (Y/N) - -***** WRONG TYPE OF ARG -\end{verbatim} -{\it exp} -\begin{verbatim} -***** CANNOT BE TRANSLATED -\end{verbatim} -\end{describe} -\begin{describe}{\example}\index{GENTRAN package ! example} -\begin{verbatim} -1: SYMBOLIC$ - -2: GENTRANLANG!* := 'FORTRAN$ - -3: SYM!-GENTRAN '(FOR I (1 1 n) DO (SETQ (V I) 0))$ - - DO 25001 I=1,N - V(I)=0.0 -25001 CONTINUE - -4: GENTRANLANG!* := 'RATFOR$ - -5: SYM!-GENTRAN '(FOR I (1 1 N) DO -5: (FOR J ((PLUS I 1) 1 N) DO -5: (PROGN -5: (SETQ (X J I) (X I J)) -5: (SETQ (Y J I) (Y I J)))))$ - -DO I=1,N - DO J=I+1,N - { - X(J,I)=X(I,J) - Y(J,I)=Y(I,J) - } - -6: GENTRANLANG!* := 'C$ - -7: SYM!-GENTRAN '(SETQ P (FOR I (1 1 N) PRODUCT I))$ - -{ - P=1; - for (I=1;I<=N;++I) - P*=I; -} - -8: GENTRANLANG!* := 'PASCAL$ - -9: SYM!-GENTRAN '(SETQ C -9: (COND ((LESSP A B) A) (T B)))$ -IF A$0.0 DO} &\verb!25004 IF(.NOT.F(N).GT.0.0)!\\ - & &\verb! . GOTO 25005!\\ -&{\bf \ \ \ \ N:=N+1\$} &\verb! N=N+1!\\ -& &\verb! GOTO 25004!\\ -& &\verb!25005 CONTINUE!\\ -& & \\ - repeat &{\bf REPEAT X:=X/2.0} &\verb!25006 CONTINUE!\\ -&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X=X/2.0!\\ -& &\verb! IF(.NOT.F(X).LT.0.0)!\\ -& &\verb! . GOTO 25006!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE Loop structures translatable to FORTRAN} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf FORTRAN CODE} \\ \hline\hline - Conditionals:& &\\ -& &\\ - if &{\bf IF X$>$0.0} &\verb! IF (X.GT.0.0) THEN!\\ -& {\bf \ \ \ \ \ \ \ THEN Y:=X\$} &\verb! Y=X!\\ -& &\verb! ENDIF!\\ -& &\\ - if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb! IF (X.GT.0.0) THEN!\\ -&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X!\\ -& &\verb! ELSE!\\ -& &\verb! Y=-X!\\ -& &\verb! ENDIF!\\ -& & \\\hline - Unconditional& &\\ - Transfer of & &\\ - Control: & &\\ -& &\\ - goto&{\bf GOTO LOOP\$} &\verb! GOTO 25010!\\ -& &\\ - call&{\bf CALCV(V,X,Y,Z)\$} &\verb! CALL CALCV(V,X,Y,Z)!\\ -& &\\ - return &{\bf RETURN X\^{}2\$} &\verb! !{\it - functionname\/}\verb!=X**2!\\ -& &\verb! RETURN!\\ -& & \\\hline -Sequences \& & &\\ -Groups: & &\\ -& &\\ - sequence &{\bf $<$$<$ U:=X\^{}2;}&\verb! U=X**2!\\ -& {\bf \ \ \ \ \ \ \ \ V:=Y\^{}2$>$$>$\$} &\verb! V=Y**2!\\ -& &\\ - group &{\bf BEGIN}&\verb! U=X**2!\\ -&{\bf\ \ \ \ U:=X\^{}2;}&\verb! V=Y**2!\\ -&{\bf\ \ \ \ V:=Y\^{}2} &\\ -&{\bf END\$}&\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE control structures translatable to FORTRAN} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf RATFOR CODE} \\ \hline\hline - -Assignments: & &\\ -& & \\ - simple &{\bf V:=X\^{}2+X\$} &\verb!V=X**2+X!\\ -& & \\ - matrix &{\bf M:=MAT((U,V),(W,X))\$} &\verb!M(1,1)=U!\\ -& &\verb!M(1,2)=V!\\ -& &\verb!M(2,1)=W!\\ -& &\verb!M(2,2)=X!\\ -& & \\ - sum &{\bf S:=FOR I:=1:10} &\verb!S=0.0!\\ -&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb!DO I=1,10!\\ -& &\verb! S=S+V(I)!\\ -& & \\ - product &{\bf P:=FOR I:=2 STEP 2} &\verb!P=1!\\ -&{\bf\ \ \ \ \ \ \ \ UNTIL N} &\verb!DO I=2,N,2!\\ -&{\ \ \ \ PRODUCT I\$} &\verb! P=P*I!\\ -& & \\ -conditional & {\bf X := IF A$<$B THEN} &\verb!IF (A$0.0 DO} &\verb!WHILE(F(N)>0.0)!\\ -&{\bf \ \ \ \ N:=N+1\$} &\verb! N=N+1!\\ -& & \\ - repeat &{\bf REPEAT X:=X/2.0} &\verb!REPEAT!\\ -&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X=X/2.0!\\ -& &\verb!UNTIL(F(X)<0.0)!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to RATFOR} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf RATFOR CODE} \\ \hline\hline - Conditionals:& &\\ -& &\\ - if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!IF(X>0.0)!\\ -& &\verb! Y=X!\\ -& &\\ - if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!IF(X>0.0)!\\ -&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X!\\ -& &\verb!ELSE!\\ -& &\verb! Y=-X!\\ -& & \\\hline - Unconditional& &\\ - Transfer of & &\\ - Control: & &\\ -& &\\ - goto&{\bf GOTO LOOP\$} &\verb!GOTO 25010!\\ -& &\\ - call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALL CALCV(V,X,Y,Z)!\\ -& &\\ - return &{\bf RETURN X\^{}2\$} &\verb!RETURN(X**2)!\\ -& & \\\hline -Sequences \& & &\\ -Groups: & &\\ -& &\\ - sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!U=X**2!\\ -& &\verb!V=Y**2!\\ -& &\\ - group &{\bf BEGIN}&\verb!{!\\ -&{\bf\ \ \ \ U:=X\^{}2;}& \verb! U=X**2!\\ -&{\bf\ \ \ \ V:=Y\^{}2} & \verb! V=Y**2!\\ -&{\bf END\$}&\verb!}!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to RATFOR} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf PASCAL CODE} \\ \hline\hline -Assignments: & &\\ -& & \\ - simple &{\bf V:=X\^{}2+X\$} &\verb!V=X**2+X;!\\ -& & \\ - matrix &{\bf M:=MAT((U,V),} &\verb!BEGIN!\\ -& {\bf \ \ \ \ \ \ \ \ (W,X))\$} &\verb! M(1,1)=U;!\\ -& &\verb! M(1,2)=V;!\\ -& &\verb! M(2,1)=W;!\\ -& &\verb! M(2,2)=X;!\\ -& &\verb!END;!\\ -& & \\ - sum &{\bf S:=FOR I:=1:10} &\verb!BEGIN!\\ -&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb! S=0.0!\\ -& &\verb! FOR I:=1 TO 10 DO!\\ -& &\verb! S:=S+V(I)!\\ -& &\verb!END;!\\ -& & \\ - product &{\bf P:=FOR I:=2:N} &\verb!BEGIN!\\ -&{\bf \ \ \ \ PRODUCT I\$} &\verb! P:=1;!\\ -& &\verb! FOR I:=2 TO N DO!\\ -& &\verb! P:=P*I!\\ -& &\verb!END;!\\ -& & \\ -conditional & {\bf X := IF A$<$B THEN} &\verb!IF (A$0.0 DO} &\verb!WHILE (F(N)>0.0)!\\ -&{\bf \ \ \ \ N:=N+1\$} &\verb! N:=N+1.0;!\\ -& & \\ - repeat &{\bf REPEAT X:=X/2.0} &\verb!REPEAT!\\ -&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X:=X/2.0!\\ -& &\verb!UNTIL F(X)<0.0;!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to PASCAL} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf PASCAL CODE} \\ \hline\hline - Conditionals:& &\\ -& &\\ - if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!IF X>0.0 THEN!\\ -& &\verb! Y:=X;!\\ -& &\\ - if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!IF X>0.0 THEN!\\ -&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y:=X;!\\ -& &\verb!ELSE!\\ -& &\verb! Y:=-X;!\\ -& & \\\hline - Unconditional& &\\ - Transfer of & &\\ - Control: & &\\ -& &\\ - goto&{\bf GOTO LOOP\$} &\verb!GOTO 25010;!\\ -& &\\ - call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALCV(V,X,Y,Z);!\\ -& &\\ - return &{\bf RETURN X\^{}2\$} &{\it functionname\/}\verb!=X**2;!\\ -& &\verb!GOTO 99999{RETURN}!\\ -& &\verb!99999;!\\ -& & \\\hline -Sequences \& & &\\ -Groups: & &\\ -& &\\ - sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!BEGIN!\\ -&&\verb! U:=X**2;!\\ -&&\verb! V:=Y**2!\\ -&&\verb!END;!\\ -& &\\ - group &{\bf BEGIN}&\verb!BEGIN!\\ -&{\bf\ \ \ \ U:=X\^{}2;}&\verb! U:=X**2;!\\ -&{\bf\ \ \ \ V:=Y\^{}2} &\verb! V:=Y**2!\\ -&{\bf END\$}&\verb!END!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to PASCAL} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} - & \multicolumn{1}{c||}{\bf C CODE} \\ \hline\hline -Assignments: & &\\ -& & \\ - simple &{\bf V:=X\^{}2+X\$} &\verb!V=power(X,2)+X;!\\ -& & \\ - matrix &{\bf M:=MAT((U,V),(W,X))\$} &\verb!M[1][1]=U;!\\ -& &\verb!M[1][2]=V;!\\ -& &\verb!M[2][1]=W;!\\ -& &\verb!M[2][2]=X;!\\ -& & \\ - sum &{\bf S:=FOR I:=1:10} &\verb!S=0.0;!\\ -&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb!for(I=1;I<=10;++I)!\\ -& &\verb! S+=V[I];!\\ -& & \\ - product &{\bf P:=FOR I:=2 STEP 2} &\verb!P=1;!\\ -&{\bf\ \ \ \ \ \ \ \ UNTIL N} &\verb!for(I=2;I<=N;++I)!\\ -&{\ \ \ \ PRODUCT I\$} &\verb! P*=I;!\\ -& & \\ -conditional & {\bf X := IF A$<$B THEN} &\verb!if (A$0.0 DO} &\verb!while(F(N)>0.0)!\\ -&{\bf \ \ \ \ N:=N+1\$} &\verb! N+=1;!\\ -& & \\ - repeat &{\bf REPEAT X:=X/2.0} &\verb!do!\\ -&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X/=2.0;!\\ -& &\verb!while(F(X)>=0.0);!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to C} -\end{table} - -\begin{table} -\begin{tabular}{||l|l|l||}\hline\hline -\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} & - \multicolumn{1}{c||}{\bf C CODE} \\ \hline\hline - Conditionals:& &\\ -& &\\ - if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!if(X>0.0)!\\ -& &\verb! Y=X;!\\ -& &\\ - if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!if(X>0.0)!\\ -&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X;!\\ -& &\verb!else!\\ -& &\verb! Y=-X;!\\ -& & \\\hline - Unconditional& &\\ - Transfer of & &\\ - Control: & &\\ -& &\\ - goto&{\bf GOTO LOOP\$} &\verb!goto LOOP;!\\ -& &\\ - call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALCV(V,X,Y,Z);!\\ -& &\\ - return &{\bf RETURN X\^{}2\$} &\verb!return(power(X,2) );!\\ -& & \\\hline -Sequences \& & &\\ -Groups: & &\\ -& &\\ - sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!U=power(X,2);!\\ -& &\verb!V=power(Y,2);!\\ -& &\\ - group &{\bf BEGIN}&\verb!{!\\ -&{\bf\ \ \ \ U:=X\^{}2;}& \verb! U=power(x,2);!\\ -&{\bf\ \ \ \ V:=Y\^{}2} & \verb! V=power(Y,2);!\\ -&{\bf END\$}&\verb!}!\\ -& & \\\hline\hline -\end{tabular} -\caption{REDUCE forms translatable to C} -\end{table} - -\subsection{Formal Definition} -The remainder of this section contains a formal definition of all -REDUCE expressions, statements, and prefix forms that can be translated by -GENTRAN into FORTRAN, RATFOR, PASCAL and C code. - -\begin{describe}{Preliminary Definitions} -An {\it id\/} is an identifier. Certain {\it id\/}'s are reserved words -and may not be used as array names or subprogram names. The -complete list appears in the {\it Reserved Words\/} section. - -A {\it string\/} consists of any number of characters (excluding double -quotes) which are enclosed in double quotes. -\end{describe} - -\begin{describe}{Reserved Words}\index{reserved words} -The following reserved words may not be used as array names or -subprogram names\footnote{Note that names of other built-in REDUCE functions -{\it can\/} be translated, but remember that they will be translated -{\it literally\/} unless {\bf EVAL}'d first. For example: -{\bf GENTRAN~DERIV~:=~DF(2*X\^{}2-X-1,~X)\$} -generates {\tt DERIV=DF(2*X**2-X-1,X)} -whereas -{\bf GENTRAN~DERIV~:=:~DF(2*X\^{}2-X-1,~X)\$} -generates {\tt DERIV=4*X-1} }: - -{\bf AND, BLOCK, COND, DIFFERENCE, EQUAL, EXPT, FOR, GEQ, -GO, GREATERP, LEQ, LESSP, MAT, MINUS, NEQ, NOT, OR, -PLUS, PROCEDURE, PROGN, QUOTIENT, RECIP, REPEAT, -RETURN, SETQ, TIMES, WHILE, WRITE} -\end{describe} - -\subsubsection{Translatable REDUCE Expressions and Statements} -\begin{describe}{Expressions} -\begin{tabular}{lll} -\multicolumn{3}{l}{Arithmetic Expressions:} \\ -& & \\ -exp & ::= & {\it number} $\mid$ var $\mid$ funcall $\mid$ - exp $\mid$ -/ exp $\mid$ exp + exp $\mid$ \\ - & & exp - exp $\mid$ exp * exp $\mid$ exp / exp $\mid$ exp ** exp - $\mid$ \\ - & & exp \^{} exp $\mid$ ( exp )\\\\ -& & \\ -var & ::= & {\it id} $\mid$ {\it id} ( exp$_1$, exp$_2$, \dots\ , exp$_n$ ) - $n > 0$ \\ -& & \\ -funcall & ::= & {\it id} ( arg$_1$, arg$_2$, \dots\ , arg$_n$ ) $n \geq 0$ \\ -& & \\ -arg & ::= & exp $\mid$ logexp $\mid$ {\it string} \\ -& &\\ -\multicolumn{3}{l}{Logical Expressions:}\\ -& & \\ -logexp & ::= & {\it T} $\mid$ {\it NIL} $\mid$ var $\mid$ funcall $\mid$ - exp $>$ exp $\mid$ exp $>$= exp $\mid$\\ - & & exp = exp $\mid$ exp {\it NEQ} exp $\mid$ exp $<$ exp $\mid$ \\ - & & exp $<$= exp $\mid$ {\it NOT\/} logexp $\mid$ logexp {\it AND\/} - logexp $\mid$ \\ - & & logexp {\it OR\/} logexp $\mid$ ( logexp )\\ -\end{tabular} -\end{describe} - -\begin{describe}{Operator Precedence} -The following is a list of REDUCE arithmetic and logical -operators in order of decreasing precedence: -\begin{center} -** (or \^{}) / * --- + $<$ $<$= $>$ $>$= NEQ = NOT AND OR -\end{center} - -When unparenthesised expressions are translated which contain -operators whose precedence in REDUCE differs from that in the -target language, parentheses are automatically generated. Thus -the meaning of the original expression is preserved\footnote{ -For example in REDUCE, {\bf NOT~A~=~B} and {\bf NOT~(A~=~B)} -are equivalent, whereas in C, {\bf !~A~==~B} and {\bf (!A)~==~B} -are equivalent. Therefore, {\bf NOT~A~=~B} -is translated into C code which forces the REDUCE precedence rules: -{\bf !(A~==~B)} -}. -\end{describe} -\begin{describe}{Statements} -\begin{tabular}{lll} -stmt & ::= & assign $\mid$ break $\mid$ cond $\mid$ while $\mid$ - repeat $\mid$ for $\mid$ goto $\mid$ label $\mid$ \\ -& & call $\mid$ return $\mid$ stop $\mid$ stmtgp \\ -\end{tabular} - -Assignment Statements: - -\begin{tabular}{llll} -assign & ::= & \multicolumn{2}{l}{var := assign' $\mid$ matassign $\mid$ - cond}\\ -& & & \\ -assign' & ::= & \multicolumn{2}{l}{exp $\mid$ logexp}\\ -& & & \\ -matassign & ::= & {\it id} := {\it MAT\/}(&(exp$_{11}$, \dots\ , exp$_{1m}$),\\ - & & &(exp$_{21}$, \dots\ , exp$_{2m}$ ),\\ - & & & \ \ \ \ \ \ :\\ - & & & \ \ \ \ \ \ :\\ - & & &( exp$_{n1}$, \dots\ , exp$_{nm}$ ) ) $n,m > 0$ \\ -\end{tabular} - -Break Statement: - -break ::= {\it BREAK()} - -Conditional Statements: - -\begin{tabular}{lll} -cond & ::= & {\it IF\/} logexp {\it THEN\/} stmt\\ -& & {\it IF\/} logexp {\it THEN\/} stmt {\it ELSE\/} stmt\\ -\end{tabular} - -Loops: -\index{FOR loop} \index{WHILE loop} \index{REPEAT loop} - -\begin{tabular}{lll} -while & ::= & {\it WHILE\/} logexp {\it DO\/} stmt\\ -& &\\ -repeat & ::= & {\it REPEAT\/} stmt {\it UNTIL\/} logexp\\ -& &\\ -for & ::= & {\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp -{\it DO\/} stmt $\mid$\\ -& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it DO\/} stmt $\mid$\\ -& &{\it FOR\/} var := exp : exp {\it DO\/} stmt $\mid$\\ -& &var := for' $\mid$ \\ -& &\\ -for' & ::= & var := for' $\mid$\\ -& &{\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp {\it SUM\/} exp - $\mid$\\ -& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it SUM\/} exp $\mid$\\ -& &{\it FOR\/} var := exp : exp {\it SUM\/} exp $\mid$\\ -& &{\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp\\ -& & \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ {\it PRODUCT\/} exp $\mid$ \\ -& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it PRODUCT\/} exp $\mid$\\ -& &{\it FOR\/} var := exp : exp {\it PRODUCT\/} exp\\ -\end{tabular} - -Goto Statement: - -\begin{tabular}{lll} -goto & ::= & {\it GOTO\/} label $\mid$ {\it GO TO\/} label\\ -label & ::= & {\it id\/} :\\ -\end{tabular} - -Subprogram Calls \& Returns \footnote{ Note that return statements can -only be translated from inside of procedure definitions. -\index{LITERAL command} The LITERAL function must be used to generate -a return statement from anywhere else.}: - -\begin{tabular}{lll} -call & ::= & {\it id\/} ( arg$_1$, arg$_2$, \dots\ , arg$_n$ ) $n \geq 0$\\ -& &\\ -return & ::= & {\it RETURN\/} $\mid$ {\it RETURN\/} arg\\ -\end{tabular} - -Stop \& Exit Statements \footnote{ -In certain cases it may be convenient to generate a FORTRAN -STOP statement or a C EXIT statement. Since there is no -semantically equivalent REDUCE statement, STOP() can be used -and will be translated appropriately.}: - -stop ::= {\it STOP\/}() - -Statement Groups \footnote{ -Note that REDUCE BEGIN\dots\ END statement groups are translated -into RATFOR or C \{\dots\ \} statement groups, whereas -REDUCE $<$$<$\dots\ $>$$>$ statement groups are translated into RATFOR or -C statement {\it sequences}. When the target language is FORTRAN, both -types of REDUCE statement groups are translated into statement -sequences.}: - -\begin{tabular}{lll} -stmtgp & ::= & $<$$<$ stmt$_1$ ; stmt$_2$ ; \dots\ ; stmt$_n$ $>$$>$ - $\mid$\\ -& &{\it BEGIN\/} stmt$_1$ ; stmt$_2$ ; \dots\ ; stmt$_n$ {\it END\/} $ n > - 0$\\ -\end{tabular} -\end{describe} -\begin{describe}{Subprogram Definitions} -\begin{tabular}{lll} -defn & ::= & {\it PROCEDURE id\/} ({\it id$_1$, id$_2$, \dots\ , id$_n$\/}) ; - stmt $\mid$\\ -& & {\it PROCEDURE id\/} ({\it id$_1$, id$_2$, \dots\ , id$_n$\/}) ; - exp\ \ \ \ \ \ $n \geq 0$ \\ -\end{tabular} -\end{describe} - -\subsubsection{Translatable REDUCE Prefix Forms} -\begin{describe}{Expressions} - -Arithmetic Expressions: - -\begin{tabular}{lll} -exp & ::= & {\it number\/} $\mid$ funcall $\mid$ var $\mid$ -({\it DIFFERENCE\/} exp exp) $\mid$\\ -& &({\it EXPT\/} exp exp) $\mid$ ({\it MINUS\/} exp) $\mid$ ({\it PLUS\/} - exp exp') $\mid$\\ -& & ({\it QUOTIENT\/} exp exp) $\mid$ ({\it RECIP\/} exp) $\mid$\\ -& & ({\it TIMES\/} exp exp exp') $\mid$ ({\it !*SQ\/} sqform)\\ -\end{tabular} - -where sqform is a standard quotient form equivalent to any acceptable prefix -form. - -exp' ::= exp$_1$ exp$_2$ \dots\ exp$_n$ $n \geq 0$ - -Logical Expressions: - -\begin{tabular}{lll} -logexp & ::= & {\it NIL\/} $\mid$ {\it T\/} $\mid$ funcall $\mid$ var -$\mid$\\ -& & ({\it AND\/} logexp logexp logexp') $\mid$ ({\it EQUAL\/} exp exp) -$\mid$\\ -& & ({\it GEQ\/} exp exp) $\mid$ ({\it GREATERP\/} exp exp) $\mid$ \\ -& & ({\it LEQ\/} exp exp) $\mid$ ({\it LESSP\/} exp exp) $\mid$ \\ -& & ({\it NEQ\/} exp exp) $\mid$ ({\it NOT\/} logexp) $\mid$ \\ -& & ({\it OR\/} logexp logexp logexp')\\ -& &\\ -logexp' & ::= & logexp$_1$ logexp$_2$ \dots\ logexp$_n$ $n \geq 0$\\ -\end{tabular} -\end{describe} - -\begin{describe}{Statements} -\begin{tabular}{lll} -stmt & ::= & assign $\mid$ break $\mid$ call $\mid$ cond $\mid$ -for $\mid$ goto $\mid$\\ -& & label $\mid$ read $\mid$ repeat $\mid$ return $\mid$ stmtgp -$\mid$\\ -& & stop $\mid$ while $\mid$ write \\ -& &\\ -stmt' & ::= & stmt$_1$ stmt$_2$ \dots\ stmt$_n$ $n \geq 0$\\ -\end{tabular} - -Assignment Statements: - -assign ::= ({\it SETQ\/} var exp) $\mid$ ({\it SETQ\/} var logexp) $\mid$ - ({\it SETQ\/} id ({\it MAT\/} list list')) - -Conditional Statements: - -\begin{tabular}{lll} -cond & ::= & ({\it COND\/} (logexp stmt) cond1) \\ -& & \\ -cond1 & ::= & (logexp stmt$_1$) \dots\ (logexp stmt$_n$) $n \geq 0$\\ -\end{tabular} - -Loops: - -\begin{tabular}{lll} -for & ::= & ({\it FOR\/} var (exp exp exp) {\it DO\/} stmt) $\mid$\\ -& & ({\it SETQ\/} var ({\it FOR\/} var (exp exp exp) {\it SUM\/} exp) $\mid$\\ -& & ({\it SETQ\/} var ({\it FOR\/} var (exp exp exp) \\ -& & \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ {\it PRODUCT\/} exp)\\ -& &\\ -repeat & ::= & ({\it REPEAT\/} stmt logexp)\\ -& &\\ -while & ::= & ({\it WHILE\/} logexp stmt) -\end{tabular} - -Go To Statements: - -\begin{tabular}{lll} -break & ::= & ({\it BREAK\/})\\ -& & \\ -goto & ::= & ({\it GO\/} label)\\ -& & \\ -label & ::= & {\it id}\\ -\end{tabular} - -Subprogram Calls \& Returns: - -\begin{tabular}{lll} -call & ::= & ({\it id\/} arg')\\ -& &\\ -return & ::= & ({\it RETURN\/}) $\mid$ ({\it RETURN\/} arg)\\ -\end{tabular} - -Stop \& Exit Statements: - -stop ::= ({\it STOP\/}) - -Statement Groups: - -stmtgp ::= ({\it PROGN\/} stmt stmt') $\mid$ ({\it BLOCK\/} (id') stmt') - -I/O Statements: - -\begin{tabular}{lll} -read & ::= & ({\it SETQ\/} var ({\it READ\/}))\\ -& &\\ -write & ::= & ({\it WRITE\/} arg arg')\\ -\end{tabular} - -Subprogram Definitions: - -defn ::= ({\it PROCEDURE id NIL EXPR\/} (id') stmt) - -\end{describe} - -\begin{describe}{Miscellaneous} -\begin{tabular}{lll} -funcall & ::= & ({\it id\/} arg')\\ -& &\\ -var & ::= & {\it id\/} $\mid$ ({\it id\/} exp exp')\\ -& &\\ -arg & ::= & {\it string\/} $\mid$ exp $\mid$ logexp\\ -& &\\ -arg' & ::= & arg$_1$ arg$_2$ \dots\ arg$_n$ $n \geq 0$ \\ -& &\\ -list & ::= & (exp exp')\\ -& &\\ -list' & ::= & list$_1$ list$_2$ \dots\ list$_n$ $n \geq 0$ \\ -& &\\ -id' & ::= & {\it id$_1$ id$_2$} \dots\ {\it id$_n$} $n \geq 0$ \\ -\end{tabular} -\end{describe} - -\section{List of Commands, Switches, \& Variables} -\label{appb} -\begin{describe}{COMMANDS} -\index{GENTRAN command} -{\bf GENTRAN} {\it stmt\/} [{\bf OUT}{\it f1,f2,\dots\ ,fn\/}]{\it ;} - -\index{GENTRANIN command} -{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm\/} [{\bf OUT}{\it f1,f2,\dots\ -,fn\/}]{\it ;} - -\index{GENTRANOUT command} -{\bf GENTRANOUT} {\it f1,f2,\dots\ ,fn;} - -\index{GENTRANSHUT command} -{\bf GENTRANSHUT} {\it f1,f2,\dots\ ,fn;} - -\index{GENTRANPUSH command} -{\bf GENTRANPUSH} {\it f1,f2,\dots\ ,fn;} - -\index{GENTRANPOP command} -{\bf GENTRANPOP} {\it f1,f2,\dots\ ,fn;} -\end{describe} - -\begin{describe}{SPECIAL FUNCTIONS \& OPERATORS} - -\ttindex{EVAL} -{\bf EVAL} {\it exp} - -\index{::=} -{\it var} {\bf ::=} {\it exp;} - -\index{:=:} -{\it var} {\bf :=:} {\it exp;} - -\index{::=:} -{\it var} {\bf ::=:} {\it exp;} - -\ttindex{LSETQ} -{\it var} {\bf LSETQ} {\it exp;} - -\ttindex{RSETQ} -{\it var} {\bf RSETQ} {\it exp;} - -\ttindex{LRSETQ} -{\it var} {\bf LRSETQ} {\it exp;} - -\index{DECLARE function} -{\bf DECLARE} {\it v1,v2,\dots\ ,vn\/}{\bf :} {\it type;} - -\begin{tabular}{ll} -{\bf DECLARE}\\ -{\bf $<$$<$}\\ -&{\it v11,v12,\dots\ ,v1n} {\bf :} {\it type1\/}{\bf ;}\\ -&{\it v12,v22,\dots\ ,v2n} {\bf :} {\it type2\/}{\bf ;}\\ -& \ \ \ :\\ -& \ \ \ :\\ -&{\it vm1,vm2,\dots\ ,vmn} {\bf :} {\it typen\/}{\bf ;}\\ -{\bf $>$$>$}{\it ;} -\end{tabular} - -\ttindex{LITERAL} -{\bf LITERAL} {\it arg1,arg2,\dots\ ,argn;} -\end{describe} - -\begin{describe}{MODE SWITCHES} -{\bf PERIOD} \index{PERIOD switch} - -{\bf GENTRANSEG} \index{GENTRANSEG switch} - -{\bf GENDECS} \index{GENDECS switch} - -{\bf DOUBLE} \index{DOUBLE switch} - -{\bf MAKECALLS} \index{MAKECALLS switch} - -{\bf KEEPDECS} \index{KEEPDECS switch} - -{\bf GETDECS} \index{GETDECS switch} - -\end{describe} - -\begin{describe}{VARIABLES} -{\bf GENTRANLANG!*} \ttindex{GENTRANLANG!*} - -{\bf MAXEXPPRINTLEN!*} \ttindex{MAXEXPPRINTLEN!*} - -{\bf TEMPVARNAME!*} \ttindex{TEMPVARNAME!*} - -{\bf TEMPVARNUM!*} \ttindex{TEMPVARNUM!*} - -{\bf TEMPVARTYPE!*} \ttindex{TEMPVARTYPE!*} - -{\bf GENSTMTNUM!*} \ttindex{GENSTMTNUM!*} - -{\bf GENSTMTINCR!*} \ttindex{GENSTMTINCR!*} - -{\bf TABLEN!*} \ttindex{TABLEN!*} - -{\bf FORTLINELEN!*} \ttindex{FORTLINELEN!*} - -{\bf RATLINELEN!*} \ttindex{RATLINELEN!*} - -{\bf CLINELEN!*} \ttindex{CLINELEN!*} - -{\bf PASCLINELEN!*} \ttindex{PASCLINELEN!*} - -{\bf MINFORTLINELEN!*} \ttindex{MINFORTLINELEN!*} - -{\bf MINRATLINELEN!*} \ttindex{MINRATLINELEN!*} - -{\bf MINCLINELEN!*} \ttindex{MINCLINELEN!*} - -{\bf MINPASCLINELEN!*} \ttindex{MINPASCLINELEN!*} - -{\bf DEFTYPE!*} \ttindex{DEFTYPE!*} -\end{describe} - -\begin{describe}{TEMPORARY VARIABLE GENERATION, MARKING \& UNMARKING} -{\bf TEMPVAR} {\it type;} \ttindex{TEMPVAR} - -{\bf MARKVAR} {\it var;} \ttindex{MARKVAR} - -{\bf UNMARKVAR} {\it var;} \ttindex{UNMARKVAR} -\end{describe} - -\begin{describe}{EXPLICIT GENERATION OF TYPE DECLARATIONS} -{\bf GENDECS} {\it subprogname;} \ttindex{GENDECS switch} -\end{describe} - -\begin{describe}{SYMBOLIC MODE FUNCTIONS} -{\bf SYM!-GENTRAN} {\it form;} \index{SYM"!-GENTRAN command} - -{\bf SYM!-GENTRANIN} {\it list-of-fnames;} \index{SYM"!-GENTRANIN command} - -{\bf SYM!-GENTRANOUT} {\it list-of-fnames;} \index{SYM"!-GENTRANOUT command} - -{\bf SYM!-GENTRANSHUT} {\it list-of-fnames;} \index{SYM"!-GENTRANSHUT command} - -{\bf SYM!-GENTRANPUSH} {\it list-of-fnames;} \index{SYM"!-GENTRANPUSH command} - -{\bf SYM!-GENTRANPOP} {\it list-of-fnames;} \index{SYM"!-GENTRANPOP command} -\end{describe} - -\begin{describe}{SYMBOLIC MODE SPECIAL FORMS} -\begin{tabular}{ll} -\ttindex{DECLARE} -{\bf (DECLARE} & {\bf (}{\it type1 v11 v12 \dots\ v1n\/}{\bf )}\\ -& {\bf (}{\it type2 v21 v22 \dots\ v2n\/}{\bf )}\\ -& \ \ \ :\\ -& \ \ \ :\\ -& {\bf (}{\it typen vn1 vn2 \dots\ vnn\/}{\bf ))}\\ -\end{tabular} - -{\bf (LITERAL} {\it arg1 arg2 \dots\ argn\/}{\bf )} \ttindex{LITERAL} - -{\bf (EVAL} {\it exp\/}{\bf )} \ttindex{EVAL} - -{\bf (LSETQ} {\it var exp\/}{\bf )} \ttindex{LSETQ} - -{\bf (RSETQ} {\it var exp\/}{\bf )} \ttindex{RSETQ} - -{\bf (LRSETQ} {\it var exp\/}{\bf )} \ttindex{LRSETQ} -\end{describe} - -\section{The Programs {\tt M1.F} and {\tt M2.F}.} -\label{appc} - -This section contains the two files generated in chapter 6. -Contents of file m1.f: -\begin{framedverbatim} - M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE - . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 - . +J30Y+J10Y - M(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*DCOS(DBLE( - . Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+J30Y - M(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30) - M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ - . J30Y - M(2,3)=0.0D0 - M(3,3)=9.0D0*P**2*M30+J30X - MIV(1,1)=(-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y)+9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2* - . M30*J30X)-(DSIN(DBLE(Q3))**2*J30Y*J30X)+DSIN(DBLE(Q3)) - . **2*J30Z*J30X+81.0D0*P**4*M30**2+9.0D0*P**2*M30*J30Y+ - . 9.0D0*P**2*M30*J30X+J30Y*J30X)/(729.0D0*DSIN(DBLE(Q3)) - . **4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE(Q3 - . ))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0*DSIN( - . DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ - . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* - . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 - . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** - . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* - . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN - . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* - . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( - . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y - . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** - . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) - . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 - . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* - . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P - . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* - . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN - . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 - . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** - . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* - . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* - . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( - . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* - . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( - . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 - . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) - . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* - . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ - . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* - . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* - . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* - . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) - MIV(1,2)=(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Y-(9.0D0*DSIN(DBLE(Q3)) - . **2*P**2*M30*J30Z)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30* - . J30X+DSIN(DBLE(Q3))**2*J30Y*J30X-(DSIN(DBLE(Q3))**2* - . J30Z*J30X)-(81.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4* - . M30**2)-(9.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30* - . J30X)-(81.0D0*P**4*M30**2)-(9.0D0*P**2*M30*J30Y)-( - . 9.0D0*P**2*M30*J30X)-(J30Y*J30X))/(729.0D0*DSIN(DBLE( - . Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE - . (Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0* - . DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ - . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* - . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 - . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** - . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* - . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN - . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* - . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( - . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y - . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** - . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) - . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 - . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* - . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P - . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* - . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN - . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 - . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** - . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* - . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* - . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( - . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* - . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( - . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 - . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) - . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* - . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ - . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* - . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* - . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* - . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) - MIV(1,3)=(-(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P** - . 4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 - . *M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 - . *M30*J30Z+81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**4* - . M30**2+9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30* - . J30Y)/(729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P** - . 6*M30**3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P - . **4*M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2 - . ))**2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4* - . Y*M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2* - . J30Y)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30)+9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-(9.0D0*DSIN(DBLE - . (Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN(DBLE(Q3))**4*P** - . 2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y - . *J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3 - . ))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3))**4*J30Y**2*J30X - . )+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE( - . Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DSIN( - . DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y)-( - . 729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-(81.0D0*DSIN( - . DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN(DBLE(Q3))** - . 2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3))**2*P**4*M30 - . **2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J10Y)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J30X)-(9.0D0*DSIN - . (DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30Y - . *J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30X*J30)+ - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2-(9.0D0*DSIN( - . DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0*DSIN(DBLE(Q3)) - . **2*P**2*M30*J30Z*J10Y+9.0D0*DSIN(DBLE(Q3))**2*P**2* - . M30*J30Z*J30X-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y* - . J30X)-(DSIN(DBLE(Q3))**2*P**2*J30Y*M10*J30X)+DSIN(DBLE - . (Q3))**2*P**2*J30Z*M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y* - . J30X*J30)+DSIN(DBLE(Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3 - . ))**2*J30Y*J10Y*J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X - . -(729.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30 - . **3)-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* - . J30X+J30Y*J10Y*J30X) - MIV(2,2)=(-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2* - . P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+9.0D0*DSIN( - . DBLE(Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*M30*J30X)-(DSIN(DBLE(Q3))**2*Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Z*J30X+162.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2 - . ))*P**4*M30**2+18.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P - . **2*M30*J30X+162.0D0*P**4*M30**2+9.0D0*P**4*M30*M10+ - . 9.0D0*P**2*M30*J30Y+9.0D0*P**2*M30*J10Y+18.0D0*P**2* - . M30*J30X+P**2*M10*J30X+J30Y*J30X+J10Y*J30X)/(729.0D0* - . DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0 - . *DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y- - . (81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30** - . 2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-( - . 81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2* - . Y*M30*J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y - . **2)+9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0 - . *DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3)) - . **4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30 - . )-(DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4* - . J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2 - . ))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE - . (Q2))**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2* - . P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10 - . )-(81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* - . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P - . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* - . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN - . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 - . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** - . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* - . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* - . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( - . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* - . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( - . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 - . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) - . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* - . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ - . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* - . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* - . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* - . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) - MIV(2,3)=(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**4* - . M30**2+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 - . *J30Y-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 - . *J30Z)-(81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*DCOS(DBLE - . (Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3 - . ))*DSIN(DBLE(Q2))*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))* - . DSIN(DBLE(Q2))*P**2*M30*J30Y))/(729.0D0*DSIN(DBLE(Q3)) - . **4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE(Q3) - . )**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0*DSIN( - . DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ - . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* - . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 - . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** - . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* - . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN - . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* - . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( - . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y - . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** - . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) - . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 - . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* - . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P - . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* - . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN - . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 - . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** - . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* - . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* - . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( - . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* - . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( - . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 - . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) - . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* - . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ - . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* - . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* - . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* - . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) - MIV(3,3)=(9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30-(9.0D0 - . *DSIN(DBLE(Q3))**4*P**2*M30*J30Y)+DSIN(DBLE(Q3))**4*Y* - . J30Y*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2)+DSIN(DBLE(Q3))**4*J30Y*J30Z-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **4*M30*M10)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+ - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J10Y)-(DSIN(DBLE(Q3))**2*P**2*J30Y* - . M10)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10-(DSIN(DBLE(Q3))** - . 2*Y*J30Y*J30)+DSIN(DBLE(Q3))**2*J30Y**2-(DSIN(DBLE(Q3) - . )**2*J30Y*J10Y)+DSIN(DBLE(Q3))**2*J30Z*J10Y-(81.0D0* - . DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4*M30**2)+ - . 81.0D0*P**4*M30**2+9.0D0*P**4*M30*M10+9.0D0*P**2*M30* - . J30Y+9.0D0*P**2*M30*J10Y+P**2*J30Y*M10+J30Y*J10Y)/( - . 729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30** - . 3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30 - . **2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P - . **4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30** - . 2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+ - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE - . (Q3))**4*P**2*Y*M30*J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4* - . P**2*M30*J30Y**2)+9.0D0*DSIN(DBLE(Q3))**4*P**2*M30* - . J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30X) - . +DSIN(DBLE(Q3))**4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3))**4* - . Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN - . (DBLE(Q3))**4*J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))** - . 2*DSIN(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3) - . )**2*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y)-(729.0D0*DSIN - . (DBLE(Q3))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P - . **6*M30**2*M10)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30** - . 2*J30)+81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J10Y)-(81.0D0* - . DSIN(DBLE(Q3))**2*P**4*M30**2*J30X)-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P** - . 4*M30*J30Z*M10-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10* - . J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-( - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30X*J30)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3 - . ))**2*P**2*M30*J30Y*J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2 - . *M30*J30Z*J10Y+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z* - . J30X-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-( - . DSIN(DBLE(Q3))**2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))** - . 2*P**2*J30Z*M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X* - . J30)+DSIN(DBLE(Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2 - . *J30Y*J10Y*J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-( - . 729.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30** - . 3)-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0 - . *P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2 - . *M30*J30Y*J30X+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* - . J30X+J30Y*J10Y*J30X) - DO 25005 J=1,3 - DO 25006 K=J+1,3 - M(K,J)=M(J,K) - MIV(K,J)=MIV(J,K) -25006 CONTINUE -25005 CONTINUE -\end{framedverbatim} - -\newpage - -Contents of file m2.f: -\begin{framedverbatim} - M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE - . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 - . +J30Y+J10Y(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-( - . DSIN(DBLE(Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0* - . DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+ - . J30Y(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2* - . M30) - M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( - . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ - . J30Y - M(2,3)=0.0D0 - M(3,3)=9.0D0*P**2*M30+J30X - T1=-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-(9.0D0*DSIN( - . DBLE(Q3))**2*P**2*M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**2*P - . **2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30X)-( - . DSIN(DBLE(Q3))**2*J30Y*J30X)+DSIN(DBLE(Q3))**2*J30Z* - . J30X+81.0D0*P**4*M30**2+9.0D0*P**2*M30*J30Y+9.0D0*P**2 - . *M30*J30X+J30Y*J30X - T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - ; M30*J30Y*J30X - MIV(1,1)=T1/(T0+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* - . J30X+J30Y*J10Y*J30X) - T0=81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2+9.0D0*DSIN(DBLE - . (Q3))**2*P**2*M30*J30Y-(9.0D0*DSIN(DBLE(Q3))**2*P**2* - . M30*J30Z)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30X+DSIN( - . DBLE(Q3))**2*J30Y*J30X-(DSIN(DBLE(Q3))**2*J30Z*J30X)-( - . 81.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-( - . 9.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30*J30X)-( - . 81.0D0*P**4*M30**2)-(9.0D0*P**2*M30*J30Y) - T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X - MIV(1,2)=(T0-(9.0D0*P**2*M30*J30X)-(J30Y*J30X))/(T1+ - . 9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y* - . J30X) - T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X - MIV(1,3)=(-(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P** - . 4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 - . *M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 - . *M30*J30Z+81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**4* - . M30**2+9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30* - . J30Y)/(T0+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+ - . J30Y*J10Y*J30X) - T0=-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-(9.0D0* - . DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+9.0D0*DSIN(DBLE(Q3)) - . **2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30* - . J30X)-(DSIN(DBLE(Q3))**2*Y*J30X*J30)+DSIN(DBLE(Q3))**2 - . *J30Z*J30X+162.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4* - . M30**2+18.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30* - . J30X+162.0D0*P**4*M30**2 - T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X - MIV(2,2)=(T0+9.0D0*P**4*M30*M10+9.0D0*P**2*M30*J30Y+ - . 9.0D0*P**2*M30*J10Y+18.0D0*P**2*M30*J30X+P**2*M10*J30X - . +J30Y*J30X+J10Y*J30X)/(T1+9.0D0*P**2*M30*J10Y*J30X+P** - . 2*J30Y*M10*J30X+J30Y*J10Y*J30X) - T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X - MIV(2,3)=(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**4* - . M30**2+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 - . *J30Y-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 - . *J30Z)-(81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*DCOS(DBLE - . (Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3 - . ))*DSIN(DBLE(Q2))*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))* - . DSIN(DBLE(Q2))*P**2*M30*J30Y))/(T0+9.0D0*P**2*M30*J10Y - . *J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) - T0=9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30-(9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y)+DSIN(DBLE(Q3))**4*Y*J30Y* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30)-(DSIN(DBLE(Q3))**4* - . J30Y**2)+DSIN(DBLE(Q3))**4*J30Y*J30Z-(81.0D0*DSIN(DBLE - . (Q3))**2*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30*M10)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+ - . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z - T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y)-(DSIN( - . DBLE(Q3))**2*P**2*J30Y*M10)+DSIN(DBLE(Q3))**2*P**2* - . J30Z*M10-(DSIN(DBLE(Q3))**2*Y*J30Y*J30)+DSIN(DBLE(Q3)) - . **2*J30Y**2-(DSIN(DBLE(Q3))**2*J30Y*J10Y)+DSIN(DBLE(Q3 - . ))**2*J30Z*J10Y-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2 - . ))**2*P**4*M30**2)+81.0D0*P**4*M30**2+9.0D0*P**4*M30* - . M10+9.0D0*P**2*M30*J30Y - T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 - . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** - . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* - . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) - . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* - . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) - T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( - . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( - . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) - . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* - . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) - . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( - . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** - . 3) - T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* - . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( - . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN - . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) - . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* - . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* - . J30X) - T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 - . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( - . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P - . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* - . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 - . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* - . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y - T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 - . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) - . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* - . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE - . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* - . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( - . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) - T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* - . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* - . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ - . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* - . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* - . M30*J30Y*J30X - MIV(3,3)=(T0+9.0D0*P**2*M30*J10Y+P**2*J30Y*M10+J30Y* - . J10Y)/(T1+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+ - . J30Y*J10Y*J30X) - DO 25007 J=1,3 - DO 25008 K=J+1,3 - M(K,J)=M(J,K) - MIV(K,J)=MIV(J,K) -25008 CONTINUE -25007 CONTINUE -\end{framedverbatim} -\bibliography{gentran} -\bibliographystyle{plain} -\end{document} +\documentstyle[11pt,reduce]{article} +\title{GENTRAN User's Manual \\ REDUCE Version} +\date{} +\author{Barbara L. Gates \\ RAND \\ +Santa Monica CA 90407-2138 USA \\[0.05in] +{\em Updated for {\REDUCE} 3.4 by} \\[0.05in] +Michael C. Dewar \\ +The University of Bath \\ +Email: miked@nag.co.uk} +\begin{document} +\maketitle + +\index{GENTRAN ! package} \index{GENTRAN package !} + +\begin{center} February 1991 \end{center} + +GENTRAN is an automatic code GENerator and TRANslator which runs under +REDUCE and VAXIMA\index{VAXIMA}. It constructs complete numerical +programs based on sets of algorithmic specifications and symbolic +expressions. Formatted FORTRAN, RATFOR or C code can be generated +through a series of interactive commands or under the control of a +template processing routine. Large expressions can be automatically +segmented into subexpressions of manageable size, and a special +file-handling mechanism maintains stacks of open I/O channels to allow +output to be sent to any number of files simultaneously and to +facilitate recursive invocation of the whole code generation process. +GENTRAN provides the flexibility necessary to handle most code +generation applications. This manual describes usage of the GENTRAN +package for REDUCE. + +\subsection*{Acknowledgements} + +The GENTRAN package was created at Kent State University to generate +numerical code for computations in finite element analysis. I would +like to thank Prof. Paul Wang for his guidance and many suggestions +used in designing the original package for VAXIMA. + +The second version of GENTRAN was implemented at Twente University of +Technology to run under REDUCE. It was designed to be interfaced with +a code optimization facility created by Dr. J. A. van Hulzen. I would +like to thank Dr. van Hulzen for all of his help in the implementation +of GENTRAN in RLISP during a stay at his university in The +Netherlands. + +Finally, I would like to thank Dr. Anthony Hearn of the RAND +Corporation for his help in better integrating GENTRAN into the REDUCE +environment. + +\section{INTRODUCTION} + +Solving a problem in science or engineering is often a two-step +process. First the problem is modeled mathematically and derived +symbolically to provide a set of formulas which describe how to solve +the problem numerically. Next numerical programs are written based on +this set of formulas to efficiently compute specific values for given +sets of input. Computer algebra systems such as REDUCE +provide powerful tools for use in the formula-derivation phase but +only provide primitive program-coding tools. The GENTRAN +package~\cite{Gates:85,Gates:85a,Gates:85b,Gates:86} +has been constructed to automate the tedious, +time consuming and error-prone task of writing numerical programs +based on a set of symbolic expressions. + +\subsection{The GENTRAN Code Generator and Translator} +The GENTRAN code GENeration and TRANslation package, originally +implemented in Franz LISP to run under VAXIMA~\cite{Gates:84}, is now also +implemented in RLISP to run under REDUCE. Although GENTRAN +was originally created specifically to generate numerical +code for use with an existing FORTRAN-based finite element analysis +package~\cite{Wang:86,Wang:84}, it was designed +to provide the flexibility required to handle most code generation +applications. GENTRAN contains code generation commands, file-handling +commands, mode switches, and global variables, all of which are +accessible from both the algebraic and symbolic modes of REDUCE to +give the user maximal control over the code generation process. Formatted +\index{FORTRAN} \index{RATFOR} \index{C} +FORTRAN~\cite{FORTRAN}, RATFOR~\cite{Kernighan:79}, C~\cite{Kernighan:78}, +or PASCAL code can be generated from algorithmic specifications, +i.e., descriptions of the behaviour of the target numerical program expressed +in the REDUCE programming language, and from symbolically derived expressions +and formulas. + +In addition to arithmetic expressions and assignment statements, +GENTRAN can also generate type declarations and control-flow +structures. Code generation can be guided by user-supplied +template file(s) to insert generated code into pre-existing program +skeletons, or it can be accomplished interactively through a series +of translation commands without the use of template files. Special +mode switches enable the user to turn on or off specific features such as +automatic segmentation of large expressions, and global variables +allow the user to modify the code formatting process. Generated +code can be sent to one or more files and, optionally, to +the user's terminal. Stacks of open I/O channels facilitate temporary +output redirection and recursive invocation of the code generation process. + +\subsection{Code Optimization} +\index{optimization, code} +A code optimizer~\cite{vanHulzen:89}, which runs under REDUCE, has +been constructed to reduce the arithmetic complexity of a set of +symbolic expressions (see the SCOPE package on +page~\pageref{SCOPE:intro}). It optimizes them by extracting common +subexpressions and assigning them to temporary variables which are +inserted in their places. The optimization technique is based on +mapping the expressions onto a matrix of coefficients and exponents +which are searched for patterns corresponding to the common +subexpressions. Due to this process the size of the expressions is +often considerably reduced. + +GENTRAN and the Code Optimizer have been interfaced to make it +possible to generate optimized numerical programs directly +\index{GENTRANOPT switch} from REDUCE. Setting the switch {\tt +GENTRANOPT} {\bf ON} specifies that all sequences of assignment +statements are to be optimized before being converted to numerical +code. + +\subsection{Organization of the Manual} +The remainder of this manual is divided into five sections. Sections +\ref{GENTRAN:inter} and \ref{GENTRAN:template} describe code +generation. Section \ref{GENTRAN:inter} explains interactive code +generation, the expression segmentation facility, and how temporary +variables can be generated; then section \ref{GENTRAN:template} +explains how code generation can be guided by a user-supplied template +file. Section \ref{GENTRAN:output} describes methods of output +redirection, and section \ref{GENTRAN:mod} describes user-accessible +global variables and mode switches which alter the code generation +process. Finally section \ref{GENTRAN:examples} presents three +complete examples. + +\subsubsection{Typographic Conventions} +The following conventions are used in the syntactic definitions of +commands in this manual: +\begin{itemize} +\item[{-}] +Command parts which must be typed exactly as shown are given in +{\bf BOLD PRINT}. +\item[{-}] +User-supplied arguments are {\it emphasized}. +\item[{-}] +[ ... ] indicate optional command parts. +\end{itemize} +The syntax of each GENTRAN command is shown terminated with a {\bf ;}. +However, either {\bf ;} or {\bf \$} can be used to terminate any +command with the usual REDUCE meaning: {\bf ;} indicates that the +returned value is to be printed, while {\bf \$} indicates that printing +of the returned value is to be suppressed. + +Throughout this manual it is stated that file name arguments must be +atoms. The exact type of atom (e.g., identifier or string) is +system and/or site dependent. The instructions for the implementation +being used should therefore be consulted. + +\section{Interactive Code Generation}\label{GENTRAN:inter} +GENTRAN generates numerical programs based on algorithmic specifications +in the REDUCE programming language and derived symbolic expressions +\index{FORTRAN} \index{RATFOR} \index{PASCAL} \index{C} +produced by REDUCE evaluations. FORTRAN, RATFOR, PASCAL or C code can +be produced. Type declarations can be generated, and comments and +other literal strings can be inserted into the generated code. In +addition, large arithmetic expressions can be automatically segmented +into a sequence of subexpressions of manageable size. + +This section explains how to select the target language, generate +code, control expression segmentation, and how to generate temporary +variable names. + +\subsection{Target Language Selection} +\label{gentranlang} +Before generating code, the target numerical language must be +selected. GENTRAN is currently able to generate FORTRAN, RATFOR, +PASCAL and C \ttindex{GENTRANLANG"!*} code. The global variable {\bf +GENTRANLANG!*} determines which type of code is produced. {\bf +GENTRANLANG!*} can be set in algebraic or symbolic mode. It can be +set to any value, but only four atoms have special meaning: {\bf +FORTRAN}, {\bf RATFOR}, {\bf PASCAL} and {\bf C}. Any other value is +assumed to mean {\bf FORTRAN}. {\bf GENTRANLANG!*} is always +initialized to {\bf FORTRAN}. + + +\subsection{Translation} +\label{translation} +\index{GENTRAN ! command} +The {\bf GENTRAN} (GENerate/TRANslate) command is used to generate +numerical code and also to translate code from algorithmic +specifications in the REDUCE programming language to code in the +target numerical language. Section~\ref{generation} explains code +{\em generation}. This section explains code {\em translation}. + +A substantial subset of all expressions and statements in the REDUCE +programming language can be translated directly into numerical code. +The {\bf GENTRAN} command takes a REDUCE expression, statement, or +procedure definition, and translates it into code in the target +language. + +\begin{describe}{Syntax:} +{\bf GENTRAN} {\it stmt} [ {\bf OUT} {\it f1,f2,\dots\ ,fn} ]{\it ;} +\end{describe} + +\begin{describe}{Arguments:} +{\it stmt} is any REDUCE expression, statement (simple, compound, or +group), or procedure definition that can be translated by GENTRAN into the +target language\footnote{See~\ref{appa} for a complete listing of REDUCE +expressions and statements that can be translated.} +{\it stmt} may contain any number of calls +to the special functions {\bf EVAL}, {\bf DECLARE}, and {\bf LITERAL} +(see sections~\ref{translation}~--~\ref{comments}). + +{\it f1,f2,\dots\ ,fn } is an optional argument list containing one or more +{\it f}'s, where each {\it f} is one of: +\par +\begin{tabular}{lll} +{\it an atom} &= &an output file\\ +{\bf T} &= &the terminal\\ +{\bf NIL} &= &the current output file(s)\\ +\ttindex{ALL"!*} {\bf ALL!*} &= &all files currently open for output \\ +& & by GENTRAN (see section~\ref{GENTRAN:output})\\ +\end{tabular} +\end{describe} +\index{side effects} +\begin{describe}{Side Effects:} +{\bf GENTRAN} translates {\it stmt} into formatted code in the target language. + +If the optional part of the command is not given, generated code is simply +written to the current output file. However, if it is +given, then the current output file is temporarily overridden. Generated +code is written to each file represented by +{\it f1,f2,\dots\ ,fn} for this command only. Files which were open prior +to the call to {\bf GENTRAN} will remain open after the call, and files +which did not exist prior to the call will be created, opened, written to, +and closed. The output stack will be exactly the same both before and +after the call. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRAN} returns the name(s) of the file(s) to which code was written. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** OUTPUT FILE ALREADY EXISTS + OVERWRITE FILE? (Y/N) +\end{verbatim} +\begin{verbatim} +***** WRONG TYPE OF ARG +\end{verbatim} +exp +\begin{verbatim} +***** CANNOT BE TRANSLATED +\end{verbatim} +\end{describe} +\begin{describe}{\example\footnote{When the {\bf PERIOD} flag (default +setting: ON) is turned on, all \ttindex{PERIOD} +integers are automatically printed as real numbers except exponents, +subscripts in subscripted variables, and index values in DO-type loops.}} +\index{GENTRAN package ! example} +\begin{verbatim} +1: GENTRANLANG!* := 'FORTRAN$ + +2: GENTRAN +2: FOR I:=1:N DO +2: V(I) := 0$ + + DO 25001 I=1,N + V(I)=0.0 +25001 CONTINUE + +3: GENTRANLANG!* := 'RATFOR$ + +4: GENTRAN +4: FOR I:=1:N DO +4: FOR J:=I+1:N DO +4: << +4: X(J,I) := X(I,J); +4: Y(J,I) := Y(I,J) +4: >>$ + +DO I=1,N + DO J=I+1,N + { + X(J,I)=X(I,J) + Y(J,I)=Y(I,J) + } + +5: GENTRANLANG!* := 'C$ + +6: GENTRAN +6: P := FOR I:=1:N PRODUCT I$ + +{ + P=1; + for (I=1;I<=N;++I) + P*=I; +} + +7: GENTRANLANG!* := 'PASCAL$ + +8: GENTRAN +8: S := FOR I := 1:10 SUM V(I)$ +BEGIN + S:=0; + FOR I:=1 TO 10 DO + S:=S+V(I) +END; +\end{verbatim} +\end{describe} + + +\index{numeric code} Translation is a convenient method of producing +numerical code when the exact behaviour of the resultant code is +known. It gives the REDUCE user who is familiar with the syntax of +statements in the REDUCE programming language the ability to write +code in a numerical programming language without knowing the exact +syntactical requirements of the language. However the {\em real} +power of the {\bf GENTRAN} command lies in its ability to generate +code: it can produce numerical code from symbolic expressions derived +in REDUCE in addition to translating statements directly. This aspect +is described in section~\ref{generation}. + +\subsection{Precision} +\label{precision} +\index{precision} \index{DOUBLE switch} +By default {\bf GENTRAN} generates constants and type declarations in +single precision form. If the user requires double precision output +then the switch {\bf DOUBLE} must be set {\bf ON}. This does the +following: + +\begin{itemize} +\item Declarations of appropriate type are converted to their double +precision counterparts. In FORTRAN and RATFOR this means that objects of type +{\it REAL\/} are converted to objects of type {\it DOUBLE PRECISION\/} +and objects of type {\it COMPLEX\/} are converted to {\it COMPLEX*16\/} +\footnote{This is not part of the ANSI FORTRAN standard. Some compilers +accept {\it DOUBLE COMPLEX\/} as well as, or instead of, {\it COMPLEX*16\/}, +and some accept neither.}. \index{DOUBLE PRECISION} \index{COMPLEX} +\index{COMPLEX*16} +In C the counterpart of {\it float\/} is {\it double\/}, and of {\it int\/} +is {\it long\/}. There is no complex data type and trying to translate complex +objects causes an error. +\item Similarly subprograms are given their correct type where appropriate. +\item In FORTRAN and RATFOR {\it REAL\/} and {\it COMPLEX\/} numbers are +printed with the correct double precision format. +\item Intrinsic functions are converted to their double precision counterparts +(e.g. in FORTRAN $SIN \rightarrow DSIN$ etc.). +\end{itemize} + +\subsubsection{Intrinsic FORTRAN and RATFOR functions.} +An attempt is made to convert the arguments of intrinsic functions to +the correct type. For example: +\begin{verbatim} +5: GENTRAN f:=sin(1)$ + F=SIN(1.0) + +6: GENTRAN f:=sin(x)$ + F=SIN(REAL(X)) + +7: GENTRAN DECLARE <>$ + +8: GENTRAN f:=sin(x)$ + F=SIN(X) +\end{verbatim} +Which function is used to coerce the argument may, of course, depend on the +setting of the switch {\bf DOUBLE}. + +\subsubsection{Number of printed floating point digits.} +\index{PRECISION command} \index{PRINT"!-PRECISION command} +To ensure the correct number of floating point digits are +generated it may be necessary to use either the {\bf PRECISION} or +{\bf PRINT!-PRECISION} commands. The former alters the number of +digits REDUCE calculates, the latter only the number of digits REDUCE +prints. Each takes an integer argument. It is not possible to set +the printed precision higher than the actual precision. Calling {\bf +PRINT!-PRECISION} with a negative argument causes the printed +precision to revert to the actual precision. + +\begin{verbatim} +1: on rounded$ + +2: precision 16$ + +3: 1/3; + +0.333 33333 33333 333 + +4: print!-precision 6$ + +5: 1/3; + +0.333333 + +6: print!-precision(-1)$ + +7: 1/3; + +0.333 33333 33333 333 +\end{verbatim} + +\subsection{Code Generation: Evaluation Prior to Translation} +\label{generation} +Section~\ref{translation} showed how REDUCE statements and expressions +can be translated directly into the target language. This section +shows how to indicate that parts of those statements and expressions +are to be handed to REDUCE to be evaluated before being translated. +In other words, this section explains how to generate numerical code +from algorithmic specifications (in the REDUCE programming language) +and symbolic expressions. Each of the following four subsections +describes a special function or operator that can be used to request +partial or full evaluation of expressions prior to translation. Note +that these functions and operators have the described effects {\it +only} when applied to arguments to the {\bf GENTRAN} function and that +evaluation is done in algebraic or symbolic mode, depending on the +value of the REDUCE variable {\bf !*MODE}.\ttindex{"!*MODE} + +\subsubsection{The EVAL Function} +\label{eval} +\begin{describe}{Syntax:} +{\bf EVAL} {\it exp} +\end{describe} \ttindex{EVAL} +\begin{describe}{Argument:} +{\it exp} is any REDUCE expression or statement which, after evaluation +by REDUCE, results in an expression that can be translated by +GENTRAN into the target language. +\end{describe} +\begin{describe}{Side Effect:} +When {\bf EVAL} is called on an expression which is to be translated, it +tells {\bf GENTRAN} to give the expression to REDUCE +for evaluation first, and then to translate the result of that evaluation. +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +The following formula, F, has been derived symbolically: +\begin{verbatim} + 2 +2*X - 5*X + 6 +\end{verbatim} +We wish to generate an assignment statement for the quotient +of F and its derivative. +\begin{verbatim} +1: GENTRAN +1: Q := EVAL(F)/EVAL(DF(F,X))$ + + Q=(2.0*X**2-(5.0*X)+6.0)/(4.0*X-5.0) +\end{verbatim} +\end{describe} + +\subsubsection{The :=: Operator} +\index{:=:} +\label{rsetq} \index{GENTRAN ! preevaluation} \index{rsetq operator} +In many applications, assignments must be generated in which the +left-hand side is some known variable name, but the +right-hand side is an expression that must be evaluated. For +this reason, a special operator is provided to indicate that the expression +on the right-hand side is to be evaluated prior to translation. This +special operator is {\bf :=:} (i.e., the usual REDUCE assignment operator +with an extra ``:'' on the right). +\begin{describe}{\example} \index{GENTRAN package ! example} +\begin{verbatim} +1: GENTRAN +1: DERIV :=: DF(X^4-X^3+2*x^2+1,X)$ + + DERIV=4.0*X**3-(3.0*X**2)+4.0*X +\end{verbatim} +\end{describe} +Each built-in operator in REDUCE has an alternative alphanumeric identifier +associated with it. Similarly, the GENTRAN {\bf :=:} operator has a +special identifier associated with it: {\bf RSETQ} may be used \ttindex{RSETQ} +interchangeably with {\bf :=:} on input. +\subsubsection{The ::= Operator} +\label{lsetq} +\index{matrices ! in GENTRAN} +When assignments to matrix or array elements must be generated, many +times the indices of the element must be evaluated first. The special operator +\index{::=} \index{lsetq operator} +{\bf ::=} can be used within a call to {\bf GENTRAN} +to indicate that the indices of the matrix or +array element on the left-hand side of the assignment are to +be evaluated prior to translation. (This is the usual REDUCE +assignment operator with an extra ``:'' on the left.) +\begin{describe}{\example}\index{GENTRAN package ! example} +We wish to generate assignments which assign zeros to all elements +on the main diagonal of M, an n x n matrix. +\begin{verbatim} +10: FOR j := 1 : 8 DO +10: GENTRAN +10: M(j,j) ::= 0$ + + M(1,1)=0.0 + M(2,2)=0.0 + : + : + M(8,8)=0.0 +\end{verbatim} +\end{describe} + +{\bf LSETQ} may be used interchangeably with {\bf ::=} on input.\ttindex{LSETQ} +\subsubsection{The ::=: Operator} +\label{lrsetq} +\index{::=:} \index{lrsetq operator} +In applications in which evaluated expressions are to be assigned to +array elements with evaluated subscripts, the {\bf ::=:} operator can be +used. It is a combination of the {\bf ::=} and {\bf :=:} operators described +in sections~\ref{rsetq} and ~\ref{lsetq}. +\index{matrices ! in GENTRAN} + +\newpage +\begin{describe}{\example}\index{GENTRAN package ! example} +The following matrix, M, has been derived symbolically: +\begin{verbatim} +( A 0 -1 1) +( ) +( 0 B 0 0) +( ) +( -1 0 C -1) +( ) +( 1 0 -1 D) +\end{verbatim} +We wish to generate assignment statements for those elements +on the main diagonal of the matrix. +\begin{verbatim} +10: FOR j := 1 : 4 DO +10: GENTRAN +10: M(j,j) ::=: M(j,j)$ + + M(1,1)=A + M(2,2)=B + M(3,3)=C + M(4,4)=D +\end{verbatim} +\end{describe} +The alternative alphanumeric identifier associated with {\bf ::=:} is +{\bf LRSETQ}.\ttindex{LRSETQ} + +\subsection{Explicit Type Declarations} +\label{explicit:type} +Type declarations are automatically generated each time a subprogram +heading is generated. Type declarations are constructed +from information stored in the GENTRAN symbol table. The user +can place entries into the symbol table explicitly through calls +to the special GENTRAN function {\bf DECLARE}. \index{DECLARE function} +\begin{describe}{Syntax:} +{\bf \ \ DECLARE} {\it v1,v2,\dots\ ,vn} {\bf :} {\it type;} + + or + +\begin{tabular}{ll} +{\bf DECLARE}\\ +{\bf $<$$<$}\\ +&{\it v11,v12,\dots\ ,v1n} {\bf :} {\it type1;}\\ +&{\it v21,v22,\dots\ ,v2n} {\bf :} {\it type2;}\\ +& :\\ +& :\\ +&{\it vn1,vnn,\dots\ ,vnn} {\bf :} {\it typen;}\\ +{\bf $>$$>$}{\it ;} +\end{tabular} +\end{describe} +\begin{describe}{Arguments:} +Each {\it v1,v2,\dots\ ,vn} is a list of one or more variables +(optionally subscripted to indicate array dimensions), or +variable ranges (two letters separated by a ``-''). {\it v}'s are +not evaluated unless given as arguments to {\bf EVAL}. + +Each {\it type} is a variable type in the target language. Each +must be an atom, optionally preceded by the atom {\bf IMPLICIT}. +\index{IMPLICIT option} +{\it type}'s are not evaluated unless given as arguments to {\bf EVAL}. +\end{describe} +\begin{describe}{Side Effect:} +Entries are placed in the symbol table for each variable or +variable range declared in the call to this function. The function +call itself is removed from the statement group being +translated. Then after translation, type declarations are +generated from these symbol table entries before the resulting +executable statements are printed. +\end{describe} +\begin{describe}{Diagnostic Message:} +\begin{verbatim} +***** INVALID SYNTAX +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +\begin{verbatim} +1: GENTRAN +1: << +1: DECLARE +1: << +1: A-H, O-Z : IMPLICIT REAL; +1: M(4,4) : INTEGER +1: >>; +1: FOR I:=1:4 DO +1: FOR J:=1:4 DO +1: IF I=J +1: THEN M(I,J):=1 +1: ELSE M(I,J):=0; +1: DECLARE I, J : INTEGER; +1: >>$ + + IMPLICIT REAL (A-H,O-Z) + INTEGER M(4,4),I,J + DO 25001 I=1,4 + DO 25002 J=1,4 + IF (I.EQ.J) THEN + M(I,J)=1.0 + ELSE + M(I,J)=0.0 + ENDIF +25002 CONTINUE +25001 CONTINUE +\end{verbatim} +\end{describe} +The {\bf DECLARE} statement can also be used to declare subprogram types (i.e. +{\bf SUBROUTINE} or {\bf FUNCTION}) for \index{SUBROUTINE} \index{FUNCTION} +FORTRAN and RATFOR code, and function types for all four languages. +\begin{describe}{\example}\index{GENTRAN package ! example} +\begin{verbatim} +1: GENTRANLANG!* := 'RATFOR$ + +2: GENTRAN +2: PROCEDURE FAC N; +2: BEGIN +2: DECLARE +2: << +2: FAC : FUNCTION; +2: FAC, N : INTEGER +2: >>; +2: F := FOR I:=1:N PRODUCT I; +2: DECLARE F, I : INTEGER; +2: RETURN F +2: END$ + +INTEGER FUNCTION FAC(N) +INTEGER N,F,I +{ + F=1 + DO I=1,N + F=F*I +} +RETURN(F) +END + +3: GENTRANLANG!* := 'C$ +4: GENTRAN +4: PROCEDURE FAC N; +4: BEGIN +4: DECLARE FAC, N, I, F : INTEGER; +4: F := FOR I:=1:N PRODUCT I; +4: RETURN F +4: END$ + +int FAC(N) +int N; +{ + int I,F; + { + F=1; + for (I=1;I<=N;++I) + F*=I; + } + return(F); +} +\end{verbatim} +\end{describe} + +When generating code for subscripted variables (i.e., matrix and +array elements), it is important to keep several things in mind. First +of all, when a REDUCE array is declared with a declaration such as +\index{ARRAY} +\begin{center} +{\bf ARRAY A(}{\it n}{\bf )\$} +\end{center} +where {\it n} is a positive integer, {\bf A} is actually being declared +to be of size {\bf n}+1. Each of the elements {\bf A(0), A(1), \dots\ , A(n)} +can be used. However, a FORTRAN or RATFOR declaration such as +\begin{center} +{\bf DIMENSION A(}{\it n}{\bf )} +\end{center} +declares {\bf A} only to be of size {\bf n}. Only the elements +{\bf A(1), A(2), \dots\ , A(n)} can be used. Furthermore, a C declaration +such as +\begin{center} +{\bf float A[}{\it n}{\bf ];} +\end{center} +declares {\bf A} to be of size {\bf n} with elements referred to as +{\bf A[0], A[1], \dots\ , A[}{\it n-1}{\bf ]}. + +To resolve these array size and subscripting conflicts, the user should +remember the following: +\index{subscripts ! in GENTRAN} +\begin{itemize} +\item {\it All REDUCE array subscripts are translated literally.} +Therefore it is the user's responsibility to be sure that array elements with +subscript 0 are not translated into FORTRAN or RATFOR. +\item Since C and PASCAL +arrays allow elements with a subscript of 0, when an array is +declared to be of size {\it n} by the user, {\it the actual generated type +declaration will be of size n+1} so that the user can translate +elements with subscripts from 0, and up to and including {\it n}. +\end{itemize} + +If the user is generating C code, it is possible to produce declarations +for arrays with unknown bounds: +\begin{verbatim} +5: gentran declare <>$ + +6: gendecs nil; +float X[ ][ ]; +int Y[ ]; +\end{verbatim} + + +\subsection{Implicit Type Declarations} +\label{implicit:type} \index{GETDECS switch} +Some type declarations can be made automatically if the switch {\bf GETDECS} +is {\bf ON}. In this case: +\begin{enumerate} +\item The indices of loops are automatically declared to be integers. +\index{loop indices ! in GENTRAN} +\item There is a global variable {\bf DEFTYPE!*}, which is the default +type given to objects. Subprograms, their parameters, and local scalar +objects are automatically assigned this type. \ttindex{DEFTYPE"!*} +\index{REAL*8} \index{DOUBLE PRECISION} +Note that types such as REAL*8 or DOUBLE PRECISION should not +be used as, if {\bf DOUBLE} is on, then a default type of REAL +will in fact be DOUBLE PRECISION anyway. +\item If GENTRAN is used to translate a REDUCE procedure, then it assigns +objects declared {\bf SCALAR} the type given by {\bf DEFTYPE!*}. Note that +\index{INTEGER declaration} \index{REAL declaration} +it is legal to use the commands {\bf INTEGER} and {\bf REAL} in the place +of {\bf SCALAR}, which allows the user to specify an actual type. The +procedure may also be given a return type, in which case that is used as +the default. For example: +\begin{verbatim} + +2: on getdecs,gendecs$ + +3: GENTRAN +3: real procedure f(x); +3: begin integer n;real y; +3: n := 4; +3: y := n/(1+x)^2; +3: return y; +3: end; + REAL FUNCTION F(X) + INTEGER N + REAL X,Y + N=4 + Y=N/(1.0+X)**2 + F=Y + RETURN + END + +\end{verbatim} +\end{enumerate} + +\subsection{More about Type Declarations} +\label{more:type} +A check is made on output to ensure that all types generated are legal ones. +This is necessary since {\bf DEFTYPE!*} can be set to anything. +Note that {\bf DEFTYPE!*} ought normally to be given a simple +type as its \ttindex{DEFTYPE"!*} +value, such as REAL, INTEGER, or COMPLEX, +since this will always be translated into the corresponding type in the +target language on output. + +An entry is removed from the symbol table once a declaration has been +generated for it. The {\bf KEEPDECS} switch (by default {\bf OFF}) +disables this, allowing a user to check the types of objects +\index{KEEPDECS switch} which GENTRAN has generated (useful if they +are being generated automatically) + +\subsection{Comments and Literal Strings} +\label{comments} \index{comments ! in GENTRAN} +Comments and other strings of characters can be inserted directly into +the stream of generated code through a call to the special function +{\bf LITERAL}. +\begin{describe}{Syntax:} +{\bf LITERAL} {\it arg1,arg2,\dots\ ,argn;} +\end{describe} +\begin{describe}{Arguments:} +{\it arg1,arg2,\dots\ ,argn} is an argument list containing one or more +{\it arg}'s, where each {\it arg} either is, or evaluates to, an atom. The +\ttindex{TAB"!*} \ttindex{CR"!*} +atoms {\bf TAB!*} and {\bf CR!*} have special meanings. {\it arg}'s are +not evaluated unless given as arguments to {\bf EVAL}. +\end{describe} +\begin{describe}{Side Effect:} +This statement is replaced by the character sequence resulting from +concatenation of the given atoms. Double quotes are stripped from +all string type {\it arg}'s, and the reserved atoms {\bf TAB!*} and +{\bf CR!*} are replaced by a tab to the current level of indentation, and +an end-of-line character, respectively. +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +Suppose N has value 10. +\begin{verbatim} +1: GENTRANLANG!* := 'FORTRAN$ + +2: GENTRAN +2: << +2: LITERAL +2: "C",TAB!*,"--THIS IS A FORTRAN COMMENT--",CR!*, +2: "C",CR!*; +2: LITERAL +2: TAB!*,"DATA N/",EVAL(N),"/",CR!* +2: >>$ + +C --THIS IS A FORTRAN COMMENT-- +C + DATA N/10/ + +3: GENTRANLANG!* := 'RATFOR$ +4: GENTRAN +4: FOR I:=1:N DO +4: << +4: LITERAL +4: TAB!*,"# THIS IS A RATFOR COMMENT",CR!*; +4: LITERAL +4: TAB!*,"WRITE(6,10) (M(I,J),J=1,N)",CR!*, +4: 10,TAB!*,"FORMAT(1X,10(I5,3X))",CR!* +4: >>$ + +DO I=1,N + { + # THIS IS A RATFOR COMMENT + WRITE(6,10) (M(I,J),J=1,N) +10 FORMAT(1X,10(I5,3X)) + } + +5: GENTRANLANG!* := 'C$ +6: GENTRAN +6: << +6: X:=0; +6: LITERAL "/* THIS IS A",CR!*, +6: " C COMMENT */",CR!* +6: >>$ + +{ + X=0.0; +/* THIS IS A + C COMMENT */ +} + +7: GENTRANLANG!* := 'PASCAL$ + +8: GENTRAN +8: << +8: X := SIN(Y); +8: LITERAL "{ THIS IS A PASCAL COMMENT }", CR!* +8: >>$ +BEGIN + X:=SIN(Y) +{ THIS IS A PASCAL COMMENT } +END; + +\end{verbatim} +\end{describe} +\subsection{Expression Segmentation} +\label{segmentation} \index{segmenting expressions} +Symbolic derivations can easily produce formulas that can be anywhere +from a few lines to several pages in length. Such formulas +can be translated into numerical assignment statements, but unless they +are broken into smaller pieces they may be too long for a compiler +to handle. (The maximum number of continuation lines for one statement +allowed by most FORTRAN compilers is only 19.) Therefore GENTRAN +\index{continuation lines} +contains a segmentation facility which automatically {\it segments}, +or breaks down unreasonably large expressions. + +The segmentation facility generates a sequence of assignment +statements, each of which assigns a subexpression to an automatically +generated temporary variable. This sequence is generated in such a +way that temporary variables are re-used as soon as possible, thereby +keeping the number of automatically generated variables to a minimum. +The facility can be turned on or off by setting the mode +\index{GENTRANSEG switch} switch {\bf GENTRANSEG} accordingly (i.e., +by calling the REDUCE function {\bf ON} or {\bf OFF} on it). The user +can control the maximum allowable expression size by setting the +\ttindex{MAXEXPPRINTLEN"!*} +variable {\bf MAXEXPPRINTLEN!*} to the maximum number of characters +allowed in an expression printed in the target language (excluding +spaces automatically printed by the formatter). The {\bf GENTRANSEG} +switch is on initially, and {\bf MAXEXPPRINTLEN!*} is initialized to +800. +\begin{describe}{\example}\index{GENTRAN package ! example} +\begin{verbatim} +1: ON EXP$ + +2: JUNK1 := (A+B+C+D)^2$ + +3: MAXEXPPRINTLEN!* := 24$ + +4: GENTRAN VAL :=: JUNK1$ + + T0=A**2+2.0*A*B + T0=T0+2.0*A*C+2.0*A*D + T0=T0+B**2+2.0*B*C + T0=T0+2.0*B*D+C**2 + VAL=T0+2.0*C*D+D**2 + +5: JUNK2 := JUNK1/(E+F+G)$ + +6: MAXEXPPRINTLEN!* := 23$ + +7: GENTRANLANG!* := 'C$ + +8: GENTRAN VAL :=: JUNK2$ + +{ + T0=power(A,2)+2.0*A*B; + T0+=2.0*A*C; + T0=T0+2.0*A*D+power(B,2); + T0+=2.0*B*C; + T0=T0+2.0*B*D+power(C,2); + T0=T0+2.0*C*D+power(D,2); + VAL=T0/(exp(1.0)+F+G); +} +\end{verbatim} +\end{describe} +\subsubsection{Implicit Type Declarations}\label{GENTRAN:itd} +When the segmentation routine generates temporary variables, it places +type declarations in the symbol table for those variables if +possible. It uses the following rules to determine their type: +\index{implicit type declarations} \index{temporary variables ! type} +\begin{itemize} +\item[{(1)}] +If the type of the variable to which the large expression is being +assigned is already known (i.e., has been declared by the user), +then the temporary variables will be declared to be of that same type. +\item[{(2)}] \ttindex{TEMPVARTYPE"!*} +If the global variable {\bf TEMPVARTYPE!*} has a non-NIL value, then the +temporary variables are declared to be of that type. +\item[{(3)}] +Otherwise, the variables are not declared. +\end{itemize} + +\newpage +\begin{describe}{\example} \index{GENTRAN package ! example} + +\begin{verbatim} +1: MAXEXPPRINTLEN!* := 20$ + +2: TEMPVARTYPE!* := 'REAL$ + +3: GENTRAN +3: << +3: DECLARE ISUM : INTEGER; +3: ISUM := II+JJ+2*KK+LL+10*MM+NN; +3: PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2) +3: >>$ + + INTEGER ISUM,T0 + REAL T1 + T0=II+JJ+2.0*KK+LL + ISUM=T0+10.0*MM+NN + T1=V(X,Y)*SIN(X)*COS(Y**2) + PROD=T1*(X+Y+Z**2) +\end{verbatim} +\end{describe} +\subsection{Generation of Temporary Variable Names} +\label{tempvars} \index{temporary variables ! names} +As we have just seen, GENTRAN's segmentation module generates +temporary variables and places type declarations in the symbol table +for them whenever possible. Various other modules also generate +variables and corresponding declarations. All of these modules call +one special GENTRAN function each time they need a temporary +variable name. This function is {\bf TEMPVAR}. There are situations +in which it may be convenient for the user to be able to generate +temporary variable names directly.\footnote{One such example is suppression +of the simplification process to generate numerical code which is more +efficient. See the example in section~\ref{tempvar:example} on +page~\pageref{tempvar:example}.} +Therefore {\bf TEMPVAR} \ttindex{TEMPVAR} +is a user-accessible function which may be called from both +the algebraic and symbolic modes of REDUCE. +\begin{describe}{Syntax:} +{\bf TEMPVAR} {\it type} +\end{describe} +\begin{describe}{Argument:} +{\it type} is an atom which either indicates the variable type in the +target language (INTEGER, REAL, etc.), or is {\bf NIL} if the variable +type is unknown. +\end{describe} +\begin{describe}{Side Effects:} +{\bf TEMPVAR} creates temporary variable names by repeatedly concatenating +the values of the global variables {\bf TEMPVARNAME!*} (which has a +\ttindex{TEMPVARNUM"!*} +default value of {\bf T}) and {\bf TEMPVARNUM!*} (which is initially set +to 0) and incrementing {\bf TEMPVARNUM!*} until a variable name is created +which satisfies one of the following conditions: +\begin{itemize} +\item[{(1)}] +It was not generated previously, and it has not been declared by the user. +\item[{(2)}] +It was previously generated to hold the same type of value that it +must hold this time (e.g. INTEGER, REAL, etc.), and the value assigned +to it previously is no longer needed. +\end{itemize} +If {\it type} is a non-NIL argument, or if {\it type} is {\bf NIL} +and the global variable {\bf TEMPVARTYPE!*} (initially NIL) has been +\ttindex{TEMPVARTYPE"!*} +set to a non-NIL value, then a type entry for the generated variable name +is placed in the symbol table. +\end{describe} +\begin{describe}{Returned Value:} +{\bf TEMPVAR} returns an atom which can be used as a variable. +\end{describe} +Note: It is the user's responsibility to set {\bf TEMPVARNAME!*} and +{\bf TEMPVARNUM!*} to values such that generated variable +names will not clash with variables used elsewhere in the +program unless those variables have been declared. + +\subsubsection{Marking Temporary Variables} +In section~\ref{tempvars} we saw that a temporary variable name (of a certain +type) can be regenerated when the value previously assigned to it +is no longer needed. This section describes a function which {\it marks} +a variable to indicate that it currently holds a +significant value, and the next section describes functions which +{\it unmark} variables to indicate that the values they hold are no +\index{temporary variables ! marking} +\index{marking temporary variables} +longer significant.\ttindex{MARKVAR} +\begin{describe}{Syntax:} +{\bf MARKVAR} {\it var} +\end{describe} +\begin{describe}{Argument:} +{\it var} is an atom. +\end{describe} +\begin{describe}{Side Effects:} +{\bf MARKVAR} sets a flag on {\it var}'s property list to indicate that +{\it var} currently holds a significant value. +\end{describe} +\begin{describe}{Returned Value:} +{\bf MARKVAR} returns {\it var}. +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +The following matrix, M has been derived symbolically: +\begin{verbatim} +(X*(Y+Z) 0 X*Z) +( ) +( -X X+Y 0) +( ) +( X*Z 0 Z**2) +\end{verbatim} +We wish to replace each non-zero element by a generated variable name +to prevent these expressions from being resubstituted into further +calculations. (We will also record these substitutions in the +numerical program we are constructing by generating assignment +statements.)\footnote{ Note: {\bf MARKVAR} is a symbolic mode +procedure. Therefore, the name of each variable whose value is to be +passed to it from algebraic mode must appear in a {\bf SHARE} +\index{SHARE command} declaration. This tells REDUCE to share the +variable's value between algebraic and symbolic modes.} +\begin{verbatim} +9: SHARE var$ + +10: FOR j := 1 : 3 DO +10: FOR k := 1 : 3 DO +10: IF M(j,k) NEQ 0 THEN +10: << +10: var := TEMPVAR(NIL); +10: MARKVAR var; +10: GENTRAN +10: EVAL(var) :=: M(j,k); +10: M(j,k) := var +10: >>$ + + T0=X*(Y+Z) + T1=X*Z + T2=-X + T3=X+Y + T4=X*Z + T5=Z**2 +\end{verbatim} +Now matrix M contains the following entries: +\begin{verbatim} +(T0 0 T1) +( ) +(T2 T3 0) +( ) +(T4 0 T5) +\end{verbatim} +\end{describe} + +\subsubsection{Unmarking Temporary Variables} +\index{unmarking temporary variables} \index{temporary variables ! unmarking} +After the value assigned to a temporary variable has been used +in the numerical program and is no longer needed, the variable name can be \ +\ttindex{UNMARKVAR} +{\it unmarked} with the {\bf UNMARKVAR} function. +\begin{describe}{Syntax:} +{\bf UNMARKVAR} {\it var;} +\end{describe} +\begin{describe}{Argument:} +{\it var} is an atom (variable name) or an expression containing one or more +variable names. +\end{describe} +\begin{describe}{Side Effect:} +{\bf UNMARKVAR} resets flags on the property lists of all variable names in +{\it var} to indicate that they do not hold significant values any longer. +\end{describe} + +\subsection{Enabling and Disabling Generation of Type Declarations} +\label{control:type} +GENTRAN maintains a symbol table of variable type and dimension +information. It adds information to the symbol table by processing +user-supplied calls to the {\bf DECLARE} function (see +Section~\ref{explicit:type}) and as a +side effect of generating temporary variable names +(see Sections~\ref{segmentation} and \ref{tempvars}). +All information is stored in the symbol table until GENTRAN is ready +to print formatted numerical code. Since programming languages such as +FORTRAN require that type declarations appear before executable statements, +GENTRAN automatically extracts all relevant type information and prints it +in the form of type declarations before printing executable +statements. This feature is useful when the entire body of a (sub)program is +generated at one time: in this case, type declarations are printed +before any executable code. However, if the user chooses to generate code +in pieces, the resulting code may have type declarations interleaved +\index{GENDECS switch} +with executable code. For this reason, the user may turn the {\bf GENDECS} +mode switch on or off, depending on whether or not s/he chooses to use +this feature. + +In the following we re-examine the example of Section~\ref{GENTRAN:itd}. +\begin{describe}{\example}\index{GENTRAN package ! example} +\begin{verbatim} +1: MAXEXPPRINTLEN!* := 20$ + +2: TEMPVARTYPE!* := 'REAL!*8$ + +3: GENTRAN +3: << +3: DECLARE ISUM : INTEGER; +3: ISUM := II+JJ+2*KK+LL+10*MM+NN +3: >>$ + + INTEGER ISUM,T0 + T0=II+JJ+2*KK+LL + ISUM=T0+10*MM+NN + +4: GENTRAN PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2)$ + + REAL*8 T2 + T2=V(X,Y)*SIN(REAL(X))*COS(REAL(Y**2)) + PROD=T2*(X+Y+Z**2) + +5: OFF GENDECS$ + +6: GENTRAN +6: << +6: DECLARE ISUM : INTEGER; +6: ISUM := II+JJ+2*KK+LL+10*MM+NN +6: >>$ + + T0=II+JJ+2*KK+LL + ISUM=T0+10*MM+NN + +7: GENTRAN PROD := V(X,Y)*SIN(X)*COS(Y^2)*(X+Y+Z^2)$ + + T2=V(X,Y)*SIN(REAL(X))*COS(REAL(Y**2)) + PROD=T2*(X+Y+Z**2) +\end{verbatim} +\end{describe} + +In Section~\ref{template:type} we will explain how to further control +the generation of type declarations. + +\subsection{Complex Numbers} +\label{complex} \index{complex numbers} \index{COMPLEX} +With the switch {\bf COMPLEX} set {\bf ON}, GENTRAN will generate the +correct representation for a complex number in the given precision +provided that: + +\begin{enumerate} +\item The current language supports a complex data type (if it doesn't then +an error results); +\item The complex quantity is evaluated by REDUCE +to give an object of the correct +domain; i.e. +\begin{verbatim} + GENTRAN x:=: 1+i; + + GENTRAN x:= eval 1+i; + + z := 1+i; + GENTRAN x:=: z; +\end{verbatim} +will all generate the correct result, as will their Symbolic mode equivalents, +while: +\begin{verbatim} + GENTRAN x := 1+i; +\end{verbatim} +will not. +\end{enumerate} + +\subsection{Intrinsic Functions} +\label{intrinsic} \index{intrinsic functions} +A warning is issued if a standard REDUCE function is encountered which +does not have an intrinsic counterpart in the target language (e.g. + {\it cot\/}, +{\it sec\/} etc.). +Output is not halted in case this is a user--supplied function, either via +a REDUCE definition or within a GENTRAN template. + +The types of intrinsic FORTRAN functions are coerced to reals (in the correct +precision) as the following examples demonstrate: +\begin{verbatim} +19: GENTRAN x:=sin(0)$ + X=SIN(0.0) + +20: GENTRAN x:=cos(A)$ + X=COS(REAL(A)) + +21: ON DOUBLE$ + +22: GENTRAN x := log(1)$ + X=DLOG(1.0D0) + +23: GENTRAN x := exp(B)$ + X=DEXP(DBLE(B)) + +24: GENTRAN DECLARE <>$ + +25: GENTRAN x := exp(B)$ + X=DEXP(B) + +\end{verbatim} + +\subsection{Miscellaneous} + +\subsubsection{MAKECALLS} +A statement like: +\begin{verbatim} + GENTRAN x^2+1$ +\end{verbatim} +will yield the result: +\begin{verbatim} + X**2+1 +\end{verbatim} +but, under normal circumstances, a statement like: +\begin{verbatim} + GENTRAN sin(x)$ +\end{verbatim} +will yield the result: +\begin{verbatim} + CALL SIN(X) +\end{verbatim} +\index{MAKECALLS switch} +The switch {\bf MAKECALLS} (OFF by default) will make GENTRAN yield +\begin{verbatim} + SIN(X) +\end{verbatim} +This is useful if you don't know in advance what the form of the expression +which you are translating is going to be. + +\subsubsection{E} +\index{e} \index{EXP} +When GENTRAN encounters $e$ it translates it into EXP(1), and when GENTRAN +encounters +$e^x$ it is translated to EXP(X). This is then translated +into the correct statement in the given language and precision. Note that +it is still possible to do something like: +\begin{verbatim} + GENTRAN e:=:e; +\end{verbatim} +and get the correct result. + +\subsection{Booleans} +\index{booleans} \index{true} \index{false} +Some languages, like Fortran-77, have a boolean data type. Others, like +C, do not. When translating Reduce code into a language with a boolean +data type, GENTRAN will recognise the special identifiers $true$ and +$false$. For example: +\begin{verbatim} +3: gentran <>; + LOGICAL T + T=.TRUE. +\end{verbatim} + + +\section{Template Processing}\label{GENTRAN:template} + +\index{GENTRAN ! templates} \index{templates !} \index{code templates} +In some code generation applications pieces of the target numerical +program are known in advance. A {\it template} file containing a +program outline is supplied by the user, and formulas are derived in +REDUCE, converted to numerical code, and inserted in the corresponding +places in the program outline to form a complete numerical program. A +template processor is provided by GENTRAN for use in these +applications. + +\subsection{The Template Processing Command} +\label{templates} \index{GENTRANIN command} +\begin{describe}{Syntax:} +{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm} [{\bf OUT} {\it f1,f2,\dots\ + ,fn\/}]{\it ;} +\end{describe} +\begin{describe}{Arguments:} +{\it f1,f2,\dots\ ,fm\/} is an argument list containing one or more +{\it f\/}'s, +where each {\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom}& = &a template (input) file\\ +{\bf T}& = &the terminal\\ +\end{tabular} +\end{center} +{\it f1,f2,\dots\ ,fn\/} is an optional argument list containing one or more +{\it f\/}'s, where each {\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom}& = &an output file\\ +{\bf T}& = &the terminal\\ +{\bf NIL}& = &the current output file(s)\\ +{\bf ALL!*}& = &all files currently open for output \\ +& & by GENTRAN (see section~\ref{GENTRAN:output}) \\ +\end{tabular} +\end{center} +\end{describe} +\begin{describe}{Side Effects:} +{\bf GENTRANIN} processes each template file {\it f1,f2,\dots\ ,fm} +sequentially. + +A template file may contain any number of parts, each of which +is either an active or an inactive part. All active parts start with +the character sequence {\bf ;BEGIN;} and end with {\bf ;END;}. The end +of the template file is indicated by an extra {\bf ;END;} character +sequence. \index{;BEGIN; marker} \index{;END; marker} + +Inactive parts of template files are assumed to contain code in the +target language (FORTRAN, RATFOR, PASCAL or C, depending on the value +\ttindex{GENTRANLANG"!*} +of the global variable {\bf GENTRANLANG!*}). All inactive parts are +copied to the output. Comments delimited by the appropriate characters, +\index{comments ! in GENTRAN} +\begin{center} +\begin{tabular}{lll} +&{\bf C} \dots\ $<$cr$>$ & FORTRAN (beginning in column 1)\\ +&{\bf \#} \dots\ $<$cr$>$ & RATFOR \\ +&{\bf /*} \dots\ {\bf */} & C \\ +&{\bf \{} \dots\ {\bf \}} or {\bf *(} \dots\ {\bf )*} & PASCAL\\ +\end{tabular} +\end{center} +are also copied in their entirety to the output. Thus the character +sequences {\bf ;BEGIN;} and {\bf ;END;} have no special meanings +within comments. + +Active parts may contain any number of REDUCE expressions, statements, +and commands. They are not copied directly to the output. Instead, +they are given to REDUCE for evaluation in algebraic mode\footnote{ +Active parts are evaluated in algebraic mode unless the mode is +explicitly changed to symbolic from within the active part itself. +This is true no matter which mode the system was in when the template +processor was called.}. All output generated by each evaluation is +sent to the output file(s). Returned values are only printed on the +terminal.\index{GENTRAN ! preevaluation} + +Active parts will most likely contain calls to {\bf GENTRAN} to +generate code. This means that the result of processing a +template file will be the original template file with all active +parts replaced by generated code. + +If {\bf OUT} {\it f1,f2,\dots\ ,fn} is not given, generated code is simply +written to the current-output file. + +However, if {\bf OUT} {\it f1,f2,\dots\ ,fn} +is given, then the current-output file +is temporarily overridden. Generated code is written to each file represented +by {\it f1,f2,\dots\ ,fn} for this command only. Files which were +open prior to the call to {\bf GENTRANIN} will remain open after the +call, and files which did not exist prior to the call will be +created, opened, written to, and closed. The output-stack will be +exactly the same both before and after the call. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRANIN} returns the names of all files written to by this +command. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** OUTPUT FILE ALREADY EXISTS + OVERWRITE FILE? (Y/N) + +***** NONEXISTENT INPUT FILE + +***** TEMPLATE FILE ALREADY OPEN FOR INPUT + +***** WRONG TYPE OF ARG +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +Suppose we wish to generate a FORTRAN subprogram to compute the +determinant of a 3 x 3 matrix. We can construct a template +file with an outline of the FORTRAN subprogram and REDUCE and +GENTRAN commands to fill it in: +\index{matrices ! in GENTRAN} + +Contents of file {\tt det.tem}: +\end{describe} +\begin{framedverbatim} + REAL FUNCTION DET(M) + REAL M(3,3) +;BEGIN; + OPERATOR M$ + MATRIX MM(3,3)$ + MM := MAT( (M(1,1),M(1,2),M(1,3)), + (M(2,1),M(2,2),M(2,3)), + (M(3,1),M(3,2),M(3,3)) )$ + GENTRAN DET :=: DET(MM)$ +;END; + RETURN + END +;END; +\end{framedverbatim} + +\begin{describe}{} +Now we can generate a FORTRAN subprogram with the following +REDUCE session: +\begin{verbatim} +1: GENTRANLANG!* := 'FORTRAN$ + +2: GENTRANIN +2: "det.tem" +2: OUT "det.f"$ +\end{verbatim} +Contents of file det.f: +\end{describe} +\begin{framedverbatim} + REAL FUNCTION DET(M) + REAL M(3,3) + DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) + . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1 + . ,2)-(M(3,1)*M(2,2)*M(1,3)) + RETURN + END +\end{framedverbatim} + +\subsection{Copying Files into Template Files} +\label{copy:template} + +\index{GENTRANIN command} \index{files ! in GENTRAN} +Template files can be copied into other template files with recursive +calls to {\bf GENTRANIN} ; i.e., by calling {\bf GENTRANIN} from the +active part of a template file. + +For example, suppose we wish to copy the contents of a file containing +a subprogram into a file containing a main program. We will call +{\bf GENTRANIN} to do the copying, so the subprogram file must +have {\bf ;END;} on its last line: + +Contents of file {\tt det.tem}: +\begin{framedverbatim} + REAL FUNCTION DET(M) + REAL M(3,3) + DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) + . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1 + . ,2)-(M(3,1)*M(2,2)*M(1,3)) + RETURN + END +;END; +\end{framedverbatim} + +Now the template file for the main program can be constructed +with an active part which will include file det.tem: + +Contents of file {\tt main.tem}: +\begin{framedverbatim} +C +C MAIN PROGRAM +C + REAL M(3,3),DET + WRITE(6,*) 'ENTER 3 x 3 MATRIX' + DO 100 I=1,3 + READ(5,*) (M(I,J),J=1,3) +100 CONTINUE + WRITE(6,*) ' DET = ', DET(M) + STOP + END +C +C DETERMINANT CALCULATION +C +;BEGIN; + GENTRANIN "det.tem"$ +;END; +;END; +\end{framedverbatim} + +The following REDUCE session will create the file {\tt main.f}: +\begin{verbatim} +1: GENTRANIN +1: "main.tem" +1: OUT "main.f"$ +\end{verbatim} + +Contents of file {\tt main.f}: +\begin{framedverbatim} +C +C MAIN PROGRAM +C + REAL M(3,3),DET + WRITE(6,*) 'ENTER 3 x 3 MATRIX' + DO 100 I=1,3 + READ(5,*) (M(I,J),J=1,3) +100 CONTINUE + WRITE(6,*) ' DET = ', DET(M) + STOP + END +C +C DETERMINANT CALCULATION +C + REAL FUNCTION DET(M) + REAL M(3,3) + DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) + . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)* + . M(1,2)-(M(3,1)*M(2,2)*M(1,3)) + RETURN + END +\end{framedverbatim} + +\subsection{The Template File Stack} +\label{template:stack} + +\index{templates ! file stack} +The REDUCE {\bf IN} command takes one or more file names as +arguments. REDUCE reads each of the given files and executes all +statements and commands, any of which may be another {\bf IN} +command. A stack of input file names is maintained by +REDUCE to allow recursive invocation of the {\bf IN} command. Similarly, +a stack of template file names is maintained by GENTRAN to facilitate +recursive invocation of the template processor. Section~\ref{copy:template} +showed that the {\bf GENTRANIN} command can be +\index{GENTRANIN command} +called recursively to copy files into other files. This section shows +that template files which are copied into other template files can also +contain active parts, and thus the whole code generation process can +be invoked recursively. + +We can generalize the example of section~\ref{copy:template} by +generating code recursively. We can extend it to generate code which +will compute entries of the inverse matrix, also. Suppose +we have created the file init.red, which contains REDUCE commands to +create an {\it n}x{\it n} matrix MM and initialize its entries +to M(1,1), M(1,2),~\dots~, M({\it n}, {\it n}), for some user-entered +value of {\it n}: + +Contents of file {\tt init.red}: +\begin{framedverbatim} +OPERATOR M$ +MATRIX MM(n,n)$ +FOR J := 1 : n DO + FOR K := 1 : n DO + MM(J,K) := M(J,K)$ +END$ +\end{framedverbatim} + +We have also created template files {\tt det.tem} and {\tt inv.tem} which +contain outlines of FORTRAN subprograms to compute the +determinant and inverse of an {\it n}x{\it n} matrix, respectively: + +Contents of file {\tt det.tem}: +\begin{framedverbatim} + REAL FUNCTION DET(M) +;BEGIN; + GENTRAN + << + DECLARE M(EVAL(n),EVAL(n)) : REAL; + DET :=: DET(MM) + >>$ +;END; + RETURN + END +;END; +\end{framedverbatim} +Contents of file {\tt inv.tem}: +\begin{framedverbatim} + SUBROUTINE INV(M,MINV) +;BEGIN; + GENTRAN + << + DECLARE M(EVAL(n),EVAL(n)), + MINV(EVAL(n),EVAL(n)) : REAL; + MINV :=: MM^(-1) + >>$ +;END; + RETURN + END +;END; +\end{framedverbatim} + +Now we can construct a template file with a generalized version of the main +program given in section~\ref{copy:template} +and can place {\bf GENTRANIN} commands +in this file to generate code recursively from the template files det.tem +and inv.tem: + +Contents of file {\tt main.tem}: +\begin{framedverbatim} +C +C MAIN PROGRAM +C +;BEGIN; + GENTRAN + << + DECLARE + << + M(EVAL(n),EVAL(n)), + DET, + MINV(EVAL(n),EVAL(n)) : REAL; + N : INTEGER + >>; + LITERAL TAB!*, "DATA N/", EVAL(n), "/", CR!* + >>$ +;END; + WRITE(6,*) 'ENTER ', N, 'x', N, ' MATRIX' + DO 100 I=1,N + READ(5,*) (M(I,J),J=1,N) +100 CONTINUE + WRITE(6,*) ' DET = ', DET(M) + WRITE(6,*) ' INVERSE MATRIX:' + CALL INV(M,MINV) + DO 200 I=1,N + WRITE(6,*) (MINV(I,J),J=1,N) +200 CONTINUE + STOP + END +C +C DETERMINANT CALCULATION +C +;BEGIN; + GENTRANIN "det.tem"$ +;END; +C +C INVERSE CALCULATION +C +;BEGIN; + GENTRANIN "inv.tem"$ +;END; +;END; +\end{framedverbatim} + +The following REDUCE session will create the file {\tt main.f}: +\begin{verbatim} +1: n := 3$ + +2: IN "init.red"$ + +3: GENTRANLANG!* := 'FORTRAN$ + +4: GENTRANIN +4: "main.tem" +4: OUT "main.f"$ +\end{verbatim} +Contents of file {\tt main.f}: +\begin{framedverbatim} +C +C MAIN PROGRAM +C + REAL M(3,3),DET,MINV(3,3) + INTEGER N + DATA N/3/ + WRITE(6,*) 'ENTER ', N, 'x', N, ' MATRIX' + DO 100 I=1,N + READ(5,*) (M(I,J),J=1,N) +100 CONTINUE + WRITE(6,*) ' DET = ', DET(M) + WRITE(6,*) ' INVERSE MATRIX:' + CALL INV(M,MINV) + DO 200 I=1,N + WRITE(6,*) (MINV(I,J),J=1,N) +200 CONTINUE + STOP + END +C +C DETERMINANT CALCULATION +C + REAL FUNCTION DET(M) + REAL M(3,3) + DET=M(3,3)*M(2,2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2) + . *M(2,3)*M(1,1))+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3) + . *M(1,2)-(M(3,1)*M(2,2)*M(1,3)) + RETURN + END +C +C INVERSE CALCULATION +C + SUBROUTINE INV(M,MINV) + REAL M(3,3),MINV(3,3) + MINV(1,1)=(M(3,3)*M(2,2)-(M(3,2)*M(2,3)))/(M(3,3)*M(2,2 + . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) + . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 + . ,2)*M(1,3))) + MINV(1,2)=(-(M(3,3)*M(1,2))+M(3,2)*M(1,3))/(M(3,3)*M(2, + . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) + . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( + . 2,2)*M(1,3))) + MINV(1,3)=(M(2,3)*M(1,2)-(M(2,2)*M(1,3)))/(M(3,3)*M(2,2 + . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) + . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 + . ,2)*M(1,3))) + MINV(2,1)=(-(M(3,3)*M(2,1))+M(3,1)*M(2,3))/(M(3,3)*M(2, + . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) + . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( + . 2,2)*M(1,3))) + MINV(2,2)=(M(3,3)*M(1,1)-(M(3,1)*M(1,3)))/(M(3,3)*M(2,2 + . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) + . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 + . ,2)*M(1,3))) + MINV(2,3)=(-(M(2,3)*M(1,1))+M(2,1)*M(1,3))/(M(3,3)*M(2, + . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) + . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( + . 2,2)*M(1,3))) + MINV(3,1)=(M(3,2)*M(2,1)-(M(3,1)*M(2,2)))/(M(3,3)*M(2,2 + . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) + . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 + . ,2)*M(1,3))) + MINV(3,2)=(-(M(3,2)*M(1,1))+M(3,1)*M(1,2))/(M(3,3)*M(2, + . 2)*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1) + . )+M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M( + . 2,2)*M(1,3))) + MINV(3,3)=(M(2,2)*M(1,1)-(M(2,1)*M(1,2)))/(M(3,3)*M(2,2 + . )*M(1,1)-(M(3,3)*M(2,1)*M(1,2))-(M(3,2)*M(2,3)*M(1,1)) + . +M(3,2)*M(2,1)*M(1,3)+M(3,1)*M(2,3)*M(1,2)-(M(3,1)*M(2 + . ,2)*M(1,3))) + RETURN + END +\end{framedverbatim} + +This is an example of a modular approach to code generation; separate +subprogram templates are given in separate files. Furthermore, the template +files are general; they can be used for matrices of any predetermined +size. Therefore, we can easily generate different subprograms to +handle matrices of different sizes from the same template files +simply by assigning different values to {\it n}, and reloading the +file init.red. + +\subsection{Template Processing and Generation of Type Declarations} +\label{template:type} +\index{GENDECS switch} \index{type declarations} +In Section~\ref{control:type} we described the {\bf GENDECS} flag. We +explained that type declarations are not generated when this flag is +turned off. Now that the concept of template processing has been +explained, it is appropriate to continue our discussion of generation +of type declarations. + +When the {\bf GENDECS} flag is off, type declaration information is not +simply discarded --- it is still maintained in the symbol table. Only the +automatic extraction of this information in the form of declarations is +disabled. When the {\bf GENDECS} flag is turned off, all type +information associated with a specific subprogram can be retrieved in the +form of generated declarations by calling the {\bf GENDECS} function with +the subprogram name as argument. The template processor recognizes +function and subroutine headings. It always keeps track of the name of +the subprogram it is processing. Therefore, the declarations associated with +a particular subprogram {\it subprogname} can be generated with a call to +{\bf GENDECS} as follows: +\begin{center} +{\bf GENDECS} {\it subprogname}\$ +\end{center} + +By using the {\bf GENDECS} flag and function together with the template +processing facility, it is possible to have type information +inserted into the symbol table during a first pass over a template file, and +then to have it extracted during a second pass. Consider the following +example in which the original template file is transformed into an +intermediate template during the first pass, and then into the final file +of FORTRAN code during the second pass: + +Contents of file {\tt junk.tem}: +\begin{framedverbatim} +;BEGIN; +MAXEXPPRINTLEN!* := 50$ +OFF GENDECS$ +;END; + SUBROUTINE CALC(X,Y,Z,A,B,RES) +;BEGIN; +GENTRAN LITERAL ";BEGIN;", CR!*, + "GENDECS CALC$", CR!*, + ";END;", CR!*$ +;END; + X=3.75 + Y=-10.2 + Z=16.473 +;BEGIN; +GENTRAN +<< + DECLARE X,Y,Z,A,B,RES : REAL; + RES :=: (X + Y + Z)^3*(A + B)^2 +>>$ +;END; + RETURN + END +;BEGIN; +GENTRAN LITERAL ";END;", CR!*$ +;END; +;END; +\end{framedverbatim} + +Invocation of the template processor on this file produces an +intermediate template file: +\begin{verbatim} +1: GENTRANIN +1: "junk.tem" +1: OUT "#junk.tem"$ +\end{verbatim} +Contents of file {\tt \#junk.tem}: +\begin{framedverbatim} + SUBROUTINE CALC(X,Y,Z,A,B,RES) +;BEGIN; +GENDECS CALC$ +;END; + X=3.75 + Y=-10.2 + Z=16.473 + T0=A**2*X**3+3.0*A**2*X**2*Y + T0=T0+3.0*A**2*X**2*Z+3.0*A**2*X*Y**2 + T0=T0+6.0*A**2*X*Y*Z+3.0*A**2*X*Z**2 + T0=T0+A**2*Y**3+3.0*A**2*Y**2*Z + T0=T0+3.0*A**2*Y*Z**2+A**2*Z**3 + T0=T0+2.0*A*B*X**3+6.0*A*B*X**2*Y + T0=T0+6.0*A*B*X**2*Z+6.0*A*B*X*Y**2 + T0=T0+12.0*A*B*X*Y*Z+6.0*A*B*X*Z**2 + T0=T0+2.0*A*B*Y**3+6.0*A*B*Y**2*Z + T0=T0+6.0*A*B*Y*Z**2+2.0*A*B*Z**3 + T0=T0+B**2*X**3+3.0*B**2*X**2*Y + T0=T0+3.0*B**2*X**2*Z+3.0*B**2*X*Y**2 + T0=T0+6.0*B**2*X*Y*Z+3.0*B**2*X*Z**2 + T0=T0+B**2*Y**3+3.0*B**2*Y**2*Z + RES=T0+3.0*B**2*Y*Z**2+B**2*Z**3 + RETURN + END +;END; +\end{framedverbatim} +Another pass of the template processor produced the final file of FORTRAN +code: +\begin{verbatim} +2: GENTRANIN +2: "#junk.tem" +2: OUT "junk.f"$ +\end{verbatim} +Contents of file {\tt junk.f}: +\begin{framedverbatim} + SUBROUTINE CALC(X,Y,Z,A,B,RES) + REAL X,Y,Z,A,B,RES,T0 + X=3.75 + Y=-10.2 + Z=16.473 + T0=A**2*X**3+3.0*A**2*X**2*Y + T0=T0+3.0*A**2*X**2*Z+3.0*A**2*X*Y**2 + T0=T0+6.0*A**2*X*Y*Z+3.0*A**2*X*Z**2 + T0=T0+A**2*Y**3+3.0*A**2*Y**2*Z + T0=T0+3.0*A**2*Y*Z**2+A**2*Z**3 + T0=T0+2.0*A*B*X**3+6.0*A*B*X**2*Y + T0=T0+6.0*A*B*X**2*Z+6.0*A*B*X*Y**2 + T0=T0+12.0*A*B*X*Y*Z+6.0*A*B*X*Z**2 + T0=T0+2.0*A*B*Y**3+6.0*A*B*Y**2*Z + T0=T0+6.0*A*B*Y*Z**2+2.0*A*B*Z**3 + T0=T0+B**2*X**3+3.0*B**2*X**2*Y + T0=T0+3.0*B**2*X**2*Z+3.0*B**2*X*Y**2 + T0=T0+6.0*B**2*X*Y*Z+3.0*B**2*X*Z**2 + T0=T0+B**2*Y**3+3.0*B**2*Y**2*Z + RES=T0+3.0*B**2*Y*Z**2+B**2*Z**3 + RETURN + END +\end{framedverbatim} + +\subsection{Referencing Subprogram and Parameter Names} +\index{"!\$n parameters} \index{"!\$0 subprogram name} +In some code generation applications in which template processing is used, +it is useful to be able to reference the names of the parameters +given in the subprogram header. For this reason, the special +symbols {\bf !\$1}, {\bf !\$2},~\dots, {\bf !\${\it n}}, where {\it n} +is the number +of parameters, can be used in computations and code generation commands in +active parts of template files. Each of these symbols will be replaced by +the corresponding parameter name when code is generated. In addition, the +special symbol {\bf !\$0} will be replaced by the subprogram name. This is +useful when FORTRAN or RATFOR functions are being generated. Finally, the +\index{"!\$"!\# in GENTRAN} +special global variable {\bf !\$!\#} is bound to the number of parameters in +the subprogram header. + +\section{Output Redirection}\label{GENTRAN:output} +\index{GENTRAN ! file output} +Many examples given thus far in this manual have sent all generated code to +the terminal screen. In actual code generation applications, however, +code must be sent to a file which will be compiled at a later +time. This section explains methods of redirecting code to a +file as it is generated. Any number of output files can be open +simultaneously, and generated code can be sent to any combination +of these open files. + +\subsection{File Selection Commands} +\label{file:selection} +\index{OUT command} \index{SHUT command} +REDUCE provides the user with two file handling commands for output +redirection: {\bf OUT} and {\bf SHUT}. The {\bf OUT} command takes a +single file name as argument and directs all REDUCE output to that +file from then on, until another {\bf OUT} changes the output file, or +{\bf SHUT} closes it. Output can go to only one file at a time, +although many can be open. If the file has previously been used for +output during the current job and not {\bf SHUT}, then the new output +is appended onto the end of the file. Any existing file is erased +before its first use for output in a job. To output on the terminal +without closing the output file, the reserved file name {\bf T} (for +terminal) may be used. + +The REDUCE {\bf SHUT} command takes a list of names of files which +have been previously opened via an {\bf OUT} command and closes them. +Most systems require this action by the user before he ends the REDUCE +job; otherwise the output may be lost. If a file is {\bf SHUT} and a +further {\bf OUT} command is issued for the same file, the file is +erased before the new output is written. If it is the current output +file that is {\bf SHUT}, output will switch to the terminal. + +These commands are suitable for most applications in which REDUCE +output must be saved. However, they have two deficiencies when +considered for use in code generation applications. First, they are +inconvenient. {\bf OUT} tells REDUCE to direct {\it all\/} output to +a specified file. Thus in addition to output written as side effects +of functions, returned values are also written to the file (unless the +user is careful to terminate all statements and commands with a {\bf +\$}, in which case only output produced by side effects is written). +If code generation is to be accomplished interactively; i.e., if +algebraic computations and code generation commands are interleaved, +then {\bf OUT} {\it filename\/}{\bf \$} must be issued before every +group of code generation requests, and {\bf OUT T\$} must be issued +after every group. Secondly, the {\bf OUT} command does not allow +output to be sent to two or more files without reissuing the {\bf OUT} +with another file name. In an effort to remove these deficiencies and +make the code generation commands flexible and easy to use, separate +file handling commands are provided by GENTRAN which redirect +generated code {\it only}. + +\index{GENTRANOUT command} \index{GENTRANSHUT command} +The {\bf GENTRANOUT} and {\bf GENTRANSHUT} commands are identical to +the REDUCE {\bf OUT} and {\bf SHUT} commands with the following +exceptions: + +\begin{itemize} +\item {\bf GENTRANOUT} and {\bf GENTRANSHUT} redirect {\it only\/} code which +is printed as a side effect of GENTRAN commands. +\item {\bf GENTRANOUT} allows more than one file name to be given +to indicate that generated code is to be sent to two or more +files. (It is particularly convenient to be able to +have generated code sent to +the terminal screen and one or more file simultaneously.) +\item {\bf GENTRANOUT} does not automatically erase existing files; it prints +a warning message on the terminal and asks the user whether the existing +file should be erased or the whole command be aborted. +\end{itemize} +The next two subsections describe these commands in detail. + +\index{GENTRANOUT command} +\subsubsection{GENTRANOUT} +\begin{describe}{Syntax:} +{\bf GENTRANOUT} {\it f1,f2,\dots\ ,fn;} +\end{describe} +\begin{describe}{Arguments:} +{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each +{\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom} & = & an output file\\ +{\bf T} & = & the terminal\\ +{\bf NIL} & = & the current output file(s)\\ +{\bf ALL!*} & = & all files currently open for output \\ +& & by GENTRAN\\ +\end{tabular} +\end{center} +\end{describe} +\begin{describe}{Side Effects:} +GENTRAN maintains a list of files currently open for output by +GENTRAN {\it only}. {\bf GENTRANOUT} inserts each file name represented by +{\it f1,f2,\dots\ ,fn\/} into that list and opens each one for output. It +also resets the current output file(s) to be all files in {\it f1,f2,\dots\ + ,fn}. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRANOUT} returns the list of files represented by +{\it f1,f2,\dots\ ,fn\/}; +i.e., the current output file(s) after the command has been executed. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** OUTPUT FILE ALREADY EXISTS + OVERWRITE FILE? (Y/N) + +***** WRONG TYPE OF ARG +\end{verbatim} +\end{describe} +\begin{describe}{\example} +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(5,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(.75,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(.7,1.5) {\vector(0,-1){.75}} +\end{picture}} + +\begin{verbatim} +1: GENTRANOUT "f1"; + +"f1" +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(5,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(2.25,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(2.2,1.5) {\vector(0,-1){.75}} +\end{picture}} + +\begin{verbatim} +2: GENTRANOUT "f2"; + +"f2" +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(5,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(3,0) {\framebox(1.5,.75){"f2"}} +\put(3.75,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(3.7,1.5) {\vector(0,-1){.75}} +\end{picture}} + + +\begin{verbatim} +3: GENTRANOUT T,"f3"; + +{T,"f3"} +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(3,0) {\framebox(1.5,.75){"f2"}} +\put(4.5,0) {\framebox(1.5,.75){"f3"}} +\put(5.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(5.25,1.5) {\vector(0,-1){.75}} +\put(5.45,1.5) {\line(-1,0){4.70}} +\put(.75,1.5) {\vector(0,-1){.75}} +\end{picture}} + + +\begin{verbatim} +4: GENTRANOUT "f1"; + +"f1" +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(3,0) {\framebox(1.5,.75){"f2"}} +\put(4.5,0) {\framebox(1.5,.75){"f3"}} +\put(2.25,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(2.2,1.5) {\vector(0,-1){.75}} +\end{picture}} + +\begin{verbatim} +5: GENTRANOUT NIL,"f4"; + +{"f1","f4"} +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(3,0) {\framebox(1.5,.75){"f2"}} +\put(4.5,0) {\framebox(1.5,.75){"f3"}} +\put(6,0) {\framebox(1.5,.75){"f4"}} +\put(7.5,1.5) {\makebox(0,0)[bl]{\tt current-output}} +\put(6.75,1.5) {\vector(0,-1){.75}} +\put(2.25,1.5) {\vector(0,-1){.75}} +\put(7.45,1.5) {\line(-1,0){5.2}} +\end{picture}} + + +\ttindex{ALL"!*} +\begin{verbatim} +6: GENTRANOUT ALL!*; + +{"f1","f2","f3","f4"} +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1.5,.75){T}} +\put(1.5,0) {\framebox(1.5,.75){"f1"}} +\put(3,0) {\framebox(1.5,.75){"f2"}} +\put(4.5,0) {\framebox(1.5,.75){"f3"}} +\put(6,0) {\framebox(1.5,.75){"f4"}} +\put(7.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(6.75,1.5) {\vector(0,-1){.75}} +\put(5.25,1.5) {\vector(0,-1){.75}} +\put(3.75,1.5) {\vector(0,-1){.75}} +\put(2.25,1.5) {\vector(0,-1){.75}} +\put(7.45,1.5) {\line(-1,0){5.2}} +\end{picture}} + +\end{describe} + +\subsubsection{GENTRANSHUT} +\index{GENTRANSHUT command} +\begin{describe}{Syntax:} +{\bf GENTRANSHUT} {\it f1,f2,\dots\ ,fn;\/} +\end{describe} +\begin{describe}{Arguments:} +{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each +{\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom} & = & an output file\\ +{\bf NIL} & = & the current output file(s)\\ +{\bf ALL!*} & = & all files currently open for output \\ +& & by GENTRAN\\ +\end{tabular} +\end{center} +\end{describe} +\begin{describe}{Side Effects:} +{\bf GENTRANSHUT} creates a list of file names from {\it f1,f2,\dots\ ,fn}, +deletes each from the output file list, and closes the +corresponding files. If (all of) the current output file(s) are +closed, then the current output file is reset to the terminal. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRANSHUT} returns the current output file(s) after the command has +been executed. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** FILE NOT OPEN FOR OUTPUT + +***** WRONG TYPE OF ARG +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1,.75){T}} +\put(1,0) {\framebox(1,.75){"f1"}} +\put(2,0) {\framebox(1,.75){"f2"}} +\put(3,0) {\framebox(1,.75){"f3"}} +\put(4,0) {\framebox(1,.75){"f4"}} +\put(5,0) {\framebox(1,.75){"f5"}} +\put(6,0) {\framebox(1,.75){"f6"}} +\put(7,0) {\framebox(1,.75){"f7"}} +\put(2,1.5) {\makebox(0,0) [br]{\tt current-output}} +\put(3.5,1.5) {\vector(0,-1){.75}} +\put(4.5,1.5) {\vector(0,-1){.75}} +\put(7.5,1.5) {\vector(0,-1){.75}} +\put(2.05,1.5) {\line(1,0){5.45}} +\end{picture}} + +\begin{verbatim} +1: GENTRANSHUT "f1","f2","f7"; + +{"f3","f4"} +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1,.75){T}} +\put(1,0) {\framebox(1,.75){"f3"}} +\put(2,0) {\framebox(1,.75){"f4"}} +\put(3,0) {\framebox(1,.75){"f5"}} +\put(4,0) {\framebox(1,.75){"f6"}} +\put(4.5,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(1.5,1.5) {\vector(0,-1){.75}} +\put(2.5,1.5) {\vector(0,-1){.75}} +\put(4.45,1.5) {\line(-1,0){2.95}} +\end{picture}} + +\begin{verbatim} +2: GENTRANSHUT NIL; + +T +\end{verbatim} +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1,.75){T}} +\put(1,0) {\framebox(1,.75){"f5"}} +\put(2,0) {\framebox(1,.75){"f6"}} +\put(.55,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(.5,1.5) {\vector(0,-1){.75}} +\end{picture}} + +\begin{verbatim} +3: GENTRANSHUT ALL!*; + +T +\end{verbatim} + +Output file list: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(1,.75){T}} +\put(.55,1.5) {\makebox(0,0) [bl]{\tt current-output}} +\put(.5,1.5) {\vector(0,-1){.75}} +\end{picture}} + +\end{describe} + +\subsection{The Output File Stack} +Section~\ref{file:selection} +\index{files ! in GENTRAN} +explained the {\bf GENTRANOUT} and {\bf GENTRANSHUT} +commands which are very similar to the REDUCE {\bf OUT} and {\bf SHUT} +commands but redirect {\it only code generated as side effects of GENTRAN +commands\/} to files. This section describes another pair of file +handling commands provided by GENTRAN. + +In some code generation applications it may be convenient to be +able to send generated code to one (set of) file(s), then +temporarily send code to another (set of) file(s), and later +resume sending generated code to the first (set of) file(s). In +other words, it is convenient to think of the output files as +being arranged in a stack which can be pushed whenever new +files are to be written to temporarily, and popped whenever +previously written-to files are to be appended onto. {\bf GENTRANPUSH} +\index{GENTRANPUSH command} \index{GENTRANPOP command} +and {\bf GENTRANPOP} enable the user to manipulate a stack of open +output files in these ways. + +{\bf GENTRANPUSH} simply pushes a (set of) file(s) onto +the stack and opens each one that is not already open for +output. {\bf GENTRANPOP} deletes the top-most occurrence of +the given file(s) from the stack and closes each one that is no +longer in the stack. The stack is initialized to one element: the +terminal. This element is always on the bottom of the stack, and thus, +is the default output file. The current output file is always the +file(s) on top of the stack. + +\subsubsection{GENTRANPUSH} +\index{GENTRANPUSH command} +\begin{describe}{Syntax:} +{\bf GENTRANPUSH} {\it f1,f2,\dots\ ,fn;} +\end{describe} +\begin{describe}{Arguments:} +{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each +{\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom} & = & an output file\\ +{\bf T} & = & the terminal\\ +{\bf NIL} & = & the current output file(s)\\ +{\bf ALL!*} & = & all files currently open for output \\ +& & by GENTRAN\\ +\end{tabular} +\end{center} +\end{describe} +\begin{describe}{Side Effects:} +{\bf GENTRANPUSH} creates a list of file name(s) represented by +{\it f1,f2,\dots\ ,fn\/} and pushes that list onto the output stack. Each file +in the list that is not already open for output is opened at this time. The +current output file is reset to this new element on the top of the stack. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRANPUSH} returns the list of files represented by +{\it f1,f2,\dots\ ,fn\/}; +i.e., the current output file(s) after the command has been executed. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** OUTPUT FILE ALREADY EXISTS + OVERWRITE FILE? (Y/N) + +***** WRONG TYPE OF ARG +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,1)(0,0) +\put(0,0) {\framebox(3,1){}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,.5) {\vector(-1,0){1}} +\put(4.1,.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + + +\begin{verbatim} +1: GENTRANPUSH "f1"; + +"f1" +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,1.5)(0,0) +\put(0,0) {\framebox(3,1.5){}} +\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,1) {\vector(-1,0){1}} +\put(4.1,1) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +2: GENTRANPUSH "f2","f3"; + +{"f2","f3"} +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2)(0,0) +\put(0,0) {\framebox(3,2){}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,1.5) {\vector(-1,0){1}} +\put(4.1,1.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +3: GENTRANPUSH NIL,T; + +{"f2","f3",T} +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2.5)(0,0) +\put(0,0) {\framebox(3,2.5){}} +\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,2) {\vector(-1,0){1}} +\put(4.1,2) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +4: GENTRANPUSH "f1"; + +"f1" +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,3)(0,0) +\put(0,0) {\framebox(3,3){}} +\put(0.25,2.5) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,2.5) {\vector(-1,0){1}} +\put(4.1,2.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +5: GENTRANPUSH ALL!*; + +{"f1","f2","f3"} +\end{verbatim} + +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,3.5)(0,0) +\put(0,0) {\framebox(3,3.5){}} +\put(0.25,3) {\makebox(0,0)[cl]{"f1" "f2" "f3"}} +\put(0.25,2.5) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,2) {\makebox(0,0)[cl]{"f2" "f3" T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f2" "f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,3) {\vector(-1,0){1}} +\put(4.1,3) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\end{describe} + +\subsubsection{GENTRANPOP} +\index{GENTRANPOP command} +\begin{describe}{Syntax:} +{\bf GENTRANPOP} {\it f1,f2,\dots\ ,fn;} +\end{describe} +\begin{describe}{Arguments:} +{\it f1,f2,\dots\ ,fn\/} is a list of one or more {\it f\/}'s, where each +{\it f\/} is one of: +\begin{center} +\begin{tabular}{lll} +{\it an atom} & = & an output file\\ +{\bf T} & = & the terminal\\ +{\bf NIL} & = & the current output file(s)\\ +{\bf ALL!*} & = & all files currently open for output \\ +& & by GENTRAN\\ +\end{tabular} +\end{center} +\end{describe} +\begin{describe}{Side Effects:} +{\bf GENTRANPOP} deletes the top-most occurrence of the single element +containing the file name(s) represented by {\it f1,f2,\dots\ ,fn\/} +from the output stack. Files whose names have been completely removed from +the output stack are closed. The current output file is reset to the +(new) element on the top of the output stack. +\end{describe} +\begin{describe}{Returned Value:} +{\bf GENTRANPOP} returns the current output file(s) after this command +has been executed. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** FILE NOT OPEN FOR OUTPUT + +***** WRONG TYPE OF ARG +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,4)(0,0) +\put(0,0) {\framebox(3,4){}} +\put(0.25,3.5) {\makebox(0,0)[cl]{"f4"}} +\put(0.25,3) {\makebox(0,0)[cl]{"f4" "f2" T}} +\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} +\put(0.25,2) {\makebox(0,0)[cl]{T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,3.5) {\vector(-1,0){1}} +\put(4.1,3.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +1: GENTRANPOP NIL; + +{"f4","f2",T} +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,3.5)(0,0) +\put(0,0) {\framebox(3,3.5){}} +\put(0.25,3) {\makebox(0,0)[cl]{"f4" "f2" T}} +\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} +\put(0.25,2) {\makebox(0,0)[cl]{T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,3) {\vector(-1,0){1}} +\put(4.1,3) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +2: GENTRANPOP NIL; + +"f4" +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,3)(0,0) +\put(0,0) {\framebox(3,3){}} +\put(0.25,2.5) {\makebox(0,0)[cl]{"f4"}} +\put(0.25,2) {\makebox(0,0)[cl]{T}} +\put(0.25,1.5) {\makebox(0,0)[cl]{"f3"}} +\put(0.25,1) {\makebox(0,0)[cl]{"f2" "f1"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,2.5) {\vector(-1,0){1}} +\put(4.1,2.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +3: GENTRANPOP "f2","f1"; + +"f4" +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,2.5)(0,0) +\put(0,0) {\framebox(3,2.5){}} +\put(0.25,2) {\makebox(0,0)[cl]{"f4"}} +\put(0.25,1.5) {\makebox(0,0)[cl]{T}} +\put(0.25,1) {\makebox(0,0)[cl]{"f3"}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,2) {\vector(-1,0){1}} +\put(4.1,2) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\begin{verbatim} +4: GENTRANPOP ALL!*; + +T +\end{verbatim} +Output stack: + +{\setlength{\unitlength}{1cm} +\begin{picture}(10,1)(0,0) +\put(0,0) {\framebox(3,1){}} +\put(0.25,.5) {\makebox(0,0)[cl]{T}} +\put(4,.5) {\vector(-1,0){1}} +\put(4.1,.5) {\makebox(0,0)[cl]{\tt current-output}} +\end{picture}} + +\end{describe} + +\subsection{Temporary Output Redirection} +Sections~\ref{translation} and ~\ref{templates} +explain how to use the code generation and +template processing commands. The syntax for these two commands +is: +\index{output redirection (temporary)} +\index{GENTRAN command} \index{GENTRANIN command} + +\begin{tabular}{lll} +&\multicolumn{2}{l}{{\bf GENTRAN} {\it stmt\/} [{\bf OUT} {\it f1,f2,\dots\ + ,fn\/}]{\it ;}}\\ +&&and\\ +&\multicolumn{2}{l}{{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm\/} [{\bf OUT} + {\it f1,f2,\dots\ ,fn\/}]{\it ;}}\\ +\end{tabular} + +The optional parts of these two commands can be used for {\it temporary} +output redirection; they can be used when the current output +file is to be temporarily reset, for this command only. + +Thus the following two sequences of commands are equivalent: +\begin{verbatim} +10: GENTRANPUSH "f1",T$ + +11: GENTRAN ... $ + +12: GENTRANPOP NIL$ +\end{verbatim} + +and + +\begin{verbatim} +10: GENTRAN +10: ... +10: OUT "f1",T$ +\end{verbatim} + +\section{Modification of the Code Generation Process}\label{GENTRAN:mod} + +GENTRAN is designed to be flexible enough to be used in a variety of +code generation applications. For this reason, several mode +switches and variables are provided to enable the user to tailor the +code generation process to meet his or her particular needs. + +\subsection{Mode Switches} +\index{GENTRAN package ! switches} +The following GENTRAN mode switches can be turned on and off with the +REDUCE {\bf ON} and {\bf OFF} commands. + +\begin{describe}{DOUBLE} +\index{DOUBLE switch} \index{precision} +\begin{itemize} +\item When turned on, causes (where appropriate): +\begin{itemize} +\item floating point numbers to be printed in double precision format; +\item intrinsic functions to be replaced by their double precision +counterparts; +\item generated type declarations to be of double precision form. +\end{itemize} +See also section~\ref{precision} on page~\pageref{precision}. +\item default setting: off +\end{itemize} +\end{describe} + +\begin{describe}{GENDECS} +\index{GENDECS switch} +\begin{itemize} +\item when turned on, allows type declarations to be generated automatically; +otherwise, type information is stored in but not automatically retrieved +from the symbol table. See also sections~\ref{explicit:type} on +page~\pageref{explicit:type}, \ref{more:type} on page~\pageref{more:type}, +and \ref{template:type} on page~\pageref{template:type}. +\item default setting: on +\end{itemize} +\end{describe} + +\begin{describe}{GENTRANOPT} +\index{GENTRANOPT switch} +\begin{itemize} +\item when turned on, replaces each block of straightline code by +an optimized sequence of assignments. +The Code Optimizer takes a sequence of assignments and replaces common +subexpressions with temporary variables. It returns the resulting assignment +statements with common-subexpression-to-temporary-variable assignment +statements preceding them +\item default setting: off +\end{itemize} +\end{describe} + +\begin{describe}{GENTRANSEG} +\index{GENTRANSEG switch} +\begin{itemize} +\item when turned on, checks the print length of expressions and breaks +those expressions that are longer than {\bf MAXEXPPRINTLEN!*} down +\ttindex{MAXEXPPRINTLEN"!*} +into subexpressions which are assigned to temporary variables. +See also section~\ref{segmentation} on page~\pageref{segmentation}. +\item default setting: on +\end{itemize} +\end{describe} + +\begin{describe}{GETDECS} +\index{GETDECS switch} +\begin{itemize} +\item when on, causes: +\begin{itemize} +\item the indices of loops to be declared integer; +\item objects without an explicit type declaration to be declared of the type +given by the variable {\bf DEFTYPE!*}. \ttindex{DEFTYPE"!*} +\end{itemize} +See also section~\ref{implicit:type} on page~\pageref{implicit:type}. +\item default setting: off +\end{itemize} +\end{describe} + +\begin{describe}{KEEPDECS} +\index{KEEPDECS switch} +\begin{itemize} +\item when on, prevents declarations being removed from the symbol table when +type declarations are generated. +\item default: off +\end{itemize} +\end{describe} + +\begin{describe}{MAKECALLS} +\index{MAKECALLS switch} +\begin{itemize} +\item when turned on, causes GENTRAN to translate functional expressions as +subprogram calls. +\item default setting: on +\end{itemize} +\end{describe} + +\begin{describe}{PERIOD} +\index{PERIOD switch} +\begin{itemize} +\item when turned on, causes all integers to be printed out as floating point +numbers except: +\begin{itemize} +\item exponents; +\item variable subscripts; +\item index values in DO-type loops; +\item those which have been declared to be integers. +\end{itemize} +\item default setting: on +\end{itemize} +\end{describe} + + +\subsection{Variables} +\index{GENTRAN package ! variables} +Several global variables are provided in GENTRAN to enable the +user to +\begin{itemize} +\item select the target language +\item control expression segmentation +\item change automatically generated variable names and statement numbers +\item modify the code formatter +\end{itemize} + +The following four subsections describe these variables\footnote{ +Note that when an atomic value (other than an integer) is assigned to a +variable, that value must be quoted. For example, +{\bf GENTRANLANG!* := 'FORTRAN\$} +assigns the atom {\bf FORTRAN} to the variable {\bf GENTRANLANG!*}.}. + +\subsubsection{Target Language Selection} +\begin{describe}{GENTRANLANG!*} +\ttindex{GENTRANLANG"!*} +\begin{itemize} +\item target language (FORTRAN, RATFOR, PASCAL or C) +See also section~\ref{gentranlang} on page~\pageref{gentranlang}. +\item value type: atom +\item default value: FORTRAN +\end{itemize} +\end{describe} + +\subsubsection{Expression Segmentation Control} +\begin{describe}{MAXEXPPRINTLEN!*} +\ttindex{MAXEXPPRINTLEN"!*} +\begin{itemize} +\item value used to determine whether or not an expression should be +segmented; maximum number of characters permitted in an expression +in the target language (excluding spaces printed for formatting). +See also section~\ref{segmentation} on page~\pageref{segmentation}. +\item value type: integer +\item default value: 800 +\end{itemize} +\end{describe} + +\subsubsection{Variable Names \& Statement Numbers} +\begin{describe}{TEMPVARNAME!*} +\ttindex{TEMPVARNAME"!*} +\begin{itemize} +\item name used as prefix in generating temporary variable names. +See also section~\ref{tempvars} on page~\pageref{tempvars}. +\item value type: atom +\item default value: T +\end{itemize} +\end{describe} + +\begin{describe}{TEMPVARNUM!*} +\ttindex{TEMPVARNUM"!*} +\begin{itemize} +\item number appended to {\bf TEMPVARNAME!*} to create a temporary variable +name. If the temporary variable name resulting from appending +{\bf TEMPVARNUM!*} onto {\bf TEMPVARNAME!*} has already been generated +and still holds a useful value, then {\bf TEMPVARNUM!*} is incremented +and temporary variable names are compressed until one is found which +was not previously generated or does not still hold a significant value. +See also section~\ref{tempvars} on page~\pageref{tempvars}. +\item value type: integer +\item default value: 0 +\end{itemize} +\end{describe} + +\begin{describe}{TEMPVARTYPE!*} +\ttindex{TEMPVARTYPE"!*} +\begin{itemize} +\item target language variable type (e.g., INTEGER, REAL!*8, FLOAT, etc) used +as a default for automatically generated variables whose type cannot be +determined otherwise. If {\bf TEMPVARTYPE!*} is NIL, then generated +temporary variables whose type cannot be determined are not automatically +declared. See also section~\ref{tempvars} on page~\pageref{tempvars}. +\item value type: atom +\item default value: NIL +\end{itemize} +\end{describe} + +\begin{describe}{GENSTMTNUM!*} +\ttindex{GENSTMTNUM"!*} +\begin{itemize} +\item number used when a statement number must be generated +\item value type: integer +\item default value: 25000 +\end{itemize} +\end{describe} + +\begin{describe}{GENSTMTINCR!*} +\ttindex{GENSTMTINCR"!*} +\begin{itemize} +\item number by which {\bf GENSTMTNUM!*} is increased each time a new +statement number is generated. +\item value type: integer +\item default value: 1 +\end{itemize} +\end{describe} + +\begin{describe}{DEFTYPE!*} +\ttindex{DEFTYPE"!*} +\begin{itemize} +\item default type for objects when the switch {\bf GETDECS} is on. See also +section~\ref{implicit:type} on page~\pageref{implicit:type}. +\item value type: atom +\item default value: real +\end{itemize} +\end{describe} + +\subsubsection{Code Formatting} +\begin{describe}{FORTCURRIND!*} +\ttindex{FORTCURRIND"!*} +\begin{itemize} +\item number of blank spaces printed at the beginning of each line of +generated FORTRAN code beyond column 6 +\item value type: integer +\item default value: 0 +\end{itemize} +\end{describe} + +\begin{describe}{RATCURRIND!*} +\ttindex{RATCURRIND"!*} +\begin{itemize} +\item number of blank spaces printed at the beginning of each line of +generated RATFOR code. +\item value type: integer +\item default value: 0 +\end{itemize} +\end{describe} + +\begin{describe}{CCURRIND!*} +\ttindex{CCURRIND"!*} +\begin{itemize} +\item number of blank spaces printed at the beginning of each line of +generated C code. +\item value type: integer +\item default value: 0 +\end{itemize} +\end{describe} + +\begin{describe}{PASCCURRIND!*} +\ttindex{PASCCURRIND"!*} +\begin{itemize} +\item number of blank spaces printed at the beginning of each line of +generated PASCAL code. +\item value type: integer +\item default value: 0 +\end{itemize} +\end{describe} + +\begin{describe}{TABLEN!*} +\ttindex{TABLEN"!*} +\begin{itemize} +\item number of blank spaces printed for each new level of indentation. +\item value type: integer +\item default value: 4 +\end{itemize} +\end{describe} + +\begin{describe}{FORTLINELEN!*} +\ttindex{FORTLINELEN"!*} +\begin{itemize} +\item maximum number of characters printed on each line of generated FORTRAN +code. +\item value type: integer +\item default value: 72 +\end{itemize} +\end{describe} + +\begin{describe}{RATLINELEN!*} +\ttindex{RATLINELEN"!*} +\begin{itemize} +\item maximum number of characters printed on each line of generated RATFOR +code. +\item value type: integer +\item default value: 80 +\end{itemize} +\end{describe} + +\begin{describe}{CLINELEN!*} +\ttindex{CLINELEN"!*} +\begin{itemize} +\item maximum number of characters printed on each line of generated C code. +\item value type: integer +\item default value: 80 +\end{itemize} +\end{describe} + +\begin{describe}{PASCLINELEN!*} +\ttindex{PASCLINELEN"!*} +\begin{itemize} +\item maximum number of characters printed on each line of generated PASCAL +code. +\item value type: integer +\item default value: 70 +\end{itemize} +\end{describe} + +\begin{describe}{MINFORTLINELEN!*} +\ttindex{MINFORTLINELEN"!*} +\begin{itemize} +\item minimum number of characters printed on each line of generated FORTRAN +code after indentation. +\item value type: integer +\item default value: 40 +\end{itemize} +\end{describe} + +\begin{describe}{MINRATLINELEN!*} +\ttindex{MINRATLINELEN"!*} +\begin{itemize} +\item minimum number of characters printed on each line of generated RATFOR +code after indentation. +\item value type: integer +\item default value: 40 +\end{itemize} +\end{describe} + +\begin{describe}{MINCLINELEN!*} +\ttindex{MINCLINELEN"!*} +\begin{itemize} +\item minimum number of characters printed on each line of generated C +code after indentation. +\item value type: integer +\item default value: 40 +\end{itemize} +\end{describe} + +\begin{describe}{MINPASCLINELEN!*} +\ttindex{MINPASCLINELEN"!*} +\begin{itemize} +\item minimum number of characters printed on each line of generated PASCAL +code after indentation. +\item value type: integer +\item default value: 40 +\end{itemize} +\end{describe} + +\section{Examples}\label{GENTRAN:examples} +\index{GENTRAN package ! example} + +Short examples have been given throughout this manual to illustrate +usage of the GENTRAN commands. This section gives complete code +generation examples. + +\subsection{Interactive Code Generation} \index{GENTRAN package ! example} +\index{interactive code generation} +Suppose we wish to generate a FORTRAN subprogram which can be used for +\index{Graeffe's Root-Squaring Method} +computing the roots of a polynomial by Graeffe's Root-Squaring Method\footnote{ +This is for instance convenient for ill-conditioned polynomials. More +details are given in {\it Introduction to Numerical Analysis\/} by +C. E. Froberg, Addison-Wesley Publishing Company, 1966.}. This +method states that the roots $x_i$ of a polynomial +$$P_n(x) = \sum_{i=0}^{n}{a_i x^{n-i}} $$ +can be found by constructing the polynomial +$$P^{*}_n\left({x^2}\right) = \left( a_0x^n + a_2x^{n-2} + \dots\right)^2 - +\left( a_1x^{n-1} + a_3x^{n-3} + \dots\right)^2$$ +with roots $x_i^2$ +When read into REDUCE, the following file of REDUCE statements +will place the coefficients of $P^{*}_n$ +into the list B for some user-entered value of n greater than zero. + +Contents of file {\tt graeffe.red}:\footnote{ +In accordance with section~\ref{explicit:type}, +the subscripts of A are I+1 instead of I.} +\begin{framedverbatim} +OPERATOR A$ +Q := FOR I := 0 STEP 2 UNTIL n SUM (A(I+1)*X^(n-I))$ +R := FOR I := 1 STEP 2 UNTIL n-1 SUM (A(I+1)*X^(n-I))$ +P := Q^2 - R^2$ +LET X^2 = Y$ +B := COEFF(P,Y)$ +END$ +\end{framedverbatim} + +Now a numerical subprogram can be generated with assignment +statements for the coefficients of $P^{*}_n$ (now stored in list B in +REDUCE). Since these coefficients are given in terms of the coefficients +of $P_n$ (i.e., operator A in REDUCE), the subprogram will need two +parameters: A and B, each of which must be arrays of size n+1. + +The following REDUCE session will create subroutine GRAEFF for a polynomial +of degree n=10 and write it to file {\tt graeffe.f}: +{\small +\begin{verbatim} +1: n := 10$ + +2: IN "graeffe.red"$ + +3: GENTRANLANG!* := 'FORTRAN$ + +4: ON DOUBLE$ + +5: GENTRAN +5: ( +5: PROCEDURE GRAEFF(A,B); +5: BEGIN +5: DECLARE +5: << +5: GRAEFF : SUBROUTINE; +5: A(11),B(11) : REAL +5: >>; +5: LITERAL +5: "C",CR!*, +5: "C",TAB!*,"GRAEFFE ROOT-SQUARING METHOD TO FIND",CR!*, +5: "C",TAB!*,"ROOTS OF A POLYNOMIAL",CR!*, +5: "C",CR!*; +5: B(1) :=: PART (B,1); +5: B(2) :=: PART (B,2); +5: B(3) :=: PART (B,3); +5: B(4) :=: PART (B,4); +5: B(5) :=: PART (B,5); +5: B(6) :=: PART (B,6); +5: B(7) :=: PART (B,7); +5: B(8) :=: PART (B,8); +5: B(9) :=: PART (B,9); +5: B(10) :=: PART (B,10); +5: B(11) :=: PART (B,11) +5: END +5: ) +5: OUT "graeffe.f"$ +\end{verbatim} +} + +Contents of file {\tt graeffe.f}: +\begin{framedverbatim} + SUBROUTINE GRAEFF(A,B) + DOUBLE PRECISION A(11),B(11) +C +C GRAEFFE ROOT-SQUARING METHOD TO FIND +C ROOTS OF A POLYNOMIAL +C + B(1)=A(11)**2 + B(2)=2.0D0*A(11)*A(9)-A(10)**2 + B(3)=2.0D0*A(11)*A(7)-(2.0D0*A(10)*A(8))+A(9)**2 + B(4)=2.0D0*A(11)*A(5)-(2.0D0*A(10)*A(6))+2.0D0*A(9)*A(7 + . )-A(8)**2 + B(5)=2.0D0*A(11)*A(3)-(2.0D0*A(10)*A(4))+2.0D0*A(9)*A(5 + . )-(2.0D0*A(8)*A(6))+A(7)**2 + B(6)=2.0D0*A(11)*A(1)-(2.0D0*A(10)*A(2))+2.0D0*A(9)*A(3 + . )-(2.0D0*A(8)*A(4))+2.0D0*A(7)*A(5)-A(6)**2 + B(7)=2.0D0*A(9)*A(1)-(2.0D0*A(8)*A(2))+2.0D0*A(7)*A(3)- + . (2.0D0*A(6)*A(4))+A(5)**2 + B(8)=2.0D0*A(7)*A(1)-(2.0D0*A(6)*A(2))+2.0D0*A(5)*A(3)- + . A(4)**2 + B(9)=2.0D0*A(5)*A(1)-(2.0D0*A(4)*A(2))+A(3)**2 + B(10)=2.0D0*A(3)*A(1)-A(2)**2 + B(11)=A(1)**2 + RETURN + END +\end{framedverbatim} + +\subsection{Code Generation, Segmentation \& Temporary Variables} +\index{GENTRAN package ! example} +The following 3 x 3 inertia matrix M was derived in the course of +some research \footnote{For details see: +Bos, A. M. and M. J. L. Tiernego. ``Formula Manipulation in the +Bond Graph Modelling and Simulation of Large Mechanical Systems'', +{\it Journal of the Franklin Institute} , Pergamon Press Ltd., +Vol. 319, No. 1/2, pp. 51-65, January/February 1985.}: +\begin{eqnarray*} +M(1,1) & = & 18*\cos (q_3)*\cos (q_2)*m_{30}*p^2 - \sin ^2(q_3) *j_{30}y + + \sin ^2(q_3) \\ + & & *j_{30}z - 9*\sin ^2(q_3) *m_{30}*p^2 + j_{10}y + j_{30}y + + m_{10}*p^2 + \\ + & & 18*m_{30}*p^2\\ +M(1,2) & = & 9*\cos (q_3)*\cos (q_2)*m_{30}*p^2 - \sin ^2(q_3) *j_{30}y + +\sin ^2(q_3) \\ + & & *j_{30}z - 9*\sin ^2(q_3) *m_{30}*p^2 + j_{30}y + 9* m_{30}*p^2\\ +M(2,1) & = & M(1,2)\\ +M(1,3) & = & - 9*\sin (q_3)*\sin (q_2)*m_{30}*p^2\\ +M(3,1) & = & M(1,3)\\ +M(2,2) & = & - \sin ^2(q_3) *j_{30}y + \sin ^2(q_3) *j_{30}z - + 9*\sin ^2(q_3)*m_{30}*p^2 \\ +& & + j_{30}y + 9*m_{30}*p^2\\ +M(2,3) & = & 0\\ +M(3,2) & = & M(2,3)\\ +M(3,3) & = & 9*m_{30}*p^2 + j_{30}x\\ +\end{eqnarray*} +We know M is symmetric. We wish to generate numerical code +to compute values for M and its inverse matrix. + +\subsubsection{Code Generation} +\label{code:example} +Generating code for matrix M and its inverse matrix is +straightforward. We can simply generate an assignment statement +for each element of M, compute the inverse matrix MIV, and generate +an assignment statement for each element of MIV. Since we +know M is symmetric, we know that MIV will also be symmetric. To +avoid duplicate computations, we will not generate assignments +for elements below the main diagonals of these matrices. Instead, +we will copy elements across the main diagonal by generating +nested loops. The following REDUCE session will write to the file {\tt m1.f}: + +\begin{verbatim} +1: IN "m.red"$ % Initialize M + +2: GENTRANOUT "m1.f"$ + +3: GENTRANLANG!* := 'FORTRAN$ + +4: ON DOUBLE$ + +5: FOR J := 1 : 3 DO +5: FOR K := J : 3 DO +5: GENTRAN M(J,K) ::=: M(J,K)$ + +6: MIV := M^(-1)$ + +7: FOR J := 1 : 3 DO +7: FOR K := J : 3 DO +7: GENTRAN MIV(J,K) ::=: MIV(J,K)$ + +8: GENTRAN +8: FOR J := 1 : 3 DO +8: FOR K := J+1 : 3 DO +8: << +8: M(K,J) := M(J,K); +8: MIV(K,J) := MIV(J,K) +8: >>$ + +9: GENTRANSHUT "m1.f"$ +\end{verbatim} +The contents of {\tt m1.f} are reproduced in~\ref{appc} on page~\pageref{appc}. + +This code was generated with the segmentation facility turned off. However, +most FORTRAN compilers cannot handle statements more than 20 lines +long. The next section shows how to generate segmented assignments. + +\subsubsection{Segmentation} +\label{seg:example} +\index{segmented assignments} +Large arithmetic expressions can be broken into pieces of manageable +size with the expression segmentation facility. The following REDUCE +session will write segmented assignment statements to the +file {\tt m2.f}. Large arithmetic expressions will be broken into +subexpressions of approximately 300 characters in length. + +\begin{verbatim} +1: IN "m.red"$ % Initialize M + +2: GENTRANOUT "m2.f"$ + +3: ON DOUBLE$ + +4: ON GENTRANSEG$ + +5: MAXEXPPRINTLEN!* := 300$ + +6: FOR J := 1 : 3 DO +6: FOR K := J : 3 DO +6: GENTRAN M(J,K) ::=: M(J,K)$ + +7: MIV := M^(-1)$ + +8: FOR J := 1 : 3 DO +8: FOR K := J : 3 DO +8: GENTRAN MIV(J,K) ::=: MIV(J,K)$ + +9: GENTRAN +9: FOR J := 1 : 3 DO +9: FOR K := J+1 : 3 DO +9: << +9: M(K,J) := M(J,K); +9: MIV(K,J) := MIV(J,K) +9: >>$ + +10: GENTRANSHUT "m2.f"$ +\end{verbatim} + +The contents of file {\tt m2.f} are reproduced in~\ref{appc} on +page~\pageref{appc}. + +\subsubsection{Generation of Temporary Variables to Suppress Simplification} +\label{tempvar:example} +We can dramatically improve the efficiency of the code generated +in sections~\ref{code:example} on page~\pageref{code:example} and +\ref{seg:example} on page~\pageref{seg:example} +by replacing expressions by temporary variables before computing the +inverse matrix. This effectively suppresses simplification; these +expressions will not be substituted into later computations. We +will replace each non-zero element of the REDUCE matrix M by a +generated variable name, and generate a numerical assignment statement +to reflect that substitution in the numerical program being generated. + +The following REDUCE session will write to the file {\tt m3.f}: +\begin{verbatim} +1: in "m.red"$ % Initialize M + +2: GENTRANOUT "m3.f"$ + +3: GENTRANLANG!* := 'FORTRAN$ + +4: ON DOUBLE$ + +5: FOR J := 1 : 3 DO +5: FOR K := J : 3 DO +5: GENTRAN M(J,K) ::=: M(J,K)$ + +6: SHARE VAR$ + +7: FOR J := 1 : 3 DO +7: FOR K := J : 3 DO +7: IF M(J,K) NEQ 0 THEN +7: << +7: VAR := TEMPVAR(NIL)$ +7: MARKVAR VAR$ +7: M(J,K) := VAR$ +7: M(K,J) := VAR$ +7: GENTRAN +7: EVAL(VAR) := M(EVAL(J),EVAL(K)) +7: >>$ + +8: COMMENT ** Contents of matrix M: **$ + +9: M; + +[T0 T1 T2] +[ ] +[T1 T3 0 ] +[ ] +[T2 0 T4] + + +10: MIV := M^(-1)$ + +11: FOR J := 1 : 3 DO +11: FOR K := J : 3 DO +11: GENTRAN MIV(J,K) ::=: MIV(J,K)$ + +12: GENTRAN +12: FOR J := 1 : 3 DO +12: FOR K := J+1 : 3 DO +12: << +12: M(K,J) := M(J,K); +12: MIV(K,J) := MIV(J,K) +12: >>$ + +13: GENTRANSHUT "m3.f"$ +\end{verbatim} + +Contents of file {\tt m3.f}: + +\begin{framedverbatim} + M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE + . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 + . +J30Y+J10Y + M(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*DCOS(DBLE( + . Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+J30Y + M(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30) + M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ + . J30Y + M(2,3)=0.0D0 + M(3,3)=9.0D0*P**2*M30+J30X + T0=M(1,1) + T1=M(1,2) + T2=M(1,3) + T3=M(2,2) + T4=M(3,3) + MIV(1,1)=-(T4*T3)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) + MIV(1,2)=(T4*T1)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) + MIV(1,3)=(T2*T3)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) + MIV(2,2)=(-(T4*T0)+T2**2)/(T4*T1**2-(T4*T3*T0)+T2**2* + . T3) + MIV(2,3)=-(T1*T2)/(T4*T1**2-(T4*T3*T0)+T2**2*T3) + MIV(3,3)=(T1**2-(T3*T0))/(T4*T1**2-(T4*T3*T0)+T2**2*T3) + DO 25009 J=1,3 + DO 25010 K=J+1,3 + M(K,J)=M(J,K) + MIV(K,J)=MIV(J,K) +25010 CONTINUE +25009 CONTINUE +\end{framedverbatim} + +\subsection{Template Processing} \index{template processing} +\index{GENTRAN package ! example} \index{Automatic Circuitry Code Generator} +Circuit simulation plays a vital role in computer hardware +development. A recent paper\footnote{Loe, K. F., N. Ohsawa, and E. +Goto. ``Design of an Automatic Circuitry Code Generator (ACCG)'', +{\it RSYMSAC Proceedings}, Wako-shi, Saitama, Japan. 1984.} describes +the design of an Automatic Circuitry Code Generator (ACCG), which +generates circuit simulation programs based on user-supplied circuit +specifications. The actual code generator consists of a series of +REDUCE {\bf WRITE} statements, each of which writes one line of +FORTRAN code. + +This section presents an alternative implementation for the ACCG +which uses GENTRAN's template processor to generate code. Template +processing is a much more natural method of code generation than the +REDUCE {\bf WRITE} statement method. + +First we will put all REDUCE calculations into two files: {\tt rk.red} and +{\tt ham.red}. + +Contents of file {\tt rk.red}:\footnote{ +Line 11 of procedure RUNGEKUTTA was changed from +\begin{center} +{\tt K41 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2);} +\end{center} +as given in (Loe84), to +\begin{center} +{\tt K42 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2);} +\end{center} +} +\begin{framedverbatim} +COMMENT -- RUNGE-KUTTA METHOD --$ +PROCEDURE RUNGEKUTTA(P1, P2, P, Q, TT); +BEGIN +SCALAR K11,K12,K21,K22,K31,K32,K41,K42; +K11 := HH*P1; +K12 := HH*P2; +K21 := HH*SUB(TT=TT+HH/2, P=P+K11/2, Q=Q+K12/2, P1); +K22 := HH*SUB(TT=TT+HH/2, P=P+K11/2, Q=Q+K12/2, P2); +K31 := HH*SUB(TT=TT+HH/2, P=P+K21/2, Q=Q+K22/2, P1); +K32 := HH*SUB(TT=TT+HH/2, P=P+K21/2, Q=Q+K22/2, P2); +K41 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P1); +K42 := HH*SUB(TT=TT+HH, P=P+K31, Q=Q+K32, P2); +PN := P + (K11 + 2*K21 + 2*K31 + K41)/6; +QN := Q + (K12 + 2*K22 + 2*K32 + K42)/6 +END$ +END$ +\end{framedverbatim} + +Contents of file {\tt ham.red}: + +\begin{framedverbatim} +COMMENT -- HAMILTONIAN CALCULATION --$ +DIFQ := DF(H,P)$ +DIFP := -DF(H,Q) - SUB(QDOT=P/M, DF(D,QDOT))$ +RUNGEKUTTA(DIFP, DIFQ, P, Q, TT)$ +END$ +\end{framedverbatim} + +Next we will create a template file with an outline of the target +FORTRAN program and GENTRAN commands. + +Contents of file {\tt runge.tem}: + +\begin{framedverbatim} + PROGRAM RUNGE + IMPLICIT DOUBLE PRECISION (K,M) +C +C INPUT +C + WRITE(6,*) 'INITIAL VALUE OF P' + READ(5,*) P + WRITE(6,*) ' P = ', P + WRITE(6,*) 'INITIAL VALUE OF Q' + READ(5,*) Q + WRITE(6,*) ' Q = ', Q + WRITE(6,*) 'VALUE OF M' + READ(5,*) M + WRITE(6,*) ' M = ', M + WRITE(6,*) 'VALUE OF K0' + READ(5,*) K0 + WRITE(6,*) ' K0 = ', K0 + WRITE(6,*) 'VALUE OF B' + READ(5,*) B + WRITE(6,*) ' B = ', B + WRITE(6,*) 'STEP SIZE OF T' + READ(5,*) HH + WRITE(6,*) ' STEP SIZE OF T = ', HH + WRITE(6,*) 'FINAL VALUE OF T' + READ(5,*) TP + WRITE(6,*) ' FINAL VALUE OF T = ', TP +C +C INITIALIZATION +C + TT=0.0D0 +;BEGIN; + GENTRAN + LITERAL + TAB!*, "WRITE(9,*) ' H = ", EVAL(H), "'", CR!*, + TAB!*, "WRITE(9,*) ' D = ", EVAL(D), "'", CR!*$ +;END; + WRITE(9,901) C +901 FORMAT(' C= ',D20.10) + WRITE(9,910) TT, Q, P +910 FORMAT(' '3D20.10) +C +C LOOP +C +;BEGIN; + GENTRAN + REPEAT + << + PN :=: PN; + Q :=: QN; + P := PN; + TT := TT + HH; + LITERAL + TAB!*, "WRITE(9,910) TT, QQ, P", CR!* + >> + UNTIL TT >= TF$ +;END; + STOP + END +;END; +\end{framedverbatim} + +Now we can generate a circuit simulation program simply by starting +a REDUCE session and following three steps: +\begin{enumerate} +\item Enter circuit specifications. +\item Perform calculations. +\item Call the GENTRAN template processor. +\end{enumerate} +For example, the following REDUCE session will write a simulation +program to the file {\tt runge.f}: +\begin{verbatim} +1: COMMENT -- INPUT --$ + +2: K := 1/(2*M)*P^2$ % kinetic energy + +3: U := K0/2*Q^2$ % potential energy + +4: D := B/2*QDOT$ % dissipating function + +5: H := K + U$ % hamiltonian + +6: COMMENT -- CALCULATIONS --$ + +7: IN "rk.red", "ham.red"$ + +8: COMMENT -- FORTRAN CODE GENERATION --$ + +9: GENTRANLANG!* := 'FORTRAN$ + +10: ON DOUBLE$ + +11: GENTRANIN "runge.tem" OUT "runge.f"$ +\end{verbatim} + +Contents of file {\tt runge.f}: +\begin{framedverbatim} + PROGRAM RUNGE + IMPLICIT DOUBLE PRECISION (K,M) +C +C INPUT +C + WRITE(6,*) 'INITIAL VALUE OF P' + READ(5,*) P + WRITE(6,*) ' P = ', P + WRITE(6,*) 'INITIAL VALUE OF Q' + READ(5,*) Q + WRITE(6,*) ' Q = ', Q + WRITE(6,*) 'VALUE OF M' + READ(5,*) M + WRITE(6,*) ' M = ', M + WRITE(6,*) 'VALUE OF K0' + READ(5,*) K0 + WRITE(6,*) ' K0 = ', K0 + WRITE(6,*) 'VALUE OF B' + READ(5,*) B + WRITE(6,*) ' B = ', B + WRITE(6,*) 'STEP SIZE OF T' + READ(5,*) HH + WRITE(6,*) ' STEP SIZE OF T = ', HH + WRITE(6,*) 'FINAL VALUE OF T' + READ(5,*) TP + WRITE(6,*) ' FINAL VALUE OF T = ', TP +C +C INITIALIZATION +C + TT=0.0D0 + WRITE(9,*) ' H = (M*Q**2*K0+P**2)/(2.0D0*M)' + WRITE(9,*) ' D = (B*QDOT)/2.0D0' + WRITE(9,901) C +901 FORMAT(' C= ',D20.10) + WRITE(9,910) TT, Q, P +910 FORMAT(' '3D20.10) +C +C LOOP +C +25001 CONTINUE + PN=(-(12.0D0*B*M**2*HH)+2.0D0*B*M*K0*HH**3+24.0D0* + . M**2*P-(24.0D0*M**2*Q*K0*HH)-(12.0D0*M*P*K0*HH**2) + . +4.0D0*M*Q*K0**2*HH**3+P*K0**2*HH**4)/(24.0D0*M**2 + . ) + Q=(-(12.0D0*B*M*HH**2)+B*K0*HH**4+48.0D0*M**2*Q+ + . 48.0D0*M*P*HH-(24.0D0*M*Q*K0*HH**2)-(8.0D0*P*K0*HH + . **3)+2.0D0*Q*K0**2*HH**4)/(48.0D0*M**2) + P=PN + TT=TT+HH + WRITE(9,910) TT, QQ, P + IF (.NOT.TT.GE.TF) GOTO 25001 + STOP + END +\end{framedverbatim} + +\section{Symbolic Mode Functions} +\index{symbolic mode ! in GENTRAN} + +Thus far in this manual, commands have been presented which are meant +to be used primarily in the algebraic mode of REDUCE. These commands +are designed to be used interactively. However, many code generation +applications require code to be generated under program control\footnote{ +\cite{vandenHeuvel:86ms} contains one such example.}. In these +applications, it is generally more convenient to generate code from +(computed) prefix forms. Therefore, GENTRAN provides code generation +and file handling functions designed specifically to be used in the +symbolic mode of REDUCE. This section presents the symbolic functions +which are analogous to the code generation, template processing, and +output file handling commands presented in sections \ref{GENTRAN:inter}, + \ref{GENTRAN:template}, and \ref{GENTRAN:output}. + +\subsection{Code Generation and Translation} +Sections~\ref{translation} through \ref{comments} +describe interactive commands and functions which +generate and translate code, declare variables to be of +specific types, and insert literal strings of characters into the +stream of generated code. This section describes analogous symbolic +mode code generation functions. + +\subsubsection{Translation of Prefix Forms} +In algebraic mode, the {\bf GENTRAN} command translates algorithmic +specifications supplied in the form of REDUCE statements into +numerical code. Similarly, the symbolic function {\bf SYM!-GENTRAN} +\index{SYM"!-GENTRAN command} +translates algorithmic specifications supplied in the form of REDUCE +prefix forms into numerical code. + +\begin{describe}{Syntax:} +{\bf SYM!-GENTRAN} {\it form\/}; +\end{describe} +\begin{describe}{Function Type:} +expr +\end{describe} +\begin{describe}{Argument:} +{\it form\/} is any LISP prefix form that evaluates to a +REDUCE prefix form that can be translated by GENTRAN into the target +language\footnote{ +See~\ref{appa} on page~\pageref{appa} for a complete listing of REDUCE +prefix forms that can be translated.}. +{\it form\/} may contain any number of occurrences of the special forms +\ttindex{EVAL} \ttindex{LSETQ} \ttindex{RSETQ} \ttindex{LRSETQ} +\ttindex{DECLARE} \ttindex{LITERAL} +{\bf EVAL}, {\bf LSETQ}, {\bf RSETQ}, {\bf LRSETQ}, {\bf DECLARE}, and +{\bf LITERAL} (see sections~\ref{sym:cg} through \ref{special} on +pages~\pageref{sym:cg}--\pageref{special}). +\end{describe} +\begin{describe}{Side Effects:} +{\bf SYM!-GENTRAN} translates {\it form\/} into formatted code in the target +language and writes it to the file(s) currently selected for output. +\end{describe} +\begin{describe}{Returned Value:} +{\bf SYM!-GENTRAN} returns the name(s) of the file(s) to which code +was written. If code was written to one file, the returned value is an atom; +otherwise, it is a list. +\end{describe} +\begin{describe}{Diagnostic Messages:} +\begin{verbatim} +*** OUTPUT FILE ALREADY EXISTS + + OVERWRITE FILE? (Y/N) + +***** WRONG TYPE OF ARG +\end{verbatim} +{\it exp} +\begin{verbatim} +***** CANNOT BE TRANSLATED +\end{verbatim} +\end{describe} +\begin{describe}{\example}\index{GENTRAN package ! example} +\begin{verbatim} +1: SYMBOLIC$ + +2: GENTRANLANG!* := 'FORTRAN$ + +3: SYM!-GENTRAN '(FOR I (1 1 n) DO (SETQ (V I) 0))$ + + DO 25001 I=1,N + V(I)=0.0 +25001 CONTINUE + +4: GENTRANLANG!* := 'RATFOR$ + +5: SYM!-GENTRAN '(FOR I (1 1 N) DO +5: (FOR J ((PLUS I 1) 1 N) DO +5: (PROGN +5: (SETQ (X J I) (X I J)) +5: (SETQ (Y J I) (Y I J)))))$ + +DO I=1,N + DO J=I+1,N + { + X(J,I)=X(I,J) + Y(J,I)=Y(I,J) + } + +6: GENTRANLANG!* := 'C$ + +7: SYM!-GENTRAN '(SETQ P (FOR I (1 1 N) PRODUCT I))$ + +{ + P=1; + for (I=1;I<=N;++I) + P*=I; +} + +8: GENTRANLANG!* := 'PASCAL$ + +9: SYM!-GENTRAN '(SETQ C +9: (COND ((LESSP A B) A) (T B)))$ +IF A$0.0 DO} &\verb!25004 IF(.NOT.F(N).GT.0.0)!\\ + & &\verb! . GOTO 25005!\\ +&{\bf \ \ \ \ N:=N+1\$} &\verb! N=N+1!\\ +& &\verb! GOTO 25004!\\ +& &\verb!25005 CONTINUE!\\ +& & \\ + repeat &{\bf REPEAT X:=X/2.0} &\verb!25006 CONTINUE!\\ +&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X=X/2.0!\\ +& &\verb! IF(.NOT.F(X).LT.0.0)!\\ +& &\verb! . GOTO 25006!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE Loop structures translatable to FORTRAN} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf FORTRAN CODE} \\ \hline\hline + Conditionals:& &\\ +& &\\ + if &{\bf IF X$>$0.0} &\verb! IF (X.GT.0.0) THEN!\\ +& {\bf \ \ \ \ \ \ \ THEN Y:=X\$} &\verb! Y=X!\\ +& &\verb! ENDIF!\\ +& &\\ + if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb! IF (X.GT.0.0) THEN!\\ +&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X!\\ +& &\verb! ELSE!\\ +& &\verb! Y=-X!\\ +& &\verb! ENDIF!\\ +& & \\\hline + Unconditional& &\\ + Transfer of & &\\ + Control: & &\\ +& &\\ + goto&{\bf GOTO LOOP\$} &\verb! GOTO 25010!\\ +& &\\ + call&{\bf CALCV(V,X,Y,Z)\$} &\verb! CALL CALCV(V,X,Y,Z)!\\ +& &\\ + return &{\bf RETURN X\^{}2\$} &\verb! !{\it + functionname\/}\verb!=X**2!\\ +& &\verb! RETURN!\\ +& & \\\hline +Sequences \& & &\\ +Groups: & &\\ +& &\\ + sequence &{\bf $<$$<$ U:=X\^{}2;}&\verb! U=X**2!\\ +& {\bf \ \ \ \ \ \ \ \ V:=Y\^{}2$>$$>$\$} &\verb! V=Y**2!\\ +& &\\ + group &{\bf BEGIN}&\verb! U=X**2!\\ +&{\bf\ \ \ \ U:=X\^{}2;}&\verb! V=Y**2!\\ +&{\bf\ \ \ \ V:=Y\^{}2} &\\ +&{\bf END\$}&\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE control structures translatable to FORTRAN} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf RATFOR CODE} \\ \hline\hline + +Assignments: & &\\ +& & \\ + simple &{\bf V:=X\^{}2+X\$} &\verb!V=X**2+X!\\ +& & \\ + matrix &{\bf M:=MAT((U,V),(W,X))\$} &\verb!M(1,1)=U!\\ +& &\verb!M(1,2)=V!\\ +& &\verb!M(2,1)=W!\\ +& &\verb!M(2,2)=X!\\ +& & \\ + sum &{\bf S:=FOR I:=1:10} &\verb!S=0.0!\\ +&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb!DO I=1,10!\\ +& &\verb! S=S+V(I)!\\ +& & \\ + product &{\bf P:=FOR I:=2 STEP 2} &\verb!P=1!\\ +&{\bf\ \ \ \ \ \ \ \ UNTIL N} &\verb!DO I=2,N,2!\\ +&{\ \ \ \ PRODUCT I\$} &\verb! P=P*I!\\ +& & \\ +conditional & {\bf X := IF A$<$B THEN} &\verb!IF (A$0.0 DO} &\verb!WHILE(F(N)>0.0)!\\ +&{\bf \ \ \ \ N:=N+1\$} &\verb! N=N+1!\\ +& & \\ + repeat &{\bf REPEAT X:=X/2.0} &\verb!REPEAT!\\ +&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X=X/2.0!\\ +& &\verb!UNTIL(F(X)<0.0)!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to RATFOR} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf RATFOR CODE} \\ \hline\hline + Conditionals:& &\\ +& &\\ + if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!IF(X>0.0)!\\ +& &\verb! Y=X!\\ +& &\\ + if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!IF(X>0.0)!\\ +&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X!\\ +& &\verb!ELSE!\\ +& &\verb! Y=-X!\\ +& & \\\hline + Unconditional& &\\ + Transfer of & &\\ + Control: & &\\ +& &\\ + goto&{\bf GOTO LOOP\$} &\verb!GOTO 25010!\\ +& &\\ + call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALL CALCV(V,X,Y,Z)!\\ +& &\\ + return &{\bf RETURN X\^{}2\$} &\verb!RETURN(X**2)!\\ +& & \\\hline +Sequences \& & &\\ +Groups: & &\\ +& &\\ + sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!U=X**2!\\ +& &\verb!V=Y**2!\\ +& &\\ + group &{\bf BEGIN}&\verb!{!\\ +&{\bf\ \ \ \ U:=X\^{}2;}& \verb! U=X**2!\\ +&{\bf\ \ \ \ V:=Y\^{}2} & \verb! V=Y**2!\\ +&{\bf END\$}&\verb!}!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to RATFOR} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf PASCAL CODE} \\ \hline\hline +Assignments: & &\\ +& & \\ + simple &{\bf V:=X\^{}2+X\$} &\verb!V=X**2+X;!\\ +& & \\ + matrix &{\bf M:=MAT((U,V),} &\verb!BEGIN!\\ +& {\bf \ \ \ \ \ \ \ \ (W,X))\$} &\verb! M(1,1)=U;!\\ +& &\verb! M(1,2)=V;!\\ +& &\verb! M(2,1)=W;!\\ +& &\verb! M(2,2)=X;!\\ +& &\verb!END;!\\ +& & \\ + sum &{\bf S:=FOR I:=1:10} &\verb!BEGIN!\\ +&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb! S=0.0!\\ +& &\verb! FOR I:=1 TO 10 DO!\\ +& &\verb! S:=S+V(I)!\\ +& &\verb!END;!\\ +& & \\ + product &{\bf P:=FOR I:=2:N} &\verb!BEGIN!\\ +&{\bf \ \ \ \ PRODUCT I\$} &\verb! P:=1;!\\ +& &\verb! FOR I:=2 TO N DO!\\ +& &\verb! P:=P*I!\\ +& &\verb!END;!\\ +& & \\ +conditional & {\bf X := IF A$<$B THEN} &\verb!IF (A$0.0 DO} &\verb!WHILE (F(N)>0.0)!\\ +&{\bf \ \ \ \ N:=N+1\$} &\verb! N:=N+1.0;!\\ +& & \\ + repeat &{\bf REPEAT X:=X/2.0} &\verb!REPEAT!\\ +&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X:=X/2.0!\\ +& &\verb!UNTIL F(X)<0.0;!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to PASCAL} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf PASCAL CODE} \\ \hline\hline + Conditionals:& &\\ +& &\\ + if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!IF X>0.0 THEN!\\ +& &\verb! Y:=X;!\\ +& &\\ + if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!IF X>0.0 THEN!\\ +&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y:=X;!\\ +& &\verb!ELSE!\\ +& &\verb! Y:=-X;!\\ +& & \\\hline + Unconditional& &\\ + Transfer of & &\\ + Control: & &\\ +& &\\ + goto&{\bf GOTO LOOP\$} &\verb!GOTO 25010;!\\ +& &\\ + call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALCV(V,X,Y,Z);!\\ +& &\\ + return &{\bf RETURN X\^{}2\$} &{\it functionname\/}\verb!=X**2;!\\ +& &\verb!GOTO 99999{RETURN}!\\ +& &\verb!99999;!\\ +& & \\\hline +Sequences \& & &\\ +Groups: & &\\ +& &\\ + sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!BEGIN!\\ +&&\verb! U:=X**2;!\\ +&&\verb! V:=Y**2!\\ +&&\verb!END;!\\ +& &\\ + group &{\bf BEGIN}&\verb!BEGIN!\\ +&{\bf\ \ \ \ U:=X\^{}2;}&\verb! U:=X**2;!\\ +&{\bf\ \ \ \ V:=Y\^{}2} &\verb! V:=Y**2!\\ +&{\bf END\$}&\verb!END!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to PASCAL} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} + & \multicolumn{1}{c||}{\bf C CODE} \\ \hline\hline +Assignments: & &\\ +& & \\ + simple &{\bf V:=X\^{}2+X\$} &\verb!V=power(X,2)+X;!\\ +& & \\ + matrix &{\bf M:=MAT((U,V),(W,X))\$} &\verb!M[1][1]=U;!\\ +& &\verb!M[1][2]=V;!\\ +& &\verb!M[2][1]=W;!\\ +& &\verb!M[2][2]=X;!\\ +& & \\ + sum &{\bf S:=FOR I:=1:10} &\verb!S=0.0;!\\ +&{\bf\ \ \ \ \ \ SUM V(I)\$} &\verb!for(I=1;I<=10;++I)!\\ +& &\verb! S+=V[I];!\\ +& & \\ + product &{\bf P:=FOR I:=2 STEP 2} &\verb!P=1;!\\ +&{\bf\ \ \ \ \ \ \ \ UNTIL N} &\verb!for(I=2;I<=N;++I)!\\ +&{\ \ \ \ PRODUCT I\$} &\verb! P*=I;!\\ +& & \\ +conditional & {\bf X := IF A$<$B THEN} &\verb!if (A$0.0 DO} &\verb!while(F(N)>0.0)!\\ +&{\bf \ \ \ \ N:=N+1\$} &\verb! N+=1;!\\ +& & \\ + repeat &{\bf REPEAT X:=X/2.0} &\verb!do!\\ +&{\bf \ \ \ \ UNTIL F(X)$<$0.0\$} &\verb! X/=2.0;!\\ +& &\verb!while(F(X)>=0.0);!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to C} +\end{table} + +\begin{table} +\begin{tabular}{||l|l|l||}\hline\hline +\multicolumn{1}{||c|}{\bf TYPE} & \multicolumn{1}{c|}{\bf EXAMPLE} & + \multicolumn{1}{c||}{\bf C CODE} \\ \hline\hline + Conditionals:& &\\ +& &\\ + if &{\bf IF X$>$0.0 THEN Y:=X\$} &\verb!if(X>0.0)!\\ +& &\verb! Y=X;!\\ +& &\\ + if - else &{\bf IF X$>$0.0 THEN Y:=X} &\verb!if(X>0.0)!\\ +&{\bf\ \ \ \ ELSE Y:=-X\$}&\verb! Y=X;!\\ +& &\verb!else!\\ +& &\verb! Y=-X;!\\ +& & \\\hline + Unconditional& &\\ + Transfer of & &\\ + Control: & &\\ +& &\\ + goto&{\bf GOTO LOOP\$} &\verb!goto LOOP;!\\ +& &\\ + call&{\bf CALCV(V,X,Y,Z)\$} &\verb!CALCV(V,X,Y,Z);!\\ +& &\\ + return &{\bf RETURN X\^{}2\$} &\verb!return(power(X,2) );!\\ +& & \\\hline +Sequences \& & &\\ +Groups: & &\\ +& &\\ + sequence &{\bf $<$$<$ U:=X\^{}2;V:=Y\^{}2$>$$>$\$}&\verb!U=power(X,2);!\\ +& &\verb!V=power(Y,2);!\\ +& &\\ + group &{\bf BEGIN}&\verb!{!\\ +&{\bf\ \ \ \ U:=X\^{}2;}& \verb! U=power(x,2);!\\ +&{\bf\ \ \ \ V:=Y\^{}2} & \verb! V=power(Y,2);!\\ +&{\bf END\$}&\verb!}!\\ +& & \\\hline\hline +\end{tabular} +\caption{REDUCE forms translatable to C} +\end{table} + +\subsection{Formal Definition} +The remainder of this section contains a formal definition of all +REDUCE expressions, statements, and prefix forms that can be translated by +GENTRAN into FORTRAN, RATFOR, PASCAL and C code. + +\begin{describe}{Preliminary Definitions} +An {\it id\/} is an identifier. Certain {\it id\/}'s are reserved words +and may not be used as array names or subprogram names. The +complete list appears in the {\it Reserved Words\/} section. + +A {\it string\/} consists of any number of characters (excluding double +quotes) which are enclosed in double quotes. +\end{describe} + +\begin{describe}{Reserved Words}\index{reserved words} +The following reserved words may not be used as array names or +subprogram names\footnote{Note that names of other built-in REDUCE functions +{\it can\/} be translated, but remember that they will be translated +{\it literally\/} unless {\bf EVAL}'d first. For example: +{\bf GENTRAN~DERIV~:=~DF(2*X\^{}2-X-1,~X)\$} +generates {\tt DERIV=DF(2*X**2-X-1,X)} +whereas +{\bf GENTRAN~DERIV~:=:~DF(2*X\^{}2-X-1,~X)\$} +generates {\tt DERIV=4*X-1} }: + +{\bf AND, BLOCK, COND, DIFFERENCE, EQUAL, EXPT, FOR, GEQ, +GO, GREATERP, LEQ, LESSP, MAT, MINUS, NEQ, NOT, OR, +PLUS, PROCEDURE, PROGN, QUOTIENT, RECIP, REPEAT, +RETURN, SETQ, TIMES, WHILE, WRITE} +\end{describe} + +\subsubsection{Translatable REDUCE Expressions and Statements} +\begin{describe}{Expressions} +\begin{tabular}{lll} +\multicolumn{3}{l}{Arithmetic Expressions:} \\ +& & \\ +exp & ::= & {\it number} $\mid$ var $\mid$ funcall $\mid$ - exp $\mid$ +/ exp $\mid$ exp + exp $\mid$ \\ + & & exp - exp $\mid$ exp * exp $\mid$ exp / exp $\mid$ exp ** exp + $\mid$ \\ + & & exp \^{} exp $\mid$ ( exp )\\\\ +& & \\ +var & ::= & {\it id} $\mid$ {\it id} ( exp$_1$, exp$_2$, \dots\ , exp$_n$ ) + $n > 0$ \\ +& & \\ +funcall & ::= & {\it id} ( arg$_1$, arg$_2$, \dots\ , arg$_n$ ) $n \geq 0$ \\ +& & \\ +arg & ::= & exp $\mid$ logexp $\mid$ {\it string} \\ +& &\\ +\multicolumn{3}{l}{Logical Expressions:}\\ +& & \\ +logexp & ::= & {\it T} $\mid$ {\it NIL} $\mid$ var $\mid$ funcall $\mid$ + exp $>$ exp $\mid$ exp $>$= exp $\mid$\\ + & & exp = exp $\mid$ exp {\it NEQ} exp $\mid$ exp $<$ exp $\mid$ \\ + & & exp $<$= exp $\mid$ {\it NOT\/} logexp $\mid$ logexp {\it AND\/} + logexp $\mid$ \\ + & & logexp {\it OR\/} logexp $\mid$ ( logexp )\\ +\end{tabular} +\end{describe} + +\begin{describe}{Operator Precedence} +The following is a list of REDUCE arithmetic and logical +operators in order of decreasing precedence: +\begin{center} +** (or \^{}) / * --- + $<$ $<$= $>$ $>$= NEQ = NOT AND OR +\end{center} + +When unparenthesised expressions are translated which contain +operators whose precedence in REDUCE differs from that in the +target language, parentheses are automatically generated. Thus +the meaning of the original expression is preserved\footnote{ +For example in REDUCE, {\bf NOT~A~=~B} and {\bf NOT~(A~=~B)} +are equivalent, whereas in C, {\bf !~A~==~B} and {\bf (!A)~==~B} +are equivalent. Therefore, {\bf NOT~A~=~B} +is translated into C code which forces the REDUCE precedence rules: +{\bf !(A~==~B)} +}. +\end{describe} +\begin{describe}{Statements} +\begin{tabular}{lll} +stmt & ::= & assign $\mid$ break $\mid$ cond $\mid$ while $\mid$ + repeat $\mid$ for $\mid$ goto $\mid$ label $\mid$ \\ +& & call $\mid$ return $\mid$ stop $\mid$ stmtgp \\ +\end{tabular} + +Assignment Statements: + +\begin{tabular}{llll} +assign & ::= & \multicolumn{2}{l}{var := assign' $\mid$ matassign $\mid$ + cond}\\ +& & & \\ +assign' & ::= & \multicolumn{2}{l}{exp $\mid$ logexp}\\ +& & & \\ +matassign & ::= & {\it id} := {\it MAT\/}(&(exp$_{11}$, \dots\ , exp$_{1m}$),\\ + & & &(exp$_{21}$, \dots\ , exp$_{2m}$ ),\\ + & & & \ \ \ \ \ \ :\\ + & & & \ \ \ \ \ \ :\\ + & & &( exp$_{n1}$, \dots\ , exp$_{nm}$ ) ) $n,m > 0$ \\ +\end{tabular} + +Break Statement: + +break ::= {\it BREAK()} + +Conditional Statements: + +\begin{tabular}{lll} +cond & ::= & {\it IF\/} logexp {\it THEN\/} stmt\\ +& & {\it IF\/} logexp {\it THEN\/} stmt {\it ELSE\/} stmt\\ +\end{tabular} + +Loops: +\index{FOR loop} \index{WHILE loop} \index{REPEAT loop} + +\begin{tabular}{lll} +while & ::= & {\it WHILE\/} logexp {\it DO\/} stmt\\ +& &\\ +repeat & ::= & {\it REPEAT\/} stmt {\it UNTIL\/} logexp\\ +& &\\ +for & ::= & {\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp +{\it DO\/} stmt $\mid$\\ +& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it DO\/} stmt $\mid$\\ +& &{\it FOR\/} var := exp : exp {\it DO\/} stmt $\mid$\\ +& &var := for' $\mid$ \\ +& &\\ +for' & ::= & var := for' $\mid$\\ +& &{\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp {\it SUM\/} exp + $\mid$\\ +& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it SUM\/} exp $\mid$\\ +& &{\it FOR\/} var := exp : exp {\it SUM\/} exp $\mid$\\ +& &{\it FOR\/} var := exp {\it STEP\/} exp {\it UNTIL\/} exp\\ +& & \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ {\it PRODUCT\/} exp $\mid$ \\ +& &{\it FOR\/} var := exp {\it UNTIL\/} exp {\it PRODUCT\/} exp $\mid$\\ +& &{\it FOR\/} var := exp : exp {\it PRODUCT\/} exp\\ +\end{tabular} + +Goto Statement: + +\begin{tabular}{lll} +goto & ::= & {\it GOTO\/} label $\mid$ {\it GO TO\/} label\\ +label & ::= & {\it id\/} :\\ +\end{tabular} + +Subprogram Calls \& Returns \footnote{ Note that return statements can +only be translated from inside of procedure definitions. +\index{LITERAL command} The LITERAL function must be used to generate +a return statement from anywhere else.}: + +\begin{tabular}{lll} +call & ::= & {\it id\/} ( arg$_1$, arg$_2$, \dots\ , arg$_n$ ) $n \geq 0$\\ +& &\\ +return & ::= & {\it RETURN\/} $\mid$ {\it RETURN\/} arg\\ +\end{tabular} + +Stop \& Exit Statements \footnote{ +In certain cases it may be convenient to generate a FORTRAN +STOP statement or a C EXIT statement. Since there is no +semantically equivalent REDUCE statement, STOP() can be used +and will be translated appropriately.}: + +stop ::= {\it STOP\/}() + +Statement Groups \footnote{ +Note that REDUCE BEGIN\dots\ END statement groups are translated +into RATFOR or C \{\dots\ \} statement groups, whereas +REDUCE $<$$<$\dots\ $>$$>$ statement groups are translated into RATFOR or +C statement {\it sequences}. When the target language is FORTRAN, both +types of REDUCE statement groups are translated into statement +sequences.}: + +\begin{tabular}{lll} +stmtgp & ::= & $<$$<$ stmt$_1$ ; stmt$_2$ ; \dots\ ; stmt$_n$ $>$$>$ + $\mid$\\ +& &{\it BEGIN\/} stmt$_1$ ; stmt$_2$ ; \dots\ ; stmt$_n$ {\it END\/} $ n > + 0$\\ +\end{tabular} +\end{describe} +\begin{describe}{Subprogram Definitions} +\begin{tabular}{lll} +defn & ::= & {\it PROCEDURE id\/} ({\it id$_1$, id$_2$, \dots\ , id$_n$\/}) ; + stmt $\mid$\\ +& & {\it PROCEDURE id\/} ({\it id$_1$, id$_2$, \dots\ , id$_n$\/}) ; + exp\ \ \ \ \ \ $n \geq 0$ \\ +\end{tabular} +\end{describe} + +\subsubsection{Translatable REDUCE Prefix Forms} +\begin{describe}{Expressions} + +Arithmetic Expressions: + +\begin{tabular}{lll} +exp & ::= & {\it number\/} $\mid$ funcall $\mid$ var $\mid$ +({\it DIFFERENCE\/} exp exp) $\mid$\\ +& &({\it EXPT\/} exp exp) $\mid$ ({\it MINUS\/} exp) $\mid$ ({\it PLUS\/} + exp exp') $\mid$\\ +& & ({\it QUOTIENT\/} exp exp) $\mid$ ({\it RECIP\/} exp) $\mid$\\ +& & ({\it TIMES\/} exp exp exp') $\mid$ ({\it !*SQ\/} sqform)\\ +\end{tabular} + +where sqform is a standard quotient form equivalent to any acceptable prefix +form. + +exp' ::= exp$_1$ exp$_2$ \dots\ exp$_n$ $n \geq 0$ + +Logical Expressions: + +\begin{tabular}{lll} +logexp & ::= & {\it NIL\/} $\mid$ {\it T\/} $\mid$ funcall $\mid$ var +$\mid$\\ +& & ({\it AND\/} logexp logexp logexp') $\mid$ ({\it EQUAL\/} exp exp) +$\mid$\\ +& & ({\it GEQ\/} exp exp) $\mid$ ({\it GREATERP\/} exp exp) $\mid$ \\ +& & ({\it LEQ\/} exp exp) $\mid$ ({\it LESSP\/} exp exp) $\mid$ \\ +& & ({\it NEQ\/} exp exp) $\mid$ ({\it NOT\/} logexp) $\mid$ \\ +& & ({\it OR\/} logexp logexp logexp')\\ +& &\\ +logexp' & ::= & logexp$_1$ logexp$_2$ \dots\ logexp$_n$ $n \geq 0$\\ +\end{tabular} +\end{describe} + +\begin{describe}{Statements} +\begin{tabular}{lll} +stmt & ::= & assign $\mid$ break $\mid$ call $\mid$ cond $\mid$ +for $\mid$ goto $\mid$\\ +& & label $\mid$ read $\mid$ repeat $\mid$ return $\mid$ stmtgp +$\mid$\\ +& & stop $\mid$ while $\mid$ write \\ +& &\\ +stmt' & ::= & stmt$_1$ stmt$_2$ \dots\ stmt$_n$ $n \geq 0$\\ +\end{tabular} + +Assignment Statements: + +assign ::= ({\it SETQ\/} var exp) $\mid$ ({\it SETQ\/} var logexp) $\mid$ + ({\it SETQ\/} id ({\it MAT\/} list list')) + +Conditional Statements: + +\begin{tabular}{lll} +cond & ::= & ({\it COND\/} (logexp stmt) cond1) \\ +& & \\ +cond1 & ::= & (logexp stmt$_1$) \dots\ (logexp stmt$_n$) $n \geq 0$\\ +\end{tabular} + +Loops: + +\begin{tabular}{lll} +for & ::= & ({\it FOR\/} var (exp exp exp) {\it DO\/} stmt) $\mid$\\ +& & ({\it SETQ\/} var ({\it FOR\/} var (exp exp exp) {\it SUM\/} exp) $\mid$\\ +& & ({\it SETQ\/} var ({\it FOR\/} var (exp exp exp) \\ +& & \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ \ {\it PRODUCT\/} exp)\\ +& &\\ +repeat & ::= & ({\it REPEAT\/} stmt logexp)\\ +& &\\ +while & ::= & ({\it WHILE\/} logexp stmt) +\end{tabular} + +Go To Statements: + +\begin{tabular}{lll} +break & ::= & ({\it BREAK\/})\\ +& & \\ +goto & ::= & ({\it GO\/} label)\\ +& & \\ +label & ::= & {\it id}\\ +\end{tabular} + +Subprogram Calls \& Returns: + +\begin{tabular}{lll} +call & ::= & ({\it id\/} arg')\\ +& &\\ +return & ::= & ({\it RETURN\/}) $\mid$ ({\it RETURN\/} arg)\\ +\end{tabular} + +Stop \& Exit Statements: + +stop ::= ({\it STOP\/}) + +Statement Groups: + +stmtgp ::= ({\it PROGN\/} stmt stmt') $\mid$ ({\it BLOCK\/} (id') stmt') + +I/O Statements: + +\begin{tabular}{lll} +read & ::= & ({\it SETQ\/} var ({\it READ\/}))\\ +& &\\ +write & ::= & ({\it WRITE\/} arg arg')\\ +\end{tabular} + +Subprogram Definitions: + +defn ::= ({\it PROCEDURE id NIL EXPR\/} (id') stmt) + +\end{describe} + +\begin{describe}{Miscellaneous} +\begin{tabular}{lll} +funcall & ::= & ({\it id\/} arg')\\ +& &\\ +var & ::= & {\it id\/} $\mid$ ({\it id\/} exp exp')\\ +& &\\ +arg & ::= & {\it string\/} $\mid$ exp $\mid$ logexp\\ +& &\\ +arg' & ::= & arg$_1$ arg$_2$ \dots\ arg$_n$ $n \geq 0$ \\ +& &\\ +list & ::= & (exp exp')\\ +& &\\ +list' & ::= & list$_1$ list$_2$ \dots\ list$_n$ $n \geq 0$ \\ +& &\\ +id' & ::= & {\it id$_1$ id$_2$} \dots\ {\it id$_n$} $n \geq 0$ \\ +\end{tabular} +\end{describe} + +\section{List of Commands, Switches, \& Variables} +\label{appb} +\begin{describe}{COMMANDS} +\index{GENTRAN command} +{\bf GENTRAN} {\it stmt\/} [{\bf OUT}{\it f1,f2,\dots\ ,fn\/}]{\it ;} + +\index{GENTRANIN command} +{\bf GENTRANIN} {\it f1,f2,\dots\ ,fm\/} [{\bf OUT}{\it f1,f2,\dots\ +,fn\/}]{\it ;} + +\index{GENTRANOUT command} +{\bf GENTRANOUT} {\it f1,f2,\dots\ ,fn;} + +\index{GENTRANSHUT command} +{\bf GENTRANSHUT} {\it f1,f2,\dots\ ,fn;} + +\index{GENTRANPUSH command} +{\bf GENTRANPUSH} {\it f1,f2,\dots\ ,fn;} + +\index{GENTRANPOP command} +{\bf GENTRANPOP} {\it f1,f2,\dots\ ,fn;} +\end{describe} + +\begin{describe}{SPECIAL FUNCTIONS \& OPERATORS} + +\ttindex{EVAL} +{\bf EVAL} {\it exp} + +\index{::=} +{\it var} {\bf ::=} {\it exp;} + +\index{:=:} +{\it var} {\bf :=:} {\it exp;} + +\index{::=:} +{\it var} {\bf ::=:} {\it exp;} + +\ttindex{LSETQ} +{\it var} {\bf LSETQ} {\it exp;} + +\ttindex{RSETQ} +{\it var} {\bf RSETQ} {\it exp;} + +\ttindex{LRSETQ} +{\it var} {\bf LRSETQ} {\it exp;} + +\index{DECLARE function} +{\bf DECLARE} {\it v1,v2,\dots\ ,vn\/}{\bf :} {\it type;} + +\begin{tabular}{ll} +{\bf DECLARE}\\ +{\bf $<$$<$}\\ +&{\it v11,v12,\dots\ ,v1n} {\bf :} {\it type1\/}{\bf ;}\\ +&{\it v12,v22,\dots\ ,v2n} {\bf :} {\it type2\/}{\bf ;}\\ +& \ \ \ :\\ +& \ \ \ :\\ +&{\it vm1,vm2,\dots\ ,vmn} {\bf :} {\it typen\/}{\bf ;}\\ +{\bf $>$$>$}{\it ;} +\end{tabular} + +\ttindex{LITERAL} +{\bf LITERAL} {\it arg1,arg2,\dots\ ,argn;} +\end{describe} + +\begin{describe}{MODE SWITCHES} +{\bf PERIOD} \index{PERIOD switch} + +{\bf GENTRANSEG} \index{GENTRANSEG switch} + +{\bf GENDECS} \index{GENDECS switch} + +{\bf DOUBLE} \index{DOUBLE switch} + +{\bf MAKECALLS} \index{MAKECALLS switch} + +{\bf KEEPDECS} \index{KEEPDECS switch} + +{\bf GETDECS} \index{GETDECS switch} + +\end{describe} + +\begin{describe}{VARIABLES} +{\bf GENTRANLANG!*} \ttindex{GENTRANLANG!*} + +{\bf MAXEXPPRINTLEN!*} \ttindex{MAXEXPPRINTLEN!*} + +{\bf TEMPVARNAME!*} \ttindex{TEMPVARNAME!*} + +{\bf TEMPVARNUM!*} \ttindex{TEMPVARNUM!*} + +{\bf TEMPVARTYPE!*} \ttindex{TEMPVARTYPE!*} + +{\bf GENSTMTNUM!*} \ttindex{GENSTMTNUM!*} + +{\bf GENSTMTINCR!*} \ttindex{GENSTMTINCR!*} + +{\bf TABLEN!*} \ttindex{TABLEN!*} + +{\bf FORTLINELEN!*} \ttindex{FORTLINELEN!*} + +{\bf RATLINELEN!*} \ttindex{RATLINELEN!*} + +{\bf CLINELEN!*} \ttindex{CLINELEN!*} + +{\bf PASCLINELEN!*} \ttindex{PASCLINELEN!*} + +{\bf MINFORTLINELEN!*} \ttindex{MINFORTLINELEN!*} + +{\bf MINRATLINELEN!*} \ttindex{MINRATLINELEN!*} + +{\bf MINCLINELEN!*} \ttindex{MINCLINELEN!*} + +{\bf MINPASCLINELEN!*} \ttindex{MINPASCLINELEN!*} + +{\bf DEFTYPE!*} \ttindex{DEFTYPE!*} +\end{describe} + +\begin{describe}{TEMPORARY VARIABLE GENERATION, MARKING \& UNMARKING} +{\bf TEMPVAR} {\it type;} \ttindex{TEMPVAR} + +{\bf MARKVAR} {\it var;} \ttindex{MARKVAR} + +{\bf UNMARKVAR} {\it var;} \ttindex{UNMARKVAR} +\end{describe} + +\begin{describe}{EXPLICIT GENERATION OF TYPE DECLARATIONS} +{\bf GENDECS} {\it subprogname;} \ttindex{GENDECS switch} +\end{describe} + +\begin{describe}{SYMBOLIC MODE FUNCTIONS} +{\bf SYM!-GENTRAN} {\it form;} \index{SYM"!-GENTRAN command} + +{\bf SYM!-GENTRANIN} {\it list-of-fnames;} \index{SYM"!-GENTRANIN command} + +{\bf SYM!-GENTRANOUT} {\it list-of-fnames;} \index{SYM"!-GENTRANOUT command} + +{\bf SYM!-GENTRANSHUT} {\it list-of-fnames;} \index{SYM"!-GENTRANSHUT command} + +{\bf SYM!-GENTRANPUSH} {\it list-of-fnames;} \index{SYM"!-GENTRANPUSH command} + +{\bf SYM!-GENTRANPOP} {\it list-of-fnames;} \index{SYM"!-GENTRANPOP command} +\end{describe} + +\begin{describe}{SYMBOLIC MODE SPECIAL FORMS} +\begin{tabular}{ll} +\ttindex{DECLARE} +{\bf (DECLARE} & {\bf (}{\it type1 v11 v12 \dots\ v1n\/}{\bf )}\\ +& {\bf (}{\it type2 v21 v22 \dots\ v2n\/}{\bf )}\\ +& \ \ \ :\\ +& \ \ \ :\\ +& {\bf (}{\it typen vn1 vn2 \dots\ vnn\/}{\bf ))}\\ +\end{tabular} + +{\bf (LITERAL} {\it arg1 arg2 \dots\ argn\/}{\bf )} \ttindex{LITERAL} + +{\bf (EVAL} {\it exp\/}{\bf )} \ttindex{EVAL} + +{\bf (LSETQ} {\it var exp\/}{\bf )} \ttindex{LSETQ} + +{\bf (RSETQ} {\it var exp\/}{\bf )} \ttindex{RSETQ} + +{\bf (LRSETQ} {\it var exp\/}{\bf )} \ttindex{LRSETQ} +\end{describe} + +\section{The Programs {\tt M1.F} and {\tt M2.F}.} +\label{appc} + +This section contains the two files generated in chapter 6. +Contents of file m1.f: +\begin{framedverbatim} + M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE + . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 + . +J30Y+J10Y + M(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*DCOS(DBLE( + . Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+J30Y + M(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30) + M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ + . J30Y + M(2,3)=0.0D0 + M(3,3)=9.0D0*P**2*M30+J30X + MIV(1,1)=(-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y)+9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2* + . M30*J30X)-(DSIN(DBLE(Q3))**2*J30Y*J30X)+DSIN(DBLE(Q3)) + . **2*J30Z*J30X+81.0D0*P**4*M30**2+9.0D0*P**2*M30*J30Y+ + . 9.0D0*P**2*M30*J30X+J30Y*J30X)/(729.0D0*DSIN(DBLE(Q3)) + . **4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE(Q3 + . ))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0*DSIN( + . DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ + . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* + . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 + . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** + . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* + . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN + . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* + . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( + . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y + . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** + . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) + . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 + . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* + . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P + . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* + . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN + . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 + . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** + . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* + . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* + . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( + . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* + . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( + . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 + . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) + . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* + . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ + . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* + . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* + . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* + . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) + MIV(1,2)=(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Y-(9.0D0*DSIN(DBLE(Q3)) + . **2*P**2*M30*J30Z)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30* + . J30X+DSIN(DBLE(Q3))**2*J30Y*J30X-(DSIN(DBLE(Q3))**2* + . J30Z*J30X)-(81.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4* + . M30**2)-(9.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30* + . J30X)-(81.0D0*P**4*M30**2)-(9.0D0*P**2*M30*J30Y)-( + . 9.0D0*P**2*M30*J30X)-(J30Y*J30X))/(729.0D0*DSIN(DBLE( + . Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE + . (Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0* + . DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ + . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* + . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 + . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** + . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* + . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN + . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* + . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( + . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y + . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** + . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) + . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 + . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* + . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P + . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* + . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN + . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 + . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** + . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* + . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* + . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( + . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* + . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( + . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 + . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) + . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* + . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ + . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* + . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* + . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* + . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) + MIV(1,3)=(-(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P** + . 4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 + . *M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 + . *M30*J30Z+81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**4* + . M30**2+9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30* + . J30Y)/(729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P** + . 6*M30**3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P + . **4*M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2 + . ))**2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4* + . Y*M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2* + . J30Y)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30)+9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-(9.0D0*DSIN(DBLE + . (Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN(DBLE(Q3))**4*P** + . 2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y + . *J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3 + . ))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3))**4*J30Y**2*J30X + . )+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE( + . Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DSIN( + . DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y)-( + . 729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-(81.0D0*DSIN( + . DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN(DBLE(Q3))** + . 2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3))**2*P**4*M30 + . **2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J10Y)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J30X)-(9.0D0*DSIN + . (DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30Y + . *J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30X*J30)+ + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2-(9.0D0*DSIN( + . DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0*DSIN(DBLE(Q3)) + . **2*P**2*M30*J30Z*J10Y+9.0D0*DSIN(DBLE(Q3))**2*P**2* + . M30*J30Z*J30X-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y* + . J30X)-(DSIN(DBLE(Q3))**2*P**2*J30Y*M10*J30X)+DSIN(DBLE + . (Q3))**2*P**2*J30Z*M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y* + . J30X*J30)+DSIN(DBLE(Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3 + . ))**2*J30Y*J10Y*J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X + . -(729.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30 + . **3)-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* + . J30X+J30Y*J10Y*J30X) + MIV(2,2)=(-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2* + . P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+9.0D0*DSIN( + . DBLE(Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*M30*J30X)-(DSIN(DBLE(Q3))**2*Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Z*J30X+162.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2 + . ))*P**4*M30**2+18.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P + . **2*M30*J30X+162.0D0*P**4*M30**2+9.0D0*P**4*M30*M10+ + . 9.0D0*P**2*M30*J30Y+9.0D0*P**2*M30*J10Y+18.0D0*P**2* + . M30*J30X+P**2*M10*J30X+J30Y*J30X+J10Y*J30X)/(729.0D0* + . DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0 + . *DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y- + . (81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30** + . 2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-( + . 81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2* + . Y*M30*J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y + . **2)+9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0 + . *DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3)) + . **4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30 + . )-(DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4* + . J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2 + . ))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE + . (Q2))**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2* + . P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10 + . )-(81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* + . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P + . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* + . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN + . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 + . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** + . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* + . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* + . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( + . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* + . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( + . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 + . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) + . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* + . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ + . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* + . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* + . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* + . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) + MIV(2,3)=(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**4* + . M30**2+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 + . *J30Y-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 + . *J30Z)-(81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*DCOS(DBLE + . (Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3 + . ))*DSIN(DBLE(Q2))*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))* + . DSIN(DBLE(Q2))*P**2*M30*J30Y))/(729.0D0*DSIN(DBLE(Q3)) + . **4*DSIN(DBLE(Q2))**2*P**6*M30**3+81.0D0*DSIN(DBLE(Q3) + . )**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y-(81.0D0*DSIN( + . DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Z)+ + . 81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30**2*J30-(81.0D0* + . DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+9.0D0*DSIN(DBLE(Q3 + . ))**4*P**2*Y*M30*J30Y*J30-(9.0D0*DSIN(DBLE(Q3))**4*P** + . 2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30* + . J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+ + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN + . (DBLE(Q3))**4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y* + . J30Y*J30X*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-( + . DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y + . *J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))** + . 2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2) + . )**2*P**4*M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6 + . *M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0* + . DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P + . **4*M30**2*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30* + . J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN + . (DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3 + . ))**2*P**2*Y*M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P** + . 2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y* + . J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y+9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3))**2*P**2* + . J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10*J30X-( + . DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE(Q3))**2* + . J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y*J30X)+DSIN( + . DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS(DBLE(Q3))**2 + . *DCOS(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DCOS(DBLE(Q3)) + . **2*DCOS(DBLE(Q2))**2*P**4*M30**2*J30X)+729.0D0*P**6* + . M30**3+81.0D0*P**6*M30**2*M10+81.0D0*P**4*M30**2*J30Y+ + . 81.0D0*P**4*M30**2*J10Y+81.0D0*P**4*M30**2*J30X+9.0D0* + . P**4*M30*J30Y*M10+9.0D0*P**4*M30*M10*J30X+9.0D0*P**2* + . M30*J30Y*J10Y+9.0D0*P**2*M30*J30Y*J30X+9.0D0*P**2*M30* + . J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) + MIV(3,3)=(9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30-(9.0D0 + . *DSIN(DBLE(Q3))**4*P**2*M30*J30Y)+DSIN(DBLE(Q3))**4*Y* + . J30Y*J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2)+DSIN(DBLE(Q3))**4*J30Y*J30Z-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **4*M30*M10)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+ + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J10Y)-(DSIN(DBLE(Q3))**2*P**2*J30Y* + . M10)+DSIN(DBLE(Q3))**2*P**2*J30Z*M10-(DSIN(DBLE(Q3))** + . 2*Y*J30Y*J30)+DSIN(DBLE(Q3))**2*J30Y**2-(DSIN(DBLE(Q3) + . )**2*J30Y*J10Y)+DSIN(DBLE(Q3))**2*J30Z*J10Y-(81.0D0* + . DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4*M30**2)+ + . 81.0D0*P**4*M30**2+9.0D0*P**4*M30*M10+9.0D0*P**2*M30* + . J30Y+9.0D0*P**2*M30*J10Y+P**2*J30Y*M10+J30Y*J10Y)/( + . 729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30** + . 3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4*M30 + . **2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P + . **4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y*M30** + . 2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y)+ + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30)+9.0D0*DSIN(DBLE + . (Q3))**4*P**2*Y*M30*J30X*J30-(9.0D0*DSIN(DBLE(Q3))**4* + . P**2*M30*J30Y**2)+9.0D0*DSIN(DBLE(Q3))**4*P**2*M30* + . J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y*J30X) + . +DSIN(DBLE(Q3))**4*Y*J30Y*J30X*J30-(DSIN(DBLE(Q3))**4* + . Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3))**4*J30Y**2*J30X)+DSIN + . (DBLE(Q3))**4*J30Y*J30Z*J30X-(729.0D0*DSIN(DBLE(Q3))** + . 2*DSIN(DBLE(Q2))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3) + . )**2*DSIN(DBLE(Q2))**2*P**4*M30**2*J30Y)-(729.0D0*DSIN + . (DBLE(Q3))**2*P**6*M30**3)-(81.0D0*DSIN(DBLE(Q3))**2*P + . **6*M30**2*M10)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*Y*M30** + . 2*J30)+81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J30Z-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2*J10Y)-(81.0D0* + . DSIN(DBLE(Q3))**2*P**4*M30**2*J30X)-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*J30Y*M10)+9.0D0*DSIN(DBLE(Q3))**2*P** + . 4*M30*J30Z*M10-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*M10* + . J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30Y*J30)-( + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30X*J30)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2-(9.0D0*DSIN(DBLE(Q3 + . ))**2*P**2*M30*J30Y*J10Y)+9.0D0*DSIN(DBLE(Q3))**2*P**2 + . *M30*J30Z*J10Y+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z* + . J30X-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-( + . DSIN(DBLE(Q3))**2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))** + . 2*P**2*J30Z*M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X* + . J30)+DSIN(DBLE(Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2 + . *J30Y*J10Y*J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-( + . 729.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30** + . 3)-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0 + . *P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2 + . *M30*J30Y*J30X+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* + . J30X+J30Y*J10Y*J30X) + DO 25005 J=1,3 + DO 25006 K=J+1,3 + M(K,J)=M(J,K) + MIV(K,J)=MIV(J,K) +25006 CONTINUE +25005 CONTINUE +\end{framedverbatim} + +\newpage + +Contents of file m2.f: +\begin{framedverbatim} + M(1,1)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*Y*J30)+DSIN(DBLE(Q3))**2*J30Z+18.0D0*DCOS(DBLE + . (Q3))*DCOS(DBLE(Q2))*P**2*M30+18.0D0*P**2*M30+P**2*M10 + . +J30Y+J10Y(1,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-( + . DSIN(DBLE(Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0* + . DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30+9.0D0*P**2*M30+ + . J30Y(1,3)=-(9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2* + . M30) + M(2,2)=-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30)-(DSIN(DBLE( + . Q3))**2*J30Y)+DSIN(DBLE(Q3))**2*J30Z+9.0D0*P**2*M30+ + . J30Y + M(2,3)=0.0D0 + M(3,3)=9.0D0*P**2*M30+J30X + T1=-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-(9.0D0*DSIN( + . DBLE(Q3))**2*P**2*M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**2*P + . **2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30X)-( + . DSIN(DBLE(Q3))**2*J30Y*J30X)+DSIN(DBLE(Q3))**2*J30Z* + . J30X+81.0D0*P**4*M30**2+9.0D0*P**2*M30*J30Y+9.0D0*P**2 + . *M30*J30X+J30Y*J30X + T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + ; M30*J30Y*J30X + MIV(1,1)=T1/(T0+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10* + . J30X+J30Y*J10Y*J30X) + T0=81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2+9.0D0*DSIN(DBLE + . (Q3))**2*P**2*M30*J30Y-(9.0D0*DSIN(DBLE(Q3))**2*P**2* + . M30*J30Z)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30X+DSIN( + . DBLE(Q3))**2*J30Y*J30X-(DSIN(DBLE(Q3))**2*J30Z*J30X)-( + . 81.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-( + . 9.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30*J30X)-( + . 81.0D0*P**4*M30**2)-(9.0D0*P**2*M30*J30Y) + T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X + MIV(1,2)=(T0-(9.0D0*P**2*M30*J30X)-(J30Y*J30X))/(T1+ + . 9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+J30Y*J10Y* + . J30X) + T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X + MIV(1,3)=(-(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P** + . 4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 + . *M30*J30Y)+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2 + . *M30*J30Z+81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**4* + . M30**2+9.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*P**2*M30* + . J30Y)/(T0+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+ + . J30Y*J10Y*J30X) + T0=-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2)-(9.0D0* + . DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+9.0D0*DSIN(DBLE(Q3)) + . **2*P**2*M30*J30Z-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30* + . J30X)-(DSIN(DBLE(Q3))**2*Y*J30X*J30)+DSIN(DBLE(Q3))**2 + . *J30Z*J30X+162.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**4* + . M30**2+18.0D0*DCOS(DBLE(Q3))*DCOS(DBLE(Q2))*P**2*M30* + . J30X+162.0D0*P**4*M30**2 + T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X + MIV(2,2)=(T0+9.0D0*P**4*M30*M10+9.0D0*P**2*M30*J30Y+ + . 9.0D0*P**2*M30*J10Y+18.0D0*P**2*M30*J30X+P**2*M10*J30X + . +J30Y*J30X+J10Y*J30X)/(T1+9.0D0*P**2*M30*J10Y*J30X+P** + . 2*J30Y*M10*J30X+J30Y*J10Y*J30X) + T0=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T0=T0+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T0=T0-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T0=T0+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T0=T0-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X + MIV(2,3)=(81.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**4* + . M30**2+9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 + . *J30Y-(9.0D0*DSIN(DBLE(Q3))**3*DSIN(DBLE(Q2))*P**2*M30 + . *J30Z)-(81.0D0*DSIN(DBLE(Q3))*DSIN(DBLE(Q2))*DCOS(DBLE + . (Q3))*DCOS(DBLE(Q2))*P**4*M30**2)-(81.0D0*DSIN(DBLE(Q3 + . ))*DSIN(DBLE(Q2))*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))* + . DSIN(DBLE(Q2))*P**2*M30*J30Y))/(T0+9.0D0*P**2*M30*J10Y + . *J30X+P**2*J30Y*M10*J30X+J30Y*J10Y*J30X) + T0=9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30-(9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y)+DSIN(DBLE(Q3))**4*Y*J30Y* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30)-(DSIN(DBLE(Q3))**4* + . J30Y**2)+DSIN(DBLE(Q3))**4*J30Y*J30Z-(81.0D0*DSIN(DBLE + . (Q3))**2*P**4*M30**2)-(9.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30*M10)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y*M30*J30)+ + . 9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z + T0=T0-(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J10Y)-(DSIN( + . DBLE(Q3))**2*P**2*J30Y*M10)+DSIN(DBLE(Q3))**2*P**2* + . J30Z*M10-(DSIN(DBLE(Q3))**2*Y*J30Y*J30)+DSIN(DBLE(Q3)) + . **2*J30Y**2-(DSIN(DBLE(Q3))**2*J30Y*J10Y)+DSIN(DBLE(Q3 + . ))**2*J30Z*J10Y-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2 + . ))**2*P**4*M30**2)+81.0D0*P**4*M30**2+9.0D0*P**4*M30* + . M10+9.0D0*P**2*M30*J30Y + T1=729.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**6*M30 + . **3+81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y-(81.0D0*DSIN(DBLE(Q3))**4*DSIN(DBLE(Q2))** + . 2*P**4*M30**2*J30Z)+81.0D0*DSIN(DBLE(Q3))**4*P**4*Y* + . M30**2*J30-(81.0D0*DSIN(DBLE(Q3))**4*P**4*M30**2*J30Y) + . +9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Y*J30-(9.0D0* + . DSIN(DBLE(Q3))**4*P**2*Y*M30*J30Z*J30) + T1=T1+9.0D0*DSIN(DBLE(Q3))**4*P**2*Y*M30*J30X*J30-( + . 9.0D0*DSIN(DBLE(Q3))**4*P**2*M30*J30Y**2)+9.0D0*DSIN( + . DBLE(Q3))**4*P**2*M30*J30Y*J30Z-(9.0D0*DSIN(DBLE(Q3)) + . **4*P**2*M30*J30Y*J30X)+DSIN(DBLE(Q3))**4*Y*J30Y*J30X* + . J30-(DSIN(DBLE(Q3))**4*Y*J30Z*J30X*J30)-(DSIN(DBLE(Q3) + . )**4*J30Y**2*J30X)+DSIN(DBLE(Q3))**4*J30Y*J30Z*J30X-( + . 729.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**6*M30** + . 3) + T1=T1-(81.0D0*DSIN(DBLE(Q3))**2*DSIN(DBLE(Q2))**2*P**4* + . M30**2*J30Y)-(729.0D0*DSIN(DBLE(Q3))**2*P**6*M30**3)-( + . 81.0D0*DSIN(DBLE(Q3))**2*P**6*M30**2*M10)-(81.0D0*DSIN + . (DBLE(Q3))**2*P**4*Y*M30**2*J30)+81.0D0*DSIN(DBLE(Q3)) + . **2*P**4*M30**2*J30Z-(81.0D0*DSIN(DBLE(Q3))**2*P**4* + . M30**2*J10Y)-(81.0D0*DSIN(DBLE(Q3))**2*P**4*M30**2* + . J30X) + T1=T1-(9.0D0*DSIN(DBLE(Q3))**2*P**4*M30*J30Y*M10)+9.0D0 + . *DSIN(DBLE(Q3))**2*P**4*M30*J30Z*M10-(9.0D0*DSIN(DBLE( + . Q3))**2*P**4*M30*M10*J30X)-(9.0D0*DSIN(DBLE(Q3))**2*P + . **2*Y*M30*J30Y*J30)-(9.0D0*DSIN(DBLE(Q3))**2*P**2*Y* + . M30*J30X*J30)+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y**2 + . -(9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Y*J10Y)+9.0D0* + . DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J10Y + T1=T1+9.0D0*DSIN(DBLE(Q3))**2*P**2*M30*J30Z*J30X-(9.0D0 + . *DSIN(DBLE(Q3))**2*P**2*M30*J10Y*J30X)-(DSIN(DBLE(Q3)) + . **2*P**2*J30Y*M10*J30X)+DSIN(DBLE(Q3))**2*P**2*J30Z* + . M10*J30X-(DSIN(DBLE(Q3))**2*Y*J30Y*J30X*J30)+DSIN(DBLE + . (Q3))**2*J30Y**2*J30X-(DSIN(DBLE(Q3))**2*J30Y*J10Y* + . J30X)+DSIN(DBLE(Q3))**2*J30Z*J10Y*J30X-(729.0D0*DCOS( + . DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**6*M30**3) + T1=T1-(81.0D0*DCOS(DBLE(Q3))**2*DCOS(DBLE(Q2))**2*P**4* + . M30**2*J30X)+729.0D0*P**6*M30**3+81.0D0*P**6*M30**2* + . M10+81.0D0*P**4*M30**2*J30Y+81.0D0*P**4*M30**2*J10Y+ + . 81.0D0*P**4*M30**2*J30X+9.0D0*P**4*M30*J30Y*M10+9.0D0* + . P**4*M30*M10*J30X+9.0D0*P**2*M30*J30Y*J10Y+9.0D0*P**2* + . M30*J30Y*J30X + MIV(3,3)=(T0+9.0D0*P**2*M30*J10Y+P**2*J30Y*M10+J30Y* + . J10Y)/(T1+9.0D0*P**2*M30*J10Y*J30X+P**2*J30Y*M10*J30X+ + . J30Y*J10Y*J30X) + DO 25007 J=1,3 + DO 25008 K=J+1,3 + M(K,J)=M(J,K) + MIV(K,J)=MIV(J,K) +25008 CONTINUE +25007 CONTINUE +\end{framedverbatim} +\bibliography{gentran} +\bibliographystyle{plain} +\end{document} Index: r36/doc/GHYPER.TEX ================================================================== --- r36/doc/GHYPER.TEX +++ r36/doc/GHYPER.TEX @@ -1,83 +1,83 @@ -\documentstyle[11pt,reduce]{article} -\title{{\tt ghyper}, a package for simplification of \\ -generalized hypergeometric functions} -\date{} -\author{Victor S. Adamchik\\ - Wolfram Research Inc. \\ - former address : \\ - Byelorussian University, Minsk, Byelorussia\\ -\\ -\\ - Present \REDUCE{} form by \\ - Winfried Neun \\ - ZIB Berlin \\ - Email: {\tt Neun@sc.ZIB-Berlin.de}} -\begin{document} -\maketitle - -This note describes the {\tt ghyper} package of \REDUCE{}, which is able -to do simplification of several cases of generalized hypergeometric functions. -The simplifications are performed towards polynomials, elementary or -special functions or simpler hypergeometric functions. -Therefore this package should be used together with the \REDUCE{} -special function package. - -\section{Introduction} - -The (generalized) hypergeometric functions - -\begin{displaymath} -_pF_q \left( {{a_1, \ldots , a_p} \atop {b_1, \ldots ,b_q}} \Bigg\vert z \right) -\end{displaymath} - -are defined in textbooks on special functions, e.g. in -\cite{Prudnikov:90}. Many well-known functions belong to this class, -e.g. exponentials, logarithms, trigonometric functions and Bessel functions. -In \cite{Graham:89} an introduction into the analysis of sums, basic -identities and applications can be found. - -Several hundreds of particular values can be found in \cite{Prudnikov:90}. - -\section{\REDUCE{} operator {\tt hypergeometric}} - -The operator {\tt hypergeometric} expects 3 arguments, namely the -list of upper parameters (which may be empty), the list of lower -parameters (which may be empty too), and the argument, e.g: - -\begin{verbatim} - -hypergeometric ({},{},z); - - Z -E - -hypergeometric ({1/2,1},{3/2},-x^2); - - ATAN(X) ---------- - X -\end{verbatim} - -\section{Enlarging the {\tt hypergeometric} operator} - -Since hundreds of particular cases for the generalized hypergeometric -functions can be found in the literature, one cannot expect that all -cases are known to the {\tt hypergeometric} operator. -Nevertheless the set of special cases can be augmented by adding -rules to the \REDUCE{} system, e.g. - -\begin{verbatim} -let {hypergeometric({1/2,1/2},{3/2},-(~x)^2) => asinh(x)/x}; -\end{verbatim} - -\begin{thebibliography}{9} - -\bibitem{Prudnikov:90} A.~P.~Prudnikov, Yu.~A.~Brychkov, O.~I.~Marichev, -{\em Integrals and Series, Volume 3: More special functions}, -Gordon and Breach Science Publishers (1990). - -\bibitem{Graham:89} R.~L.~Graham, D.~E.~Knuth, O.~Patashnik, -{\em Concrete Mathematics}, Addison-Wesley Publishing Company (1989). - -\end{thebibliography} -\end{document} +\documentstyle[11pt,reduce]{article} +\title{{\tt ghyper}, a package for simplification of \\ +generalized hypergeometric functions} +\date{} +\author{Victor S. Adamchik\\ + Wolfram Research Inc. \\ + former address : \\ + Byelorussian University, Minsk, Byelorussia\\ +\\ +\\ + Present \REDUCE{} form by \\ + Winfried Neun \\ + ZIB Berlin \\ + Email: {\tt Neun@sc.ZIB-Berlin.de}} +\begin{document} +\maketitle + +This note describes the {\tt ghyper} package of \REDUCE{}, which is able +to do simplification of several cases of generalized hypergeometric functions. +The simplifications are performed towards polynomials, elementary or +special functions or simpler hypergeometric functions. +Therefore this package should be used together with the \REDUCE{} +special function package. + +\section{Introduction} + +The (generalized) hypergeometric functions + +\begin{displaymath} +_pF_q \left( {{a_1, \ldots , a_p} \atop {b_1, \ldots ,b_q}} \Bigg\vert z \right) +\end{displaymath} + +are defined in textbooks on special functions, e.g. in +\cite{Prudnikov:90}. Many well-known functions belong to this class, +e.g. exponentials, logarithms, trigonometric functions and Bessel functions. +In \cite{Graham:89} an introduction into the analysis of sums, basic +identities and applications can be found. + +Several hundreds of particular values can be found in \cite{Prudnikov:90}. + +\section{\REDUCE{} operator {\tt hypergeometric}} + +The operator {\tt hypergeometric} expects 3 arguments, namely the +list of upper parameters (which may be empty), the list of lower +parameters (which may be empty too), and the argument, e.g: + +\begin{verbatim} + +hypergeometric ({},{},z); + + Z +E + +hypergeometric ({1/2,1},{3/2},-x^2); + + ATAN(X) +--------- + X +\end{verbatim} + +\section{Enlarging the {\tt hypergeometric} operator} + +Since hundreds of particular cases for the generalized hypergeometric +functions can be found in the literature, one cannot expect that all +cases are known to the {\tt hypergeometric} operator. +Nevertheless the set of special cases can be augmented by adding +rules to the \REDUCE{} system, e.g. + +\begin{verbatim} +let {hypergeometric({1/2,1/2},{3/2},-(~x)^2) => asinh(x)/x}; +\end{verbatim} + +\begin{thebibliography}{9} + +\bibitem{Prudnikov:90} A.~P.~Prudnikov, Yu.~A.~Brychkov, O.~I.~Marichev, +{\em Integrals and Series, Volume 3: More special functions}, +Gordon and Breach Science Publishers (1990). + +\bibitem{Graham:89} R.~L.~Graham, D.~E.~Knuth, O.~Patashnik, +{\em Concrete Mathematics}, Addison-Wesley Publishing Company (1989). + +\end{thebibliography} +\end{document} Index: r36/doc/GROEBNER.BIB ================================================================== --- r36/doc/GROEBNER.BIB +++ r36/doc/GROEBNER.BIB @@ -1,86 +1,86 @@ -% Bibliography for groebner.tex - -@BOOK{BeWei:93, - AUTHOR = "T. Becker and V. Weispfenning", - TITLE = "Groebner Bases", - PUBLISHER = "Springer", YEAR = 1993} - -@ARTICLE{Boege:86, - AUTHOR = "W. Boege and R. Gebauer and H. Kredel", - TITLE = "Some Examples for Solving Systems of Algebraic Equations -by Calculating {Groebner} Bases", - JOURNAL = "J. Symbolic Computation", - YEAR = 1986, VOLUME = 2, NUMBER = 1, PAGES = "83-98", MONTH = "March"} - -@INCOLLECTION{Buchberger:85, - AUTHOR = "B. Buchberger", - TITLE = "Groebner Bases: An Algorithmic Method in Polynomial Ideal Theory", - EDITOR = "N. K. Bose", - BOOKTITLE = "Progress, directions and open problems in multidimensional -systems theory", - PAGES = "184-232", - PUBLISHER = "Dordrecht: Reidel", - YEAR = 1985} - -@INCOLLECTION{Buchberger:88, - AUTHOR = "B. Buchberger", - TITLE = "Applications of {Groebner} Bases in Non-Linear Computational -Geometry", - EDITOR = "R. Janssen", - BOOKTITLE = "Trends in Computer Algebra", - PAGES = "52-80", - PUBLISHER = "Berlin, Heidelberg", YEAR = 1988} - -@BOOK{Davenport:88a, - AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", - TITLE = "Computer Algebra, Systems and Algorithms for Algebraic -Computation", - PUBLISHER = "Academic Press", PRINTING = "2nd", YEAR = 1989} - -@INCOLLECTION{Ebert:81, - AUTHOR = "K. H. Ebert and P. Deuflhard", - EDITOR = "W. Jaeger", - TITLE = "Modelling of Chemical Reaction Systems", - PUBLISHER = "Springer Verlag", - BOOKTITLE = "Springer Ser. Chem. Phys", VOLUME = 18, YEAR = 1981} - -@TECHREPORT{Faugere:89, - AUTHOR = "J. C. Faug{\`e}re and P. Gianni and D. Lazard and T. Mora", - TITLE = "Efficient Computation of Zero-Dimensional {Groebner} Bases by -Change of Ordering", - YEAR = 1989} - -@ARTICLE{Gebauer:88, - AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", - TITLE = "On an Installation of {Buchberger's} Algorithm", - JOURNAL = "J. Symbolic Computation", - YEAR = 1988, VOLUME = 6, NUMBER = "2 and 3", PAGES = "275-286"} - -@ARTICLE{Kredel:88, - AUTHOR = "Heinz Kredel", - TITLE = "Admissible termorderings used in Computer Algebra Systems", - JOURNAL = "{SIGSAM} Bulletin", - YEAR = 1988, VOLUME = 22, NUMBER = 1, PAGES = "28-31", MONTH = "January"} - -@ARTICLE{Kredel:88a, - AUTHOR = "H. Kredel and V. Weispfenning", - TITLE = "Computing Dimension and Independent Sets for - Polynomial Ideals", - JOURNAL = "J. Symbolic Computation", - YEAR = 1988, VOLUME = 6, NUMBER = 1, PAGES = "231-247", MONTH = "November"} - -@TECHREPORT{Melenk:88, - AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", - TITLE = "On {Gr{\"o}bner} Bases Computation on a Supercomputer -Using {REDUCE}", - INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik -Berlin", - YEAR = 1988, TYPE = "Preprint", NUMBER = "SC 88-2", MONTH = "January"} - -@INPROCEEDINGS{Giovini:91, - AUTHOR = "A. Giovini and T. Mora and G. Niesi and L.Robbiano and C. Traverso", - TITLE = "One sugar cube, please OR Selection strategies in the - {Buchberger} algorithm", - BOOKTITLE = "Proc. of {ISSAC} '91", - YEAR = 1991, PAGES = "49-55"} - +% Bibliography for groebner.tex + +@BOOK{BeWei:93, + AUTHOR = "T. Becker and V. Weispfenning", + TITLE = "Groebner Bases", + PUBLISHER = "Springer", YEAR = 1993} + +@ARTICLE{Boege:86, + AUTHOR = "W. Boege and R. Gebauer and H. Kredel", + TITLE = "Some Examples for Solving Systems of Algebraic Equations +by Calculating {Groebner} Bases", + JOURNAL = "J. Symbolic Computation", + YEAR = 1986, VOLUME = 2, NUMBER = 1, PAGES = "83-98", MONTH = "March"} + +@INCOLLECTION{Buchberger:85, + AUTHOR = "B. Buchberger", + TITLE = "Groebner Bases: An Algorithmic Method in Polynomial Ideal Theory", + EDITOR = "N. K. Bose", + BOOKTITLE = "Progress, directions and open problems in multidimensional +systems theory", + PAGES = "184-232", + PUBLISHER = "Dordrecht: Reidel", + YEAR = 1985} + +@INCOLLECTION{Buchberger:88, + AUTHOR = "B. Buchberger", + TITLE = "Applications of {Groebner} Bases in Non-Linear Computational +Geometry", + EDITOR = "R. Janssen", + BOOKTITLE = "Trends in Computer Algebra", + PAGES = "52-80", + PUBLISHER = "Berlin, Heidelberg", YEAR = 1988} + +@BOOK{Davenport:88a, + AUTHOR = "J. H. Davenport and Y. Siret and E. Tournier", + TITLE = "Computer Algebra, Systems and Algorithms for Algebraic +Computation", + PUBLISHER = "Academic Press", PRINTING = "2nd", YEAR = 1989} + +@INCOLLECTION{Ebert:81, + AUTHOR = "K. H. Ebert and P. Deuflhard", + EDITOR = "W. Jaeger", + TITLE = "Modelling of Chemical Reaction Systems", + PUBLISHER = "Springer Verlag", + BOOKTITLE = "Springer Ser. Chem. Phys", VOLUME = 18, YEAR = 1981} + +@TECHREPORT{Faugere:89, + AUTHOR = "J. C. Faug{\`e}re and P. Gianni and D. Lazard and T. Mora", + TITLE = "Efficient Computation of Zero-Dimensional {Groebner} Bases by +Change of Ordering", + YEAR = 1989} + +@ARTICLE{Gebauer:88, + AUTHOR = "R{\"u}diger Gebauer and H. Michael M{\"o}ller", + TITLE = "On an Installation of {Buchberger's} Algorithm", + JOURNAL = "J. Symbolic Computation", + YEAR = 1988, VOLUME = 6, NUMBER = "2 and 3", PAGES = "275-286"} + +@ARTICLE{Kredel:88, + AUTHOR = "Heinz Kredel", + TITLE = "Admissible termorderings used in Computer Algebra Systems", + JOURNAL = "{SIGSAM} Bulletin", + YEAR = 1988, VOLUME = 22, NUMBER = 1, PAGES = "28-31", MONTH = "January"} + +@ARTICLE{Kredel:88a, + AUTHOR = "H. Kredel and V. Weispfenning", + TITLE = "Computing Dimension and Independent Sets for + Polynomial Ideals", + JOURNAL = "J. Symbolic Computation", + YEAR = 1988, VOLUME = 6, NUMBER = 1, PAGES = "231-247", MONTH = "November"} + +@TECHREPORT{Melenk:88, + AUTHOR = "H. Melenk and H. M. M{\"o}ller and W. Neun", + TITLE = "On {Gr{\"o}bner} Bases Computation on a Supercomputer +Using {REDUCE}", + INSTITUTION = "Konrad-Zuse-Zentrum f{\"u}r Informationstechnik +Berlin", + YEAR = 1988, TYPE = "Preprint", NUMBER = "SC 88-2", MONTH = "January"} + +@INPROCEEDINGS{Giovini:91, + AUTHOR = "A. Giovini and T. Mora and G. Niesi and L.Robbiano and C. Traverso", + TITLE = "One sugar cube, please OR Selection strategies in the + {Buchberger} algorithm", + BOOKTITLE = "Proc. of {ISSAC} '91", + YEAR = 1991, PAGES = "49-55"} + Index: r36/doc/GROEBNER.TEX ================================================================== --- r36/doc/GROEBNER.TEX +++ r36/doc/GROEBNER.TEX @@ -1,1546 +1,1546 @@ -\documentstyle[11pt,reduce]{article} -\title{GROEBNER: A Package for Calculating Gr\"obner Bases} -\date{} -\author{ -H. Melenk \& W. Neun \\[0.05in] -Konrad--Zuse--Zentrum \\ -f\"ur Informationstechnik Berlin \\ -Heilbronner Strasse 10 \\ -D--10711 Berlin-Wilmersdorf \\ -Germany \\[0.05in] -Email: melenk@sc.zib--berlin.de \\[0.05in] -and \\[0.05in] -H.M. M\"oller \\[0.05in] -Fernuniversit\"at Hagen \\ -FB Math und Informatik\\ -Postfach 940 \\ -D--58084 Hagen \\ -Germany\\[0.05in] -Email: Michael.Moeller@fernuni-hagen.de} - -\begin{document} -\maketitle - -\index{Gr\"obner Bases} -Gr\"obner bases are a valuable tool for solving problems in -connection with multivariate polynomials, such as solving systems of -algebraic equations and analyzing polynomial ideals. For a definition -of Gr\"obner bases, a survey of possible applications and further -references, see~\cite{Buchberger:85}. Examples are given in \cite{Boege:86}, -in \cite{Buchberger:88} and also in the test file for this package. - -\index{GROEBNER package} \index{Buchberger's Algorithm} -The GROEBNER package calculates Gr\"obner bases using the -Buchberger algorithm. It can be used over a variety of different -coefficient domains, and for different variable and term orderings. - -The current version of the package uses parts of the previous -version, written by R. Gebauer, A.C. Hearn, H. Kredel and M. -M\"oller. The algorithms implemented in the current version are -documented in \cite{Faugere:89}, \cite{Gebauer:88}, -\cite{Kredel:88a} and \cite{Giovini:91}. - -\section{Compatibility} - -Important modifications of the present GROEBNER package compared -with the REDUCE 3.5 GROEBNER package: -\begin{itemize} -\item The variables of the polynomial ring are now declared in the - $TORDER$ statement together with the term order mode. The old - style (including the variable list in the function calls) - is still accepted, but will not be supported in future versions. -\item The term order mode $private$ has been eliminated. Instead the - mode $matrix$ has been introduced, which allows you to - define any compatible term order. For optimal efficiency - a matrix can be compiled. -\item Polynomial side relations in the parameter domain are now - considered inside the Gr\"obner calculations. You can enter - them as ordinary $LET$ rules. -\item There is an extension $NCPOLY$ for computing with - non--commutative ideals of solvable type. $NCPOLY$ is loaded - as a separate module, but it uses internally the functions - of $GROEBNER$. -\end{itemize} - -\section{Background} - -\subsection{Variables, Domains and Polynomials} - -The various functions of the GROEBNER package manipulate -equations and/or polynomials; equations are internally -transformed into polynomials by forming the difference of -left-hand side and right-hand side. - -All manipulations take place in a ring of polynomials in some -variables $x1, \ldots , xn$ over a coefficient domain $D$: -\[ -D [x1,\ldots , xn], -\] -where $D$ is a field or at least a ring without zero divisors. -The set of variables $x1,\ldots ,xn$ can be given explicitly by the -user or it is extracted automatically from the -input expressions. - -All REDUCE kernels can play the role of ``variables'' in this context; -examples are - -%{\small -\begin{verbatim} -X Y Z22 SIN(ALPHA) COS(ALPHA) C(1,2,3) C(1,3,2) FARINA4711 -\end{verbatim} -%} - -The domain $D$ is the current REDUCE domain with those kernels -adjoined that are not members of the list of variables. So the -elements of $D$ may be complicated polynomials themselves over -kernels not in the list of variables; if, however, the variables are -extracted automatically from the input expressions, $D$ is identical -with the current REDUCE domain. It is useful to regard kernels not -being members of the list of variables as ``parameters'', e.g. -\[ -\begin{array}{c} - a * x + (a - b) * y**2 \;\mbox{ with ``variables''}\ \{x,y\} \\ -\mbox{and ``parameters'' $\;a\;$ and $\;b\;$}\;. -\end{array} -\] - -The current version of the Buchberger algorithm has two internal -modes, a field mode and a ring mode. In the starting phase the -algorithm analyzes the domain type; if it recognizes $D$ as being a -ring it uses the ring mode, otherwise the field mode is needed. -Normally field calculations occur only if all coefficients are numbers -and if the current REDUCE domain is a field (e.g. rational numbers, -modular numbers). In general, the ring mode is faster. When no specific -REDUCE domain is selected, the ring mode is used, even if the input -formulas contain fractional coefficients: they are multiplied by their -common denominators so that they become integer polynomials. - - - -\subsection{Term Ordering} \par -In the theory of Gr\"obner bases, the terms of polynomials are -considered as ordered. Several order modes are available in -the current package, including the basic modes: -\index{LEX ! term order} \index{GRADLEX ! term order} -\index{REVGRADLEX ! term order} - -\begin{center} -LEX, GRADLEX, REVGRADLEX -\end{center} - -All orderings are based on an ordering among the variables. For -each pair of variables $(a,b)$ an order relation must be defined, e.g. -``$ a\gg b $''. The greater sign $\gg$ does not represent a numerical -relation among the variables; it can be interpreted only in terms of -formula representation: ``$a$'' will be placed in front of ``$b$'' or -``$a$'' is more complicated than ``$b$''. - -The sequence of variables constitutes this order base. So the notion -of -\[ -\{x1,x2,x3\} -\] - -as a list of variables at the same time means -\[ -x1 \gg x2 \gg x3 -\] -with respect to the term order. - -If terms (products of powers of variables) are compared with LEX, -that term is chosen which has a greater variable or a higher degree -if the greatest variable is the first in both. With GRADLEX the sum of -all exponents (the total degree) is compared first, and if that does -not lead to a decision, the LEX method is taken for the final decision. -The REVGRADLEX method also compares the total degree first, but -afterward it uses the LEX method in the reverse direction; this is the -method originally used by Buchberger. - -\example \ with $\{x,y,z\}$: \index{GROEBNER package ! example} -\[ -\begin{array}{rlll} -\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf LEX:}}\\ - x * y **3 & \gg & y ** 48 & \mbox{(heavier variable)} \\ - x**4 * y**2 & \gg & x**3 * y**10 & \mbox{(higher degree in 1st -variable)} \vspace*{2mm} \\ -\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf GRADLEX:}} \\ - y**3 * z**4 & \gg & x**3 * y**3 & \mbox{(higher total degree)} \\ - x*z & \gg & y**2 & \mbox{(equal total degree)} -\vspace*{2mm}\\ -\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf -REVGRADLEX:}} \\ - y**3 * z**4 & \gg & x**3 * y**3 & \mbox{(higher total degree)} \\ - x*z & \ll & y**2 & \mbox{(equal total degree,} \\ - & & & \mbox{so reverse order of LEX)} -\end{array} -\] - -The formal description of the term order modes is similar to -\cite{Kredel:88}; this description regards only the exponents of a term, -which are written as vectors of integers with $0$ for exponents of a -variable which does not occur: -\[ -\begin{array}{l} - (e) = (e1,\ldots , en) \;\mbox{ representing }\; x1**e1 \ x2**e2 \cdots - xn**en. \\ - \deg(e) \; \mbox{ is the sum over all elements of } \;(e) \\ - (e) \gg (l) \Longleftrightarrow (e)-(l)\gg (0) = (0,\ldots ,0) -\end{array} -\] -\[ -\begin{array}{rll} -\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf LEX:}} \\ - (e) > lex > (0) & \Longrightarrow & e_k > 0 \mbox{ and } e_j =0 -\mbox{ for }\; j=1,\ldots , k-1\vspace*{2mm} \\ -\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf -GRADLEX:}} \\ - (e) >gl> (0) & \Longrightarrow & \deg(e)>0 \mbox { or } (e) >lex> -(0)\vspace*{2mm} \\ -\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf -REVGRADLEX:}}\\ - (e) >rgl> (0) & \Longrightarrow & \deg(e)>0 \mbox{ or }(e) 1$: the vectors with $n$ elements of $R$ -form a $module$ under vector addition (= componentwise addition) -and multiplication with elements of $R$. For a submodule -given by a finite basis a Gr\"obner basis -can be computed, and the facilities of the GROEBNER package -can be used except the operators $GROEBNERF$ and $GROESOLVE$. - -The vectors are encoded using auxiliary variables which represent -the unit vectors in the module. E.g. using ${v_1,v_2,v_3}$ the -module element $[x_1^2,0,x_1-x_2]$ is represented as -$x_1^2 v_1 + x_1 v_3 - x_2 v_3$. The use of ${v_1,v_2,v_3}$ -as unit vectors is set up by assigning the set of auxiliary variables -to the share variable $GMODULE$, e.g. -\begin{verbatim} - GMODULE := {V1,V2,V3}; -\end{verbatim} -After this declaration all monomials built from these variables -are considered as an algebraically independent basis of a vector -space. However, you had best use them only linearly. Once $GMODULE$ -has been set, the auxiliary variables automatically will be -added to the end of each variable list (if they are not yet -member there). -Example: -\begin{verbatim} - torder({x,y,v1,v2,v3},lex)$ - gmodule := {v1,v2,v3}$ - g:=groebner{x^2*v1 + y*v2,x*y*v1 - v3,2y*v1 + y*v3}; - - 2 -G := {X *V1 + Y*V2, - - 2 - X*V3 + Y *V2, - - 3 - Y *V2 - 2*V3, - - 2*Y*V1 + Y*V3} - - preduce((x+y)^3*v1,g); - - 1 3 2 - - X*Y*V2 - ---*Y *V3 - 3*Y *V2 + 3*Y*V3 - 2 - -\end{verbatim} - -In many cases a total degree oriented term order will be adequate -for computations in modules, e.g. for all cases where the -submodule membership is investigated. However, arranging -the auxiliary variables in an elimination oriented term order -can give interesting results. E.g. -\begin{verbatim} - p1:=(x-1)*(x^2-x+3)$ p2:=(x-1)*(x^2+x-5)$ - gmodule := {v1,v2,v3}; - torder({v1,x,v2,v3},lex)$ - gb:=groebner {p1*v1+v2,p2*v1+v3}; - -GB := {30*V1*X - 30*V1 + X*V2 - X*V3 + 5*V2 - 3*V3, - - 2 2 - X *V2 - X *V3 + X*V2 + X*V3 - 5*V2 - 3*V3} - - g:=coeffn(first gb,v1,1); - -G := 30*(X - 1) - - c1:=coeffn(first gb,v2,1); - -C1 := X + 5 - - c2:=coeffn(first gb,v3,1); - -C2 := - X - 3 - - c1*p1 + c2*p2; - -30*(X - 1) - -\end{verbatim} -Here two polynomials -are entered as vectors $[p_1,1,0]$ and $[p_2,0,1]$. Using a term -ordering such that the first dimension ranges highest and the -other components lowest, a classical cofactor computation is -executed just as in the extended Euclidean algorithm. -Consequently the leading polynomial in the resulting -basis shows the greatest common divisor of $p_1$ and $p_2$, -found as a coefficient of $v_1$ while the coefficients -of $v_2$ and $v_3$ are the cofactors $c_1$ and $c_2$ of the polynomials -$p_1$ and $p_2$ with the relation $gcd(p_1,p_2) = c_1p_1 + c_2p_2$. - - -\subsection{Additional Orderings} -Besides the basic orderings, there are ordering options that are used for -special purposes. - -\subsubsection{Separating the Variables into Groups } -\index{grouped ordering} -It is often desirable to separate variables -and formal parameters in a system of polynomials. -This can be done with a {\it lex} Gr\"obner -basis. That however may be hard to compute as it does more -separation than necessary. The following orderings group the -variables into two (or more) sets, where inside each set a classical -ordering acts, while the sets are handled via their total degrees, -which are compared in elimination style. So the Gr\"obner basis will -eliminate the members of the first set, if algebraically possible. -{\it Torder} here gets an additional parameter which describe the -grouping \ttindex{TORDER} -\begin{center}{\it -\begin{tabular}{l} -TORDER ($vl$,gradlexgradlex, $n$) \\ -TORDER ($vl$,gradlexrevgradlex,$n$) \\ -TORDER ($vl$,lexgradlex, $n$) \\ -TORDER ($vl$,lexrevgradlex, $n$) -\end{tabular}} -\end{center} -Here the integer $n$ is the number of variables in the first group -and the names combine the local ordering for the first and second -group, e.g. -\begin{center} -\begin{tabular}{llll} -\multicolumn{4}{l}{{\it lexgradlex}, 3 for $\{x_1,x_2,x_3,x_4,x_5\}$:} \\ -\multicolumn{4}{l}{$x_1^{i_1}\ldots x_5^{i_5} \gg x_1^{j_1}\ldots -x_5^{j_5}$} \\ -if & & & $(i_1,i_2,i_3) \gg_{lex}(j_1,j_2,j_3)$ \\ -& or & & $(i_1,i_2,i_3) = (j_1,j_2,j_3)$ \\ -& & and & $(i_4,i_5) \gg_{gradlex}(j_4,j_5)$ -\end{tabular} -\end{center} -Note that in the second place there is no {\it lex} ordering available; -that would not make sense. - -\subsubsection{Weighted Ordering} -\ttindex{TORDER} \index{weighted ordering} -The statement -\begin{center} -\begin{tabular}{cl} -{\it TORDER} &($vl$,weighted, $\{n_1,n_2,n_3 \ldots$\}) ; \\ -\end{tabular} -\end{center} -establishes a graduated ordering, where the exponents are first -multiplied by the given weights. If there are less weight values than -variables, the weight 1 is added automatically. If the weighted -degree calculation is not decidable, a $lex$ comparison follows. - -\subsubsection{Graded Ordering} -\ttindex{TORDER} \index{graded ordering} -The statement -\begin{center} -\begin{tabular}{cl} -{\it TORDER} &($vl$,graded, $\{n_1,n_2,n_3 \ldots\}$,$order_2$) ; \\ -\end{tabular} -\end{center} -establishes a graduated ordering, where the exponents are first -multiplied by the given weights. If there are less weight values than -variables, the weight 1 is added automatically. If the weighted -degree calculation is not decidable, the term order $order_2$ specified -in the following argument(s) is used. The ordering $graded$ is designed -primarily for use with the operator $dd\_groebner$. - - -\subsubsection{Matrix Ordering} -\ttindex{TORDER} \index{matrix ordering} -The statement -\begin{center} -\begin{tabular}{cl} -{\it TORDER} &($vl$,matrix, $M$) ; \\ -\end{tabular} -\end{center} -where $M$ is a matrix with integer elements and row length which -corresponds to the variable number. The exponents of each monomial -form a vector; two monomials are compared by multiplying their -exponent vectors first with $M$ and comparing the resulting vector -lexicographically. E.g. the unit matrix establishes the classical -$LEX$ term order mode, a matrix with a first row of ones followed -by the rows of a unit matrix corresponds to the $GRADLEX$ ordering. - -The matrix $M$ must have at least as many rows as columns; a non--square -matrix contains redundant rows. The matrix must have full rank, and -the top non--zero element of each column must be positive. - -The generality of the matrix based term order has its price: the -computing time spent in the term sorting is significantly higher -than with the specialized term orders. To overcome this problem, -you can compile a matrix term order -if your REDUCE is equipped with a LISP compiler; the -compilation reduces the computing time overhead significantly. -If you set the switch $COMP$ on, any new order matrix is compiled -when any operator of the GROEBNER package accesses it for the -first time. Alternatively you can compile a matrix explicitly -\begin{verbatim} - torder_compile(,); -\end{verbatim} -where $$ is a name (an identifier) and $$ is a term order matrix. -$torder\_compile$ transforms the matrix into a LISP program, which -is compiled by the LISP compiler when $COMP$ is on or when you -generate a fast loadable module. Later you can activate the new term -order by using the name $$ in a $torder$ statement as term ordering -mode. - -\subsection{Gr\"obner Bases for Graded Homogeneous Systems} - -For a homogeneous system of polynomials under a term order -{\it graded}, {\it gradlex}, {\it revgradlex} or {\it weighted} -a Gr\"obner Base can be computed with limiting the grade -of the intermediate $S$--polynomials: -\begin{description} -\ttindex{dd\_groebner} -\item [{\it dd\_groebner}]($d1$,$d2$,$\{p_1,p_2,\ldots\}$); -\end{description} -where $d1$ is a non--negative integer and $d2$ is an integer -$>$ $d1$ or ``infinity". A pair of polynomials is considered -only if the grade of the lcm of their head terms is between -$d1$ and $d2$. See \cite{BeWei:93} for the mathematical background. -For the term orders {\it graded} or {\it weighted} the (first) weight -vector is used for the grade computation. Otherwise the total -degree of a term is used. - -\section{Ideal Decomposition \& Equation System Solving} -Based on the elementary Gr\"obner operations, the GROEBNER package offers -additional operators, which allow the decomposition of an ideal or of a -system of equations down to the individual solutions. -% Section 4.1 -\subsection{Solutions Based on Lex Type Gr\"obner Bases} -% Subsection 4.1.1 -\subsubsection{GROESOLVE: Solution of a Set of Polynomial Equations} -\ttindex{GROESOLVE} \ttindex{GROEBNERF} -The GROESOLVE operator incorporates a macro algorithm; -lexical Gr\"obner bases are computed by GROEBNERF and decomposed -into simpler ones by ideal decomposition techniques; if algebraically -possible, the problem is reduced to univariate polynomials which are -solved by SOLVE; if ROUNDED is on, numerical approximations are -computed for the roots of the univariate polynomials. -\[ - GROESOLVE(\{exp1, exp2, \ldots , expm\}[,\{var1, var2, \ldots , -varn\}]); \] -where $\{exp1, exp2,\ldots , expm\}$ is a list of any number of -expressions or equations, $\{var1, var2, \ldots , varn\}$ is an -optional list of variables. - -The result is a set of subsets. The subsets contain the solutions of the -polynomial equations. If there are only finitely many solutions, -then each subset is a set of expressions of triangular type -$\{exp1, exp2,\ldots , expn\},$ where $exp1$ depends only on -$var1,$ $exp2$ depends only on $var1$ and $var2$ etc. until $expn$ which -depends on $var1,\ldots,varn.$ This allows a successive determination of -the solution components. If there are infinitely many solutions, -some subsets consist in less than $n$ expressions. By considering some -of the variables as ``free parameters'', these subsets are usually -again of triangular type. - - -\example (intersections of a line with a circle): -\index{GROEBNER package ! example} - -\[ -GROESOLVE(\{x**2 - y**2 - a, p*x+q*y+s\},\{x,y\}); -\] -%{\small -\begin{verbatim} - 2 2 2 2 2 - {{X=(SQRT( - A*P + A*Q + S )*Q - P*S)/(P - Q ), - 2 2 2 2 2 - Y= - (SQRT( - A*P + A*Q + S )*P - Q*S)/(P - Q )}, - 2 2 2 2 2 - {X= - (SQRT( - A*P + A*Q + S )*Q + P*S)/(P - Q ), - 2 2 2 2 2 - Y=(SQRT( - A*P + A*Q + S )*P + Q*S)/(P - Q )}} -\end{verbatim} -%} -% Subsection 4.1.2 -\subsubsection{GROEPOSTPROC: Postprocessing of a Gr\"obner Basis} -\ttindex{GROEPOSTPROC} -In many cases, it is difficult to do the general Gr\"obner processing. -If a Gr\"obner basis with a {\it lex} ordering is calculated already (e.g., -by very individual parameter settings), the solutions can be derived -from it by a call to GROEPOSTPROC. GROESOLVE is functionally -equivalent to a call to GROEBNERF and subsequent calls to -GROEPOSTPROC for each partial basis. -\[ - GROEPOSTPROC(\{exp1, exp2, \ldots , expm\}[,\{var1, var2, \ldots , -varn\}]); -\] -where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of -expressions, \linebreak[4] $\{var1, var2, \ldots ,$ $ varn\}$ is an -optional list of variables. The expressions must be a {\it lex} Gr\"obner -basis with the given variables; the ordering must be still active. - -The result is the same as with GROESOLVE. - -\begin{verbatim} -groepostproc({x3**2 + x3 + x2 - 1, - x2*x3 + x1*x3 + x3 + x1*x2 + x1 + 2, - x2**2 + 2*x2 - 1, - x1**2 - 2},{x3,x2,x1}); - -{{X3= - SQRT(2), - - X2=SQRT(2) - 1, - - X1=SQRT(2)}, - - {X3=SQRT(2), - - X2= - (SQRT(2) + 1), - - X1= - SQRT(2)}, - - SQRT(4*SQRT(2) + 9) - 1 - {X3=-------------------------, - 2 - - X2= - (SQRT(2) + 1), - - X1=SQRT(2)}, - - - (SQRT(4*SQRT(2) + 9) + 1) - {X3=------------------------------, - 2 - - X2= - (SQRT(2) + 1), - - X1=SQRT(2)}, - - SQRT( - 4*SQRT(2) + 9) - 1 - {X3=----------------------------, - 2 - - X2=SQRT(2) - 1, - - X1= - SQRT(2)}, - - - (SQRT( - 4*SQRT(2) + 9) + 1) - {X3=---------------------------------, - 2 - - X2=SQRT(2) - 1, - - X1= - SQRT(2)}} -\end{verbatim} - -% Subsection 4.1.3 -\subsubsection{IDEALQUOTIENT: Quotient of an Ideal and an Expression} -\ttindex{IDEALQUOTIENT} \index{ideal quotient} -Let $I$ be an ideal and $f$ be a polynomial in the same -variables. Then the algebraic quotient is defined by -\[ -I:f = \{ p \;| \; p * f \;\mbox{ member of }\; I\}\;. -\] -The ideal quotient $I:f$ contains $I$ and is obviously part of the -whole polynomial ring, i.e. contained in $\{1\}$. The case $I:f = -\{1\}$ is equivalent to $f$ being a member of $I$. The other extremal -case, $I:f=I$, occurs, when $f$ does not vanish at any general zero of $I$. -The explanation of the notion ``general zero'' introduced by van der -Waerden, however, is beyond the aim of this manual. The operation -of GROESOLVE/GROEPOSTPROC is based on nested ideal quotient -calculations. - -If $I$ is given by a basis and $f$ is given as an expression, the -quotient can be calculated by -\[ -IDEALQUOTIENT (\{exp1, \ldots , expm\}, exp); \] -where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of -expressions or equations, {\it exp} is a single expression or equation. - -IDEALQUOTIENT calculates the algebraic quotient of the ideal $I$ -with the basis $\{exp1, exp2, \ldots , expm\}$ and {\it exp} with -respect to the variables given or extracted. $\{exp1, exp2, \ldots , -expm\}$ is not necessarily a Gr\"obner basis. -The result is the Gr\"obner basis of -the quotient. - -\subsection{Operators for Gr\"obner Bases in all Term Orderings} -\index{Hilbert polynomial} -In some cases where no Gr\"obner -basis with lexical ordering can be calculated, a calculation with a total -degree ordering is still possible. Then the Hilbert polynomial gives -information about the dimension of the solutions space and for finite -sets of solutions univariate polynomials can be calculated. The solutions -of the equation system then is contained in the cross product of all -solutions of all univariate polynomials. - -\subsubsection{HILBERTPOLYNOMIAL: Hilbert Polynomial of an Ideal} -\ttindex{HILBERTPOLYNOMIAL} -This algorithm was contributed by {\sc Joachim Hollman}, Royal -Institute of Technology, Stockholm (private communication). - -\[ -HILBERTPOLYNOMIAL (\{exp1, \ldots , expm\})\;; -\] -where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of -expressions or equations. - -HILBERTPOLYNOMIAL calculates the Hilbert polynomial of the ideal -with basis $\{exp1, exp2, \ldots , expm\}$ with respect to the -variables given or extracted provided the given term ordering is -compatible with the degree, such as the GRADLEX- or REVGRADLEX-ordering. -The term ordering of the basis -must be active and $\{exp1, exp2,\ldots$, $ expm\}$ should be a -Gr\"obner basis with respect to this ordering. The Hilbert polynomial -gives information about the cardinality of solutions of the system -$\{exp1, exp2, \ldots , expm\}$: if the Hilbert polynomial is an -integer, the system has only a discrete set of solutions and the -polynomial is identical with the number of solutions counted with -their multiplicities. Otherwise the degree of the Hilbert -polynomial is the dimension of the solution space. - -If the Hilbert polynomial is not a constant, it is constructed with the -variable ``X'' regardless of whether $x$ is member of $\{var1, var2, -\ldots , varn\}$ or not. The value of this polynomial at sufficiently -large numbers ``X'' -is the difference -of the dimension of the linear vector space of all polynomials of degree -$ \leq X $ minus the dimension of the subspace of all polynomials of -degree $\leq X $ which belong also to the ideal. - -\paragraph{Remark:} The number of zeros in an ideal and the -Hilbert polynomial depend only on the leading terms of the -Gr\"obner basis. So if a subsequent Hilbert calculation is planned, the -Gr\"obner calculation should be performed with ON GLTBASIS and -the value of GLTB (or its elements in a GROEBNERF context) should be -given to HILBERTPOLYNOMIAL. In this manner, a lot of computing time can be -saved in the case of large bases. - -% Chapter 5. -\section{Calculations ``by Hand''} -The following operators support explicit calculations with -polynomials in a distributive representation at the REDUCE top level. -So they allow one to do Gr\"obner type evaluations stepwise by -separate calls. Note that the normal REDUCE arithmetic can be used -for arithmetic combinations of monomials and polynomials. - -% Subsection 5.1 -\subsection{Representing Polynomials in Distributive Form} -\ttindex{GSORT} -\[ - GSORT (p); -\] -where $p$ is a polynomial or a list of polynomials. - -If $p$ is a single polynomial, the result is a reordered version of $p$ -in the distributive representation according to the variables and the -current term order mode; if $p$ is a list, its members are converted -into distributive representation and the result is the list sorted by -the term ordering of the leading terms; zero polynomials are -eliminated from the result. - -\begin{verbatim} - torder({alpha,beta,gamma},lex); - dip := gsort(gamma*(alpha-1)**2*(beta+1)**2); - - - 2 2 2 - DIP := ALPHA *BETA *GAMMA + 2*ALPHA *BETA*GAMMA - - 2 2 - + ALPHA *GAMMA - 2*ALPHA*BETA *GAMMA - 4*ALPHA*BETA*GAMMA - - 2 - - 2*ALPHA*GAMMA + BETA *GAMMA + 2*BETA*GAMMA + GAMMA - - \end{verbatim} - - -% Subsection 5.2 -\subsection{Splitting of a Polynomial into Leading Term and Reductum} -\ttindex{GSPLIT} -\[ -GSPLIT (p); -\] -where $p$ is a polynomial. - -GSPLIT converts the polynomial $p$ into distributive representation -and splits it into leading monomial and reductum. The result is a list -with two elements, the leading monomial and the reductum. - -\begin{verbatim} - gslit(dip); - - 2 2 - {ALPHA *BETA *GAMMA, - - 2 2 2 - 2*ALPHA *BETA*GAMMA + ALPHA *GAMMA - 2*ALPHA*BETA *GAMMA - - 2 - - 4*ALPHA*BETA*GAMMA - 2*ALPHA*GAMMA + BETA *GAMMA - - - + 2*BETA*GAMMA + GAMMA} - - \end{verbatim} - - -\subsection{Calculation of Buchberger's S-polynomial} -\ttindex{GSPOLY} -\[ -GSPOLY (p1,p2); -\] -where $p1$ and $p2$ are polynomials. - -GSPOLY calculates the $S$-polynomial from $p1$ and $p2$; - -Example for a complete calculation (taken from {\sc Davenport et al.} - \cite{Davenport:88a}): -\begin{verbatim} - torder({x,y,z},lex)$ - g1 := x**3*y*z - x*z**2; - g2 := x*y**2*z - x*y*z; - g3 := x**2*y**2 - z;$ - - % first S-polynomial - - g4 := gspoly(g2,g3);$ - - 2 2 - G4 := X *Y*Z - Z - - % next S-polynomial - - p := gspoly(g2,g4); $ - - 2 2 - P := X *Y*Z - Y*Z - - % and reducing, here only by g4 - - g5 := preduce(p,{g4}); - - 2 2 - G5 := - Y*Z + Z - - % last S-polynomial} - - g6 := gspoly(g4,g5); - - 2 2 3 - G6 := X *Z - Z - - % and the final basis sorted descending - - gsort{g2,g3,g4,g5,g6}; - - 2 2 - {X *Y - Z, - - 2 2 - X *Y*Z - Z , - - 2 2 3 - X *Z - Z , - - 2 - X*Y *Z - X*Y*Z, - - 2 2 - - Y*Z + Z } - \end{verbatim} - -\bibliography{groebner} -\bibliographystyle{plain} -\end{document} - +\documentstyle[11pt,reduce]{article} +\title{GROEBNER: A Package for Calculating Gr\"obner Bases} +\date{} +\author{ +H. Melenk \& W. Neun \\[0.05in] +Konrad--Zuse--Zentrum \\ +f\"ur Informationstechnik Berlin \\ +Heilbronner Strasse 10 \\ +D--10711 Berlin-Wilmersdorf \\ +Germany \\[0.05in] +Email: melenk@sc.zib--berlin.de \\[0.05in] +and \\[0.05in] +H.M. M\"oller \\[0.05in] +Fernuniversit\"at Hagen \\ +FB Math und Informatik\\ +Postfach 940 \\ +D--58084 Hagen \\ +Germany\\[0.05in] +Email: Michael.Moeller@fernuni-hagen.de} + +\begin{document} +\maketitle + +\index{Gr\"obner Bases} +Gr\"obner bases are a valuable tool for solving problems in +connection with multivariate polynomials, such as solving systems of +algebraic equations and analyzing polynomial ideals. For a definition +of Gr\"obner bases, a survey of possible applications and further +references, see~\cite{Buchberger:85}. Examples are given in \cite{Boege:86}, +in \cite{Buchberger:88} and also in the test file for this package. + +\index{GROEBNER package} \index{Buchberger's Algorithm} +The GROEBNER package calculates Gr\"obner bases using the +Buchberger algorithm. It can be used over a variety of different +coefficient domains, and for different variable and term orderings. + +The current version of the package uses parts of the previous +version, written by R. Gebauer, A.C. Hearn, H. Kredel and M. +M\"oller. The algorithms implemented in the current version are +documented in \cite{Faugere:89}, \cite{Gebauer:88}, +\cite{Kredel:88a} and \cite{Giovini:91}. + +\section{Compatibility} + +Important modifications of the present GROEBNER package compared +with the REDUCE 3.5 GROEBNER package: +\begin{itemize} +\item The variables of the polynomial ring are now declared in the + $TORDER$ statement together with the term order mode. The old + style (including the variable list in the function calls) + is still accepted, but will not be supported in future versions. +\item The term order mode $private$ has been eliminated. Instead the + mode $matrix$ has been introduced, which allows you to + define any compatible term order. For optimal efficiency + a matrix can be compiled. +\item Polynomial side relations in the parameter domain are now + considered inside the Gr\"obner calculations. You can enter + them as ordinary $LET$ rules. +\item There is an extension $NCPOLY$ for computing with + non--commutative ideals of solvable type. $NCPOLY$ is loaded + as a separate module, but it uses internally the functions + of $GROEBNER$. +\end{itemize} + +\section{Background} + +\subsection{Variables, Domains and Polynomials} + +The various functions of the GROEBNER package manipulate +equations and/or polynomials; equations are internally +transformed into polynomials by forming the difference of +left-hand side and right-hand side. + +All manipulations take place in a ring of polynomials in some +variables $x1, \ldots , xn$ over a coefficient domain $D$: +\[ +D [x1,\ldots , xn], +\] +where $D$ is a field or at least a ring without zero divisors. +The set of variables $x1,\ldots ,xn$ can be given explicitly by the +user or it is extracted automatically from the +input expressions. + +All REDUCE kernels can play the role of ``variables'' in this context; +examples are + +%{\small +\begin{verbatim} +X Y Z22 SIN(ALPHA) COS(ALPHA) C(1,2,3) C(1,3,2) FARINA4711 +\end{verbatim} +%} + +The domain $D$ is the current REDUCE domain with those kernels +adjoined that are not members of the list of variables. So the +elements of $D$ may be complicated polynomials themselves over +kernels not in the list of variables; if, however, the variables are +extracted automatically from the input expressions, $D$ is identical +with the current REDUCE domain. It is useful to regard kernels not +being members of the list of variables as ``parameters'', e.g. +\[ +\begin{array}{c} + a * x + (a - b) * y**2 \;\mbox{ with ``variables''}\ \{x,y\} \\ +\mbox{and ``parameters'' $\;a\;$ and $\;b\;$}\;. +\end{array} +\] + +The current version of the Buchberger algorithm has two internal +modes, a field mode and a ring mode. In the starting phase the +algorithm analyzes the domain type; if it recognizes $D$ as being a +ring it uses the ring mode, otherwise the field mode is needed. +Normally field calculations occur only if all coefficients are numbers +and if the current REDUCE domain is a field (e.g. rational numbers, +modular numbers). In general, the ring mode is faster. When no specific +REDUCE domain is selected, the ring mode is used, even if the input +formulas contain fractional coefficients: they are multiplied by their +common denominators so that they become integer polynomials. + + + +\subsection{Term Ordering} \par +In the theory of Gr\"obner bases, the terms of polynomials are +considered as ordered. Several order modes are available in +the current package, including the basic modes: +\index{LEX ! term order} \index{GRADLEX ! term order} +\index{REVGRADLEX ! term order} + +\begin{center} +LEX, GRADLEX, REVGRADLEX +\end{center} + +All orderings are based on an ordering among the variables. For +each pair of variables $(a,b)$ an order relation must be defined, e.g. +``$ a\gg b $''. The greater sign $\gg$ does not represent a numerical +relation among the variables; it can be interpreted only in terms of +formula representation: ``$a$'' will be placed in front of ``$b$'' or +``$a$'' is more complicated than ``$b$''. + +The sequence of variables constitutes this order base. So the notion +of +\[ +\{x1,x2,x3\} +\] + +as a list of variables at the same time means +\[ +x1 \gg x2 \gg x3 +\] +with respect to the term order. + +If terms (products of powers of variables) are compared with LEX, +that term is chosen which has a greater variable or a higher degree +if the greatest variable is the first in both. With GRADLEX the sum of +all exponents (the total degree) is compared first, and if that does +not lead to a decision, the LEX method is taken for the final decision. +The REVGRADLEX method also compares the total degree first, but +afterward it uses the LEX method in the reverse direction; this is the +method originally used by Buchberger. + +\example \ with $\{x,y,z\}$: \index{GROEBNER package ! example} +\[ +\begin{array}{rlll} +\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf LEX:}}\\ + x * y **3 & \gg & y ** 48 & \mbox{(heavier variable)} \\ + x**4 * y**2 & \gg & x**3 * y**10 & \mbox{(higher degree in 1st +variable)} \vspace*{2mm} \\ +\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf GRADLEX:}} \\ + y**3 * z**4 & \gg & x**3 * y**3 & \mbox{(higher total degree)} \\ + x*z & \gg & y**2 & \mbox{(equal total degree)} +\vspace*{2mm}\\ +\multicolumn{2}{l}{\hspace*{-1cm}\mbox{\bf +REVGRADLEX:}} \\ + y**3 * z**4 & \gg & x**3 * y**3 & \mbox{(higher total degree)} \\ + x*z & \ll & y**2 & \mbox{(equal total degree,} \\ + & & & \mbox{so reverse order of LEX)} +\end{array} +\] + +The formal description of the term order modes is similar to +\cite{Kredel:88}; this description regards only the exponents of a term, +which are written as vectors of integers with $0$ for exponents of a +variable which does not occur: +\[ +\begin{array}{l} + (e) = (e1,\ldots , en) \;\mbox{ representing }\; x1**e1 \ x2**e2 \cdots + xn**en. \\ + \deg(e) \; \mbox{ is the sum over all elements of } \;(e) \\ + (e) \gg (l) \Longleftrightarrow (e)-(l)\gg (0) = (0,\ldots ,0) +\end{array} +\] +\[ +\begin{array}{rll} +\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf LEX:}} \\ + (e) > lex > (0) & \Longrightarrow & e_k > 0 \mbox{ and } e_j =0 +\mbox{ for }\; j=1,\ldots , k-1\vspace*{2mm} \\ +\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf +GRADLEX:}} \\ + (e) >gl> (0) & \Longrightarrow & \deg(e)>0 \mbox { or } (e) >lex> +(0)\vspace*{2mm} \\ +\multicolumn{1}{l}{\hspace*{-.5cm}\mbox{\bf +REVGRADLEX:}}\\ + (e) >rgl> (0) & \Longrightarrow & \deg(e)>0 \mbox{ or }(e) 1$: the vectors with $n$ elements of $R$ +form a $module$ under vector addition (= componentwise addition) +and multiplication with elements of $R$. For a submodule +given by a finite basis a Gr\"obner basis +can be computed, and the facilities of the GROEBNER package +can be used except the operators $GROEBNERF$ and $GROESOLVE$. + +The vectors are encoded using auxiliary variables which represent +the unit vectors in the module. E.g. using ${v_1,v_2,v_3}$ the +module element $[x_1^2,0,x_1-x_2]$ is represented as +$x_1^2 v_1 + x_1 v_3 - x_2 v_3$. The use of ${v_1,v_2,v_3}$ +as unit vectors is set up by assigning the set of auxiliary variables +to the share variable $GMODULE$, e.g. +\begin{verbatim} + GMODULE := {V1,V2,V3}; +\end{verbatim} +After this declaration all monomials built from these variables +are considered as an algebraically independent basis of a vector +space. However, you had best use them only linearly. Once $GMODULE$ +has been set, the auxiliary variables automatically will be +added to the end of each variable list (if they are not yet +member there). +Example: +\begin{verbatim} + torder({x,y,v1,v2,v3},lex)$ + gmodule := {v1,v2,v3}$ + g:=groebner{x^2*v1 + y*v2,x*y*v1 - v3,2y*v1 + y*v3}; + + 2 +G := {X *V1 + Y*V2, + + 2 + X*V3 + Y *V2, + + 3 + Y *V2 - 2*V3, + + 2*Y*V1 + Y*V3} + + preduce((x+y)^3*v1,g); + + 1 3 2 + - X*Y*V2 - ---*Y *V3 - 3*Y *V2 + 3*Y*V3 + 2 + +\end{verbatim} + +In many cases a total degree oriented term order will be adequate +for computations in modules, e.g. for all cases where the +submodule membership is investigated. However, arranging +the auxiliary variables in an elimination oriented term order +can give interesting results. E.g. +\begin{verbatim} + p1:=(x-1)*(x^2-x+3)$ p2:=(x-1)*(x^2+x-5)$ + gmodule := {v1,v2,v3}; + torder({v1,x,v2,v3},lex)$ + gb:=groebner {p1*v1+v2,p2*v1+v3}; + +GB := {30*V1*X - 30*V1 + X*V2 - X*V3 + 5*V2 - 3*V3, + + 2 2 + X *V2 - X *V3 + X*V2 + X*V3 - 5*V2 - 3*V3} + + g:=coeffn(first gb,v1,1); + +G := 30*(X - 1) + + c1:=coeffn(first gb,v2,1); + +C1 := X + 5 + + c2:=coeffn(first gb,v3,1); + +C2 := - X - 3 + + c1*p1 + c2*p2; + +30*(X - 1) + +\end{verbatim} +Here two polynomials +are entered as vectors $[p_1,1,0]$ and $[p_2,0,1]$. Using a term +ordering such that the first dimension ranges highest and the +other components lowest, a classical cofactor computation is +executed just as in the extended Euclidean algorithm. +Consequently the leading polynomial in the resulting +basis shows the greatest common divisor of $p_1$ and $p_2$, +found as a coefficient of $v_1$ while the coefficients +of $v_2$ and $v_3$ are the cofactors $c_1$ and $c_2$ of the polynomials +$p_1$ and $p_2$ with the relation $gcd(p_1,p_2) = c_1p_1 + c_2p_2$. + + +\subsection{Additional Orderings} +Besides the basic orderings, there are ordering options that are used for +special purposes. + +\subsubsection{Separating the Variables into Groups } +\index{grouped ordering} +It is often desirable to separate variables +and formal parameters in a system of polynomials. +This can be done with a {\it lex} Gr\"obner +basis. That however may be hard to compute as it does more +separation than necessary. The following orderings group the +variables into two (or more) sets, where inside each set a classical +ordering acts, while the sets are handled via their total degrees, +which are compared in elimination style. So the Gr\"obner basis will +eliminate the members of the first set, if algebraically possible. +{\it Torder} here gets an additional parameter which describe the +grouping \ttindex{TORDER} +\begin{center}{\it +\begin{tabular}{l} +TORDER ($vl$,gradlexgradlex, $n$) \\ +TORDER ($vl$,gradlexrevgradlex,$n$) \\ +TORDER ($vl$,lexgradlex, $n$) \\ +TORDER ($vl$,lexrevgradlex, $n$) +\end{tabular}} +\end{center} +Here the integer $n$ is the number of variables in the first group +and the names combine the local ordering for the first and second +group, e.g. +\begin{center} +\begin{tabular}{llll} +\multicolumn{4}{l}{{\it lexgradlex}, 3 for $\{x_1,x_2,x_3,x_4,x_5\}$:} \\ +\multicolumn{4}{l}{$x_1^{i_1}\ldots x_5^{i_5} \gg x_1^{j_1}\ldots +x_5^{j_5}$} \\ +if & & & $(i_1,i_2,i_3) \gg_{lex}(j_1,j_2,j_3)$ \\ +& or & & $(i_1,i_2,i_3) = (j_1,j_2,j_3)$ \\ +& & and & $(i_4,i_5) \gg_{gradlex}(j_4,j_5)$ +\end{tabular} +\end{center} +Note that in the second place there is no {\it lex} ordering available; +that would not make sense. + +\subsubsection{Weighted Ordering} +\ttindex{TORDER} \index{weighted ordering} +The statement +\begin{center} +\begin{tabular}{cl} +{\it TORDER} &($vl$,weighted, $\{n_1,n_2,n_3 \ldots$\}) ; \\ +\end{tabular} +\end{center} +establishes a graduated ordering, where the exponents are first +multiplied by the given weights. If there are less weight values than +variables, the weight 1 is added automatically. If the weighted +degree calculation is not decidable, a $lex$ comparison follows. + +\subsubsection{Graded Ordering} +\ttindex{TORDER} \index{graded ordering} +The statement +\begin{center} +\begin{tabular}{cl} +{\it TORDER} &($vl$,graded, $\{n_1,n_2,n_3 \ldots\}$,$order_2$) ; \\ +\end{tabular} +\end{center} +establishes a graduated ordering, where the exponents are first +multiplied by the given weights. If there are less weight values than +variables, the weight 1 is added automatically. If the weighted +degree calculation is not decidable, the term order $order_2$ specified +in the following argument(s) is used. The ordering $graded$ is designed +primarily for use with the operator $dd\_groebner$. + + +\subsubsection{Matrix Ordering} +\ttindex{TORDER} \index{matrix ordering} +The statement +\begin{center} +\begin{tabular}{cl} +{\it TORDER} &($vl$,matrix, $M$) ; \\ +\end{tabular} +\end{center} +where $M$ is a matrix with integer elements and row length which +corresponds to the variable number. The exponents of each monomial +form a vector; two monomials are compared by multiplying their +exponent vectors first with $M$ and comparing the resulting vector +lexicographically. E.g. the unit matrix establishes the classical +$LEX$ term order mode, a matrix with a first row of ones followed +by the rows of a unit matrix corresponds to the $GRADLEX$ ordering. + +The matrix $M$ must have at least as many rows as columns; a non--square +matrix contains redundant rows. The matrix must have full rank, and +the top non--zero element of each column must be positive. + +The generality of the matrix based term order has its price: the +computing time spent in the term sorting is significantly higher +than with the specialized term orders. To overcome this problem, +you can compile a matrix term order +if your REDUCE is equipped with a LISP compiler; the +compilation reduces the computing time overhead significantly. +If you set the switch $COMP$ on, any new order matrix is compiled +when any operator of the GROEBNER package accesses it for the +first time. Alternatively you can compile a matrix explicitly +\begin{verbatim} + torder_compile(,); +\end{verbatim} +where $$ is a name (an identifier) and $$ is a term order matrix. +$torder\_compile$ transforms the matrix into a LISP program, which +is compiled by the LISP compiler when $COMP$ is on or when you +generate a fast loadable module. Later you can activate the new term +order by using the name $$ in a $torder$ statement as term ordering +mode. + +\subsection{Gr\"obner Bases for Graded Homogeneous Systems} + +For a homogeneous system of polynomials under a term order +{\it graded}, {\it gradlex}, {\it revgradlex} or {\it weighted} +a Gr\"obner Base can be computed with limiting the grade +of the intermediate $S$--polynomials: +\begin{description} +\ttindex{dd\_groebner} +\item [{\it dd\_groebner}]($d1$,$d2$,$\{p_1,p_2,\ldots\}$); +\end{description} +where $d1$ is a non--negative integer and $d2$ is an integer +$>$ $d1$ or ``infinity". A pair of polynomials is considered +only if the grade of the lcm of their head terms is between +$d1$ and $d2$. See \cite{BeWei:93} for the mathematical background. +For the term orders {\it graded} or {\it weighted} the (first) weight +vector is used for the grade computation. Otherwise the total +degree of a term is used. + +\section{Ideal Decomposition \& Equation System Solving} +Based on the elementary Gr\"obner operations, the GROEBNER package offers +additional operators, which allow the decomposition of an ideal or of a +system of equations down to the individual solutions. +% Section 4.1 +\subsection{Solutions Based on Lex Type Gr\"obner Bases} +% Subsection 4.1.1 +\subsubsection{GROESOLVE: Solution of a Set of Polynomial Equations} +\ttindex{GROESOLVE} \ttindex{GROEBNERF} +The GROESOLVE operator incorporates a macro algorithm; +lexical Gr\"obner bases are computed by GROEBNERF and decomposed +into simpler ones by ideal decomposition techniques; if algebraically +possible, the problem is reduced to univariate polynomials which are +solved by SOLVE; if ROUNDED is on, numerical approximations are +computed for the roots of the univariate polynomials. +\[ + GROESOLVE(\{exp1, exp2, \ldots , expm\}[,\{var1, var2, \ldots , +varn\}]); \] +where $\{exp1, exp2,\ldots , expm\}$ is a list of any number of +expressions or equations, $\{var1, var2, \ldots , varn\}$ is an +optional list of variables. + +The result is a set of subsets. The subsets contain the solutions of the +polynomial equations. If there are only finitely many solutions, +then each subset is a set of expressions of triangular type +$\{exp1, exp2,\ldots , expn\},$ where $exp1$ depends only on +$var1,$ $exp2$ depends only on $var1$ and $var2$ etc. until $expn$ which +depends on $var1,\ldots,varn.$ This allows a successive determination of +the solution components. If there are infinitely many solutions, +some subsets consist in less than $n$ expressions. By considering some +of the variables as ``free parameters'', these subsets are usually +again of triangular type. + + +\example (intersections of a line with a circle): +\index{GROEBNER package ! example} + +\[ +GROESOLVE(\{x**2 - y**2 - a, p*x+q*y+s\},\{x,y\}); +\] +%{\small +\begin{verbatim} + 2 2 2 2 2 + {{X=(SQRT( - A*P + A*Q + S )*Q - P*S)/(P - Q ), + 2 2 2 2 2 + Y= - (SQRT( - A*P + A*Q + S )*P - Q*S)/(P - Q )}, + 2 2 2 2 2 + {X= - (SQRT( - A*P + A*Q + S )*Q + P*S)/(P - Q ), + 2 2 2 2 2 + Y=(SQRT( - A*P + A*Q + S )*P + Q*S)/(P - Q )}} +\end{verbatim} +%} +% Subsection 4.1.2 +\subsubsection{GROEPOSTPROC: Postprocessing of a Gr\"obner Basis} +\ttindex{GROEPOSTPROC} +In many cases, it is difficult to do the general Gr\"obner processing. +If a Gr\"obner basis with a {\it lex} ordering is calculated already (e.g., +by very individual parameter settings), the solutions can be derived +from it by a call to GROEPOSTPROC. GROESOLVE is functionally +equivalent to a call to GROEBNERF and subsequent calls to +GROEPOSTPROC for each partial basis. +\[ + GROEPOSTPROC(\{exp1, exp2, \ldots , expm\}[,\{var1, var2, \ldots , +varn\}]); +\] +where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of +expressions, \linebreak[4] $\{var1, var2, \ldots ,$ $ varn\}$ is an +optional list of variables. The expressions must be a {\it lex} Gr\"obner +basis with the given variables; the ordering must be still active. + +The result is the same as with GROESOLVE. + +\begin{verbatim} +groepostproc({x3**2 + x3 + x2 - 1, + x2*x3 + x1*x3 + x3 + x1*x2 + x1 + 2, + x2**2 + 2*x2 - 1, + x1**2 - 2},{x3,x2,x1}); + +{{X3= - SQRT(2), + + X2=SQRT(2) - 1, + + X1=SQRT(2)}, + + {X3=SQRT(2), + + X2= - (SQRT(2) + 1), + + X1= - SQRT(2)}, + + SQRT(4*SQRT(2) + 9) - 1 + {X3=-------------------------, + 2 + + X2= - (SQRT(2) + 1), + + X1=SQRT(2)}, + + - (SQRT(4*SQRT(2) + 9) + 1) + {X3=------------------------------, + 2 + + X2= - (SQRT(2) + 1), + + X1=SQRT(2)}, + + SQRT( - 4*SQRT(2) + 9) - 1 + {X3=----------------------------, + 2 + + X2=SQRT(2) - 1, + + X1= - SQRT(2)}, + + - (SQRT( - 4*SQRT(2) + 9) + 1) + {X3=---------------------------------, + 2 + + X2=SQRT(2) - 1, + + X1= - SQRT(2)}} +\end{verbatim} + +% Subsection 4.1.3 +\subsubsection{IDEALQUOTIENT: Quotient of an Ideal and an Expression} +\ttindex{IDEALQUOTIENT} \index{ideal quotient} +Let $I$ be an ideal and $f$ be a polynomial in the same +variables. Then the algebraic quotient is defined by +\[ +I:f = \{ p \;| \; p * f \;\mbox{ member of }\; I\}\;. +\] +The ideal quotient $I:f$ contains $I$ and is obviously part of the +whole polynomial ring, i.e. contained in $\{1\}$. The case $I:f = +\{1\}$ is equivalent to $f$ being a member of $I$. The other extremal +case, $I:f=I$, occurs, when $f$ does not vanish at any general zero of $I$. +The explanation of the notion ``general zero'' introduced by van der +Waerden, however, is beyond the aim of this manual. The operation +of GROESOLVE/GROEPOSTPROC is based on nested ideal quotient +calculations. + +If $I$ is given by a basis and $f$ is given as an expression, the +quotient can be calculated by +\[ +IDEALQUOTIENT (\{exp1, \ldots , expm\}, exp); \] +where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of +expressions or equations, {\it exp} is a single expression or equation. + +IDEALQUOTIENT calculates the algebraic quotient of the ideal $I$ +with the basis $\{exp1, exp2, \ldots , expm\}$ and {\it exp} with +respect to the variables given or extracted. $\{exp1, exp2, \ldots , +expm\}$ is not necessarily a Gr\"obner basis. +The result is the Gr\"obner basis of +the quotient. + +\subsection{Operators for Gr\"obner Bases in all Term Orderings} +\index{Hilbert polynomial} +In some cases where no Gr\"obner +basis with lexical ordering can be calculated, a calculation with a total +degree ordering is still possible. Then the Hilbert polynomial gives +information about the dimension of the solutions space and for finite +sets of solutions univariate polynomials can be calculated. The solutions +of the equation system then is contained in the cross product of all +solutions of all univariate polynomials. + +\subsubsection{HILBERTPOLYNOMIAL: Hilbert Polynomial of an Ideal} +\ttindex{HILBERTPOLYNOMIAL} +This algorithm was contributed by {\sc Joachim Hollman}, Royal +Institute of Technology, Stockholm (private communication). + +\[ +HILBERTPOLYNOMIAL (\{exp1, \ldots , expm\})\;; +\] +where $\{exp1, exp2, \ldots , expm\}$ is a list of any number of +expressions or equations. + +HILBERTPOLYNOMIAL calculates the Hilbert polynomial of the ideal +with basis $\{exp1, exp2, \ldots , expm\}$ with respect to the +variables given or extracted provided the given term ordering is +compatible with the degree, such as the GRADLEX- or REVGRADLEX-ordering. +The term ordering of the basis +must be active and $\{exp1, exp2,\ldots$, $ expm\}$ should be a +Gr\"obner basis with respect to this ordering. The Hilbert polynomial +gives information about the cardinality of solutions of the system +$\{exp1, exp2, \ldots , expm\}$: if the Hilbert polynomial is an +integer, the system has only a discrete set of solutions and the +polynomial is identical with the number of solutions counted with +their multiplicities. Otherwise the degree of the Hilbert +polynomial is the dimension of the solution space. + +If the Hilbert polynomial is not a constant, it is constructed with the +variable ``X'' regardless of whether $x$ is member of $\{var1, var2, +\ldots , varn\}$ or not. The value of this polynomial at sufficiently +large numbers ``X'' +is the difference +of the dimension of the linear vector space of all polynomials of degree +$ \leq X $ minus the dimension of the subspace of all polynomials of +degree $\leq X $ which belong also to the ideal. + +\paragraph{Remark:} The number of zeros in an ideal and the +Hilbert polynomial depend only on the leading terms of the +Gr\"obner basis. So if a subsequent Hilbert calculation is planned, the +Gr\"obner calculation should be performed with ON GLTBASIS and +the value of GLTB (or its elements in a GROEBNERF context) should be +given to HILBERTPOLYNOMIAL. In this manner, a lot of computing time can be +saved in the case of large bases. + +% Chapter 5. +\section{Calculations ``by Hand''} +The following operators support explicit calculations with +polynomials in a distributive representation at the REDUCE top level. +So they allow one to do Gr\"obner type evaluations stepwise by +separate calls. Note that the normal REDUCE arithmetic can be used +for arithmetic combinations of monomials and polynomials. + +% Subsection 5.1 +\subsection{Representing Polynomials in Distributive Form} +\ttindex{GSORT} +\[ + GSORT (p); +\] +where $p$ is a polynomial or a list of polynomials. + +If $p$ is a single polynomial, the result is a reordered version of $p$ +in the distributive representation according to the variables and the +current term order mode; if $p$ is a list, its members are converted +into distributive representation and the result is the list sorted by +the term ordering of the leading terms; zero polynomials are +eliminated from the result. + +\begin{verbatim} + torder({alpha,beta,gamma},lex); + dip := gsort(gamma*(alpha-1)**2*(beta+1)**2); + + + 2 2 2 + DIP := ALPHA *BETA *GAMMA + 2*ALPHA *BETA*GAMMA + + 2 2 + + ALPHA *GAMMA - 2*ALPHA*BETA *GAMMA - 4*ALPHA*BETA*GAMMA + + 2 + - 2*ALPHA*GAMMA + BETA *GAMMA + 2*BETA*GAMMA + GAMMA + + \end{verbatim} + + +% Subsection 5.2 +\subsection{Splitting of a Polynomial into Leading Term and Reductum} +\ttindex{GSPLIT} +\[ +GSPLIT (p); +\] +where $p$ is a polynomial. + +GSPLIT converts the polynomial $p$ into distributive representation +and splits it into leading monomial and reductum. The result is a list +with two elements, the leading monomial and the reductum. + +\begin{verbatim} + gslit(dip); + + 2 2 + {ALPHA *BETA *GAMMA, + + 2 2 2 + 2*ALPHA *BETA*GAMMA + ALPHA *GAMMA - 2*ALPHA*BETA *GAMMA + + 2 + - 4*ALPHA*BETA*GAMMA - 2*ALPHA*GAMMA + BETA *GAMMA + + + + 2*BETA*GAMMA + GAMMA} + + \end{verbatim} + + +\subsection{Calculation of Buchberger's S-polynomial} +\ttindex{GSPOLY} +\[ +GSPOLY (p1,p2); +\] +where $p1$ and $p2$ are polynomials. + +GSPOLY calculates the $S$-polynomial from $p1$ and $p2$; + +Example for a complete calculation (taken from {\sc Davenport et al.} + \cite{Davenport:88a}): +\begin{verbatim} + torder({x,y,z},lex)$ + g1 := x**3*y*z - x*z**2; + g2 := x*y**2*z - x*y*z; + g3 := x**2*y**2 - z;$ + + % first S-polynomial + + g4 := gspoly(g2,g3);$ + + 2 2 + G4 := X *Y*Z - Z + + % next S-polynomial + + p := gspoly(g2,g4); $ + + 2 2 + P := X *Y*Z - Y*Z + + % and reducing, here only by g4 + + g5 := preduce(p,{g4}); + + 2 2 + G5 := - Y*Z + Z + + % last S-polynomial} + + g6 := gspoly(g4,g5); + + 2 2 3 + G6 := X *Z - Z + + % and the final basis sorted descending + + gsort{g2,g3,g4,g5,g6}; + + 2 2 + {X *Y - Z, + + 2 2 + X *Y*Z - Z , + + 2 2 3 + X *Z - Z , + + 2 + X*Y *Z - X*Y*Z, + + 2 2 + - Y*Z + Z } + \end{verbatim} + +\bibliography{groebner} +\bibliographystyle{plain} +\end{document} + Index: r36/doc/IDEALS.TEX ================================================================== --- r36/doc/IDEALS.TEX +++ r36/doc/IDEALS.TEX @@ -1,129 +1,129 @@ -\documentstyle[12pt]{article} -\begin{document} -\begin{center} {\Large Polynomial Ideals} \end{center} -\begin{center} Arithmetic for polynomial ideals supported by -Gr\"obner bases \end{center} -\begin{center} Version 1.0 May 1992 \end{center} - -\begin{center} Herbert Melenk \\ Konrad-Zuse-Zentrum f\"ur -Informationstechnik \\ -Heilbronner Str. 10 \\ D1000 Berlin 31 \\ Federal Republic of Germany \\ -melenk@sc.zib-berlin.de \\ May 1992 \end{center} - -\section{Introduction} - -This package implements the basic arithmetic for polynomial ideals -by exploiting the Gr\"obner bases package of REDUCE. -In order to save computing time all intermediate Gr\"obner bases -are stored internally such that time consuming repetitions -are inhibited. A uniform setting facilitates the access. - -\section{Initialization} - -Prior to any computation the set of variables has to be declared -by calling the operator $I\_setting$ . E.g. in order to initiate -computations in the polynomial ring $Q[x,y,z]$ call -\begin{verbatim} - I_setting(x,y,z); -\end{verbatim} -A subsequent call to $I\_setting$ allows one to select another set -of variables; at the same time the internal data structures -are cleared in order to free memory resources. - -\section{Bases} - -An ideal is represented by a basis (set of polynomials) tagged -with the symbol $I$, e.g. -\begin{verbatim} - u := I(x*z-y**2, x**3-y*z); -\end{verbatim} -Alternatively a list of polynomials can be used as input basis; however, -all arithmetic results will be presented in the above form. The -operator $ideal2list$ allows one to convert an ideal basis into a -conventional REDUCE list. - -\subsection{Operators} - -Because of syntactical restrictions in REDUCE, special operators -have to be used for ideal arithmetic: - -\begin{verbatim} - .+ ideal sum (infix) - .* ideal product (infix) - .: ideal quotient (infix) - ./ ideal quotient (infix) - .= ideal equality test (infix) - subset ideal inclusion test (infix) - intersection ideal intersection (prefix,binary) - member test for membership in an ideal - (infix: polynomial and ideal) - gb Groebner basis of an ideal (prefix, unary) - ideal2list convert ideal basis to polynomial list - (prefix,unary) -\end{verbatim} - -Example: - -\begin{verbatim} - I(x+y,x^2) .* I(x-z); - - 2 2 2 - I(X + X*Y - X*Z - Y*Z,X*Y - Y *Z) -\end{verbatim} - -The test operators return the values 1 (=true) or 0 (=false) -such that they can be used in REDUCE $if-then-else$ statements -directly. - -The results of $sum,product, quotient,intersction$ are ideals -represented by their Gr\"obner basis in the current setting and -term order. The term order can be modified using the operator -$torder$ from the Gr\"obner package. Note that ideal equality -cannot be tested with the REDUCE equal sign: - -\begin{verbatim} - - I(x,y) = I(y,x) is false - I(x,y) .= I(y,x) is true - -\end{verbatim} - -\section{Algorithms} - -The operators $groebner$, $preduce$ and $idealquotient$ of the -REDUCE Gr\"obner package support the basic algorithms: - -$GB(Iu_1,u_2...) \rightarrow groebner(\{u_1,u_2...\},\{x,...\})$ - -$p \in I_1 \rightarrow p=0 \ mod \ I_1$ - -$I_1 : I(p) \rightarrow (I_1 \bigcap I(p)) / p \ elementwise$ - -\noindent -On top of these the Ideals package implements the following -operations: - - -$I(u_1,u_2...)+I(v_1,v_2...) \rightarrow GB(I(u_1,u_2...,v_1,v_2...))$ - - -$I(u_1,u_2...)*I(v_1,v_2...)\rightarrow - GB(I(u_1*v_1,u_1*v2,...,u_2*v_1,u_2*v_2...))$ - - -$I_1 \bigcap I_2 \rightarrow - Q[x,...] \bigcap GB_{lex}(t*I_1 + (1-t)*I_2,\{t,x,..\}) $ - - -$I_1 : I(p_1,p_2,...) \rightarrow I_1 : I(p_1) \bigcap I_1 : I(p_2) -\bigcap ...$ - -$I_1 = I_2 \rightarrow GB(I_1)=GB(I_2)$ - -$I_1 \subseteq I_2 - \rightarrow \ u_i \in I_2 \ \forall \ u_i \in I_1=I(u_1,u_2...)$ - -\section{Examples} - -Please consult the file $ideals.tst$. -\end{document} +\documentstyle[12pt]{article} +\begin{document} +\begin{center} {\Large Polynomial Ideals} \end{center} +\begin{center} Arithmetic for polynomial ideals supported by +Gr\"obner bases \end{center} +\begin{center} Version 1.0 May 1992 \end{center} + +\begin{center} Herbert Melenk \\ Konrad-Zuse-Zentrum f\"ur +Informationstechnik \\ +Heilbronner Str. 10 \\ D1000 Berlin 31 \\ Federal Republic of Germany \\ +melenk@sc.zib-berlin.de \\ May 1992 \end{center} + +\section{Introduction} + +This package implements the basic arithmetic for polynomial ideals +by exploiting the Gr\"obner bases package of REDUCE. +In order to save computing time all intermediate Gr\"obner bases +are stored internally such that time consuming repetitions +are inhibited. A uniform setting facilitates the access. + +\section{Initialization} + +Prior to any computation the set of variables has to be declared +by calling the operator $I\_setting$ . E.g. in order to initiate +computations in the polynomial ring $Q[x,y,z]$ call +\begin{verbatim} + I_setting(x,y,z); +\end{verbatim} +A subsequent call to $I\_setting$ allows one to select another set +of variables; at the same time the internal data structures +are cleared in order to free memory resources. + +\section{Bases} + +An ideal is represented by a basis (set of polynomials) tagged +with the symbol $I$, e.g. +\begin{verbatim} + u := I(x*z-y**2, x**3-y*z); +\end{verbatim} +Alternatively a list of polynomials can be used as input basis; however, +all arithmetic results will be presented in the above form. The +operator $ideal2list$ allows one to convert an ideal basis into a +conventional REDUCE list. + +\subsection{Operators} + +Because of syntactical restrictions in REDUCE, special operators +have to be used for ideal arithmetic: + +\begin{verbatim} + .+ ideal sum (infix) + .* ideal product (infix) + .: ideal quotient (infix) + ./ ideal quotient (infix) + .= ideal equality test (infix) + subset ideal inclusion test (infix) + intersection ideal intersection (prefix,binary) + member test for membership in an ideal + (infix: polynomial and ideal) + gb Groebner basis of an ideal (prefix, unary) + ideal2list convert ideal basis to polynomial list + (prefix,unary) +\end{verbatim} + +Example: + +\begin{verbatim} + I(x+y,x^2) .* I(x-z); + + 2 2 2 + I(X + X*Y - X*Z - Y*Z,X*Y - Y *Z) +\end{verbatim} + +The test operators return the values 1 (=true) or 0 (=false) +such that they can be used in REDUCE $if-then-else$ statements +directly. + +The results of $sum,product, quotient,intersction$ are ideals +represented by their Gr\"obner basis in the current setting and +term order. The term order can be modified using the operator +$torder$ from the Gr\"obner package. Note that ideal equality +cannot be tested with the REDUCE equal sign: + +\begin{verbatim} + + I(x,y) = I(y,x) is false + I(x,y) .= I(y,x) is true + +\end{verbatim} + +\section{Algorithms} + +The operators $groebner$, $preduce$ and $idealquotient$ of the +REDUCE Gr\"obner package support the basic algorithms: + +$GB(Iu_1,u_2...) \rightarrow groebner(\{u_1,u_2...\},\{x,...\})$ + +$p \in I_1 \rightarrow p=0 \ mod \ I_1$ + +$I_1 : I(p) \rightarrow (I_1 \bigcap I(p)) / p \ elementwise$ + +\noindent +On top of these the Ideals package implements the following +operations: + + +$I(u_1,u_2...)+I(v_1,v_2...) \rightarrow GB(I(u_1,u_2...,v_1,v_2...))$ + + +$I(u_1,u_2...)*I(v_1,v_2...)\rightarrow + GB(I(u_1*v_1,u_1*v2,...,u_2*v_1,u_2*v_2...))$ + + +$I_1 \bigcap I_2 \rightarrow + Q[x,...] \bigcap GB_{lex}(t*I_1 + (1-t)*I_2,\{t,x,..\}) $ + + +$I_1 : I(p_1,p_2,...) \rightarrow I_1 : I(p_1) \bigcap I_1 : I(p_2) +\bigcap ...$ + +$I_1 = I_2 \rightarrow GB(I_1)=GB(I_2)$ + +$I_1 \subseteq I_2 + \rightarrow \ u_i \in I_2 \ \forall \ u_i \in I_1=I(u_1,u_2...)$ + +\section{Examples} + +Please consult the file $ideals.tst$. +\end{document} Index: r36/doc/INEQ.TEX ================================================================== --- r36/doc/INEQ.TEX +++ r36/doc/INEQ.TEX @@ -1,77 +1,77 @@ -\documentstyle[12pt]{article} -\begin{document} -\begin{center} {\Large INEQ} \end{center} - -\begin{center} Herbert Melenk \\ Konrad-Zuse-Zentrum fuer -Informationstechnik \\ -Heilbronner Str. 10, D10711 Berlin -- Wilmersdorf\\ Germany \\ -melenk@zib-berlin.de \end{center} - -This package supports the operator {\bf ineq\_solve} that -tries to solves single inequalities and sets of coupled inequalities. -The following types of systems are supported -\footnote{For linear optimization problems please use the operator -{\bf simplex} of the {\bf linalg} package}: -\begin{itemize} -\item only numeric coefficients (no parametric system), -\item a linear system of mixed equations and $<=$ -- $>=$ - inequalities, applying the method of Fourier and Motzkin - \footnote{described by G.B. Dantzig in {\em Linear Programming - and Extensions.}}, -\item a univariate inequality with $<=$, $>=$, $>$ or $<$ operator - and polynomial or rational left--hand and right--hand sides, - or a system of such inequalities with only one variable. -\end{itemize} - -Syntax: -\begin{center} -{\tt INEQ\_SOLVE($<$expr$>$ [,$<$vl$>$])} -\end{center} -where $<$expr$>$ is an inequality or a list of coupled inequalities -and equations, and the optional argument $<$vl$>$ is a single -variable (kernel) or a list of variables (kernels). If not -specified, they are extracted automatically from $<$expr$>$. -For multivariate input an explicit variable list specifies the -elimination sequence: the last member is the most specific one. - -An error message occurs if the input cannot be processed by the -currently implemented algorithms. - -The result is a list. It is empty if the system has no feasible solution. -Otherwise the result presents the admissible ranges as set -of equations where each variable is equated to -one expression or to an interval. -The most specific variable is the first one in the result list and -each form contains only preceding variables (resolved form). -The interval limits can be formal {\bf max} or {\bf min} expressions. -Algebraic numbers are encoded as rounded number approximations. - -\noindent -{\bf Examples}: - -\begin{verbatim} -ineq_solve({(2*x^2+x-1)/(x-1) >= (x+1/2)^2, x>0}); - -{x=(0 .. 0.326583),x=(1 .. 2.56777)} - - reg:= - {a + b - c>=0, a - b + c>=0, - a + b + c>=0, 0>=0, 2>=0, - 2*c - 2>=0, a - b + c>=0, a + b - c>=0, - a + b + c - 2>=0, - 2>=0, 0>=0, 2*b - 2>=0, k + 1>=0, - a - b - c + k>=0, - - a - b - c + k + 2>=0, - 2*b + k>=0, - - 2*c + k>=0, a + b + c - k>=0, - 2*b + 2*c - k - 2>=0, a + b + c - k>=0}$ - -ineq_solve (reg,{k,a,b,c}); - -{c=(1 .. infinity), - - b=(1 .. infinity), - - a=(max( - b + c,b - c) .. b + c - 2), - - k=a + b + c} -\end{verbatim} - -\end{document} - +\documentstyle[12pt]{article} +\begin{document} +\begin{center} {\Large INEQ} \end{center} + +\begin{center} Herbert Melenk \\ Konrad-Zuse-Zentrum fuer +Informationstechnik \\ +Heilbronner Str. 10, D10711 Berlin -- Wilmersdorf\\ Germany \\ +melenk@zib-berlin.de \end{center} + +This package supports the operator {\bf ineq\_solve} that +tries to solves single inequalities and sets of coupled inequalities. +The following types of systems are supported +\footnote{For linear optimization problems please use the operator +{\bf simplex} of the {\bf linalg} package}: +\begin{itemize} +\item only numeric coefficients (no parametric system), +\item a linear system of mixed equations and $<=$ -- $>=$ + inequalities, applying the method of Fourier and Motzkin + \footnote{described by G.B. Dantzig in {\em Linear Programming + and Extensions.}}, +\item a univariate inequality with $<=$, $>=$, $>$ or $<$ operator + and polynomial or rational left--hand and right--hand sides, + or a system of such inequalities with only one variable. +\end{itemize} + +Syntax: +\begin{center} +{\tt INEQ\_SOLVE($<$expr$>$ [,$<$vl$>$])} +\end{center} +where $<$expr$>$ is an inequality or a list of coupled inequalities +and equations, and the optional argument $<$vl$>$ is a single +variable (kernel) or a list of variables (kernels). If not +specified, they are extracted automatically from $<$expr$>$. +For multivariate input an explicit variable list specifies the +elimination sequence: the last member is the most specific one. + +An error message occurs if the input cannot be processed by the +currently implemented algorithms. + +The result is a list. It is empty if the system has no feasible solution. +Otherwise the result presents the admissible ranges as set +of equations where each variable is equated to +one expression or to an interval. +The most specific variable is the first one in the result list and +each form contains only preceding variables (resolved form). +The interval limits can be formal {\bf max} or {\bf min} expressions. +Algebraic numbers are encoded as rounded number approximations. + +\noindent +{\bf Examples}: + +\begin{verbatim} +ineq_solve({(2*x^2+x-1)/(x-1) >= (x+1/2)^2, x>0}); + +{x=(0 .. 0.326583),x=(1 .. 2.56777)} + + reg:= + {a + b - c>=0, a - b + c>=0, - a + b + c>=0, 0>=0, 2>=0, + 2*c - 2>=0, a - b + c>=0, a + b - c>=0, - a + b + c - 2>=0, + 2>=0, 0>=0, 2*b - 2>=0, k + 1>=0, - a - b - c + k>=0, + - a - b - c + k + 2>=0, - 2*b + k>=0, + - 2*c + k>=0, a + b + c - k>=0, + 2*b + 2*c - k - 2>=0, a + b + c - k>=0}$ + +ineq_solve (reg,{k,a,b,c}); + +{c=(1 .. infinity), + + b=(1 .. infinity), + + a=(max( - b + c,b - c) .. b + c - 2), + + k=a + b + c} +\end{verbatim} + +\end{document} + Index: r36/doc/INVBASE.TEX ================================================================== --- r36/doc/INVBASE.TEX +++ r36/doc/INVBASE.TEX @@ -1,172 +1,172 @@ -\documentstyle[12pt]{article} -\textwidth 155mm -\textheight 225mm -\topmargin -10mm -\oddsidemargin 7mm -\evensidemargin 7mm -\pagestyle{empty} -\begin{document} -\def \bg #1 {\begin{tabular}{{#1}}} -\def \nd {\end{tabular}} -\begin{center} -{\large \bf INVBASE: A Package for Computing Involutive Bases} -\vskip 0.7cm -\noindent -A.Yu.Zharkov, Yu.A.Blinkov\\ -Saratov University\\ -Astrakhanskaya 83\\ -410071 Saratov\\ -Russia\\ -Email: postmaster@scnit.saratov.su\\ -\end{center} -\vspace{0.3cm} -\vskip 0.5cm -\section{Introduction} -Involutive bases are a new tool for solving problems in connection with -multivariate polynomials, such as solving systems of polynomial equations -and analyzing polynomial ideals, see \cite{Lille}. An involutive basis of -polynomial ideal is nothing but a special form of a redundant Gr\"obner -basis. The construction of involutive bases reduces the problem of solving -polynomial systems to simple linear algebra.\\ -The INVBASE package -\footnote{The REDUCE implementation has been supported by -the Konrad-Zuse-Zentrum Berlin} -calculates involutive bases of polynomial ideals -using an algorithm described in \cite{Lille} -which may be considered as an alternative to -the well-known Buchberger algorithm \cite{Buch}. -The package can be used over -a variety of different coefficient domains, and for different variable -and term orderings.\\ -The algorithm implemented in the INVBASE package is proved -to be valid for any zero-dimensional ideal (finite number of solutions) -as well as for positive-dimensional ideals in generic form. However, -the algorithm does not terminate for ``sparse'' positive-dimensional systems. -In order to stop the process we use the maximum degree -bound for the Gr\"obner bases of generic ideals in the total-degree -term ordering established in \cite{Laz}. -In this case, it is reasonable -to call the GROEBNER package with the answer of INVBASE as input -information in order to compute the reduced Gr\"obner basis under the -same variable and term ordering.\\ -Though the INVBASE package supports computing involutive bases in any -admissible term ordering, -it is reasonable to compute them only for the total-degree term -orderings. The package includes a special algorithm for conversion -of total-degree involutive bases into the triangular bases -in the lexicographical term ordering that is desirable for -finding solutions. Normally the sum of timings for these two -computations is much less than the timing for direct computation -of the lexicographical involutive bases. As a rule, the result -of the conversion algorithm is a reduced Gr\"obner basis in the -lexicographical term ordering. However, because of some gaps in -the current version of the algorithm, -there may be rare situations when the resulting triangular set -does not possess the formal property of Gr\"obner bases. -Anyway, we recommend using the GROEBNER package with the result -of the conversion algorithm as input in order either to check -the Gr\"obner bases property or to transform the result into a -lexicographical Gr\"obner basis. -\section{The Basic Operators} -\subsection{Term Ordering} -The following term order modes are available: -$$ REVGRADLEX,\; GRADLEX,\; LEX $$ -These modes have the same meaning as for the GROEBNER package.\\ -All orderings are based on an ordering among the variables. -For each pair of variables an order relation $>$ must be defined, -e.g. $x>y$. The term ordering mode as well as the order of variables -are set by the operator -$$ INVTORDER\,,\{x_1,...,x_n\} $$ -where $$ is one of the term order modes listed above. -The notion of $\{x_1,...,x_n\}$ as a list of variables -at the same time means $x_1>...>x_n$. -\vskip 0.1cm -\noindent -{\bf Example 1.} -$$ INVTORDER\>\,REVGRADLEX,\{x,y,z\} $$ -sets the reverse graduated term ordering based on the variable -order $x>y>z$.\\ -The operator $INVTORDER$ may be omitted. The default term order mode -is $REV\-GRADLEX$ and the default decreasing variable order is -alphabetical (or, more generally, the default REDUCE kernel order). -Furthermore, the list of variables in the $INVTORDER$ may be omitted. -In this case the default variable order is used. -\subsection{Computing Involutive Bases} -To compute the involutive basis of ideal generated by the set of -polynomials $\{p_1,...,p_m\}$ one should type the command -$$ INVBASE \> \{p_1,...,p_m\} $$ -where $p_i$ are polynomials in variables listed in the -$INVTORDER$ operator. If some kernels in $p_i$ were not listed -previously in the $INVTORDER$ operator they are considered as -parameters, i.e. they are considered part of the coefficients of -polynomials. If $INVTORDER$ was omitted, all the kernels -in $p_i$ are considered as variables with the default REDUCE -kernel order.\\ -The coefficients of polynomials $p_i$ may be integers as well as -rational numbers (or, accordingly, polynomials and rational functions -in the parametric case). The computations modulo prime numbers are -also available. For this purpose one should type the REDUCE commands -$$ ON \> MODULAR;\> SETMOD \> p; $$ -where $p$ is a prime number.\\ -The value of the $INVBASE$ function is a list of integer polynomials -$\{g_1,...,g_n\}$ representing an involutive basis of a given ideal.\\ -\newpage -\noindent -{\bf Example 2.} -\begin{eqnarray*} -& & INVTORDER \> REVGRADLEX,\{x,y,z\}; \\ -& & g:= INVBASE \> \{4*x**2 + x*y**2 - z + 1/4,\> - 2*x + y**2*z + 1/2,\> \\ -& & x**2*z - 1/2*x - y**2 \}; -\end{eqnarray*} -The resulting involutive basis in the reverse graduate ordering is -\begin{eqnarray*} -g := \{& & 8*x*y*z^3 - 2*x*y*z^2 + 4*y^3 - \\ -& & 4*y*z^2 + 16*x*y + 17*y*z - 4*y,\\ -& & 8*y^4 - 8*x*z^2 - 256*y^2 + 2*x*z + 64*z^2 - 96*x + 20*z - 9,\\ -& & 2*y^3*z + 4*x*y + y,\\ -& & 8*x*z^3 - 2*x*z^2 + 4*y^2 - 4*z^2 + 16*x + 17*z - 4,\\ -& & - 4*y*z^3 - 8*y^3 + 6*x*y*z + y*z^2 - 36*x*y - 8*y,\\ -& & 4*x*y^2 + 32*y^2 - 8*z^2 + 12*x - 2*z + 1,\\ -& & 2*y^2*z + 4*x + 1,\\ -& & - 4*z^3 - 8*y^2 + 6*x*z + z^2 - 36*x - 8,\\ -& & 8*x^2 - 16*y^2 + 4*z^2 - 6*x - z \quad \} -\end{eqnarray*} -To convert it into a lexicographical Gr\"obner basis one should type -$$ h:=INVLEX\>g; $$ -The result is -\begin{eqnarray*} -h :=\{& &3976*x + 37104*z^6 - 600*z^5 + 2111*z^4 + \\ -& & 122062*z^3 + 232833*z^2 - 680336*z + 288814,\\ -& & 1988*y^2 - 76752*z^6 + 1272*z^5 - 4197*z^4 - \\ -& & 251555*z^3 - 481837*z^2 + 1407741*z - 595666,\\ -& & 16*z^7 - 8*z^6 + z^5 + 52*z^4 + - 75*z^3 - 342*z^2 + 266*z - 60 \quad \} -\end{eqnarray*} -In the case of ``sparse'' positive-dimensioned system -when the involutive basis in the sense of \cite{Lille} does not exist, -you get the error message $$ *****\> MAXIMUM \> DEGREE \> BOUND \> -EXCEEDED $$ The resulting list of polynomials which is not an involutive -basis is stored in the share variable INVTEMPBASIS. In this case -it is reasonable to call the GROEBNER package with the value of -INVTEMPBASIS as input under the same variable and term ordering. - -\begin{thebibliography}{99} - -\bibitem{Lille} -Zharkov A.Yu., Blinkov Yu.A. Involution Approach to Solving Systems -of Algebraic Equations. Proceedings of the IMACS '93, 1993, 11-16. - -\bibitem{Buch} -Buchberger B. Gr\"obner bases: an Algorithmic Method in Polynomial -Ideal Theory. In: (Bose N.K., ed.) Recent Trends in Multidimensional -System Theory, Reidel, 1985. - -\bibitem{Laz} -Lazard D. Gr\"obner Bases, Gaussian Elimination and Resolution of -Systems of Algebraic Equations. Proceedings of EUROCAL '83. -Lecture Notes in Computer Science 162, Springer 1983, 146-157. - -\end{thebibliography} - -\end{document} +\documentstyle[12pt]{article} +\textwidth 155mm +\textheight 225mm +\topmargin -10mm +\oddsidemargin 7mm +\evensidemargin 7mm +\pagestyle{empty} +\begin{document} +\def \bg #1 {\begin{tabular}{{#1}}} +\def \nd {\end{tabular}} +\begin{center} +{\large \bf INVBASE: A Package for Computing Involutive Bases} +\vskip 0.7cm +\noindent +A.Yu.Zharkov, Yu.A.Blinkov\\ +Saratov University\\ +Astrakhanskaya 83\\ +410071 Saratov\\ +Russia\\ +Email: postmaster@scnit.saratov.su\\ +\end{center} +\vspace{0.3cm} +\vskip 0.5cm +\section{Introduction} +Involutive bases are a new tool for solving problems in connection with +multivariate polynomials, such as solving systems of polynomial equations +and analyzing polynomial ideals, see \cite{Lille}. An involutive basis of +polynomial ideal is nothing but a special form of a redundant Gr\"obner +basis. The construction of involutive bases reduces the problem of solving +polynomial systems to simple linear algebra.\\ +The INVBASE package +\footnote{The REDUCE implementation has been supported by +the Konrad-Zuse-Zentrum Berlin} +calculates involutive bases of polynomial ideals +using an algorithm described in \cite{Lille} +which may be considered as an alternative to +the well-known Buchberger algorithm \cite{Buch}. +The package can be used over +a variety of different coefficient domains, and for different variable +and term orderings.\\ +The algorithm implemented in the INVBASE package is proved +to be valid for any zero-dimensional ideal (finite number of solutions) +as well as for positive-dimensional ideals in generic form. However, +the algorithm does not terminate for ``sparse'' positive-dimensional systems. +In order to stop the process we use the maximum degree +bound for the Gr\"obner bases of generic ideals in the total-degree +term ordering established in \cite{Laz}. +In this case, it is reasonable +to call the GROEBNER package with the answer of INVBASE as input +information in order to compute the reduced Gr\"obner basis under the +same variable and term ordering.\\ +Though the INVBASE package supports computing involutive bases in any +admissible term ordering, +it is reasonable to compute them only for the total-degree term +orderings. The package includes a special algorithm for conversion +of total-degree involutive bases into the triangular bases +in the lexicographical term ordering that is desirable for +finding solutions. Normally the sum of timings for these two +computations is much less than the timing for direct computation +of the lexicographical involutive bases. As a rule, the result +of the conversion algorithm is a reduced Gr\"obner basis in the +lexicographical term ordering. However, because of some gaps in +the current version of the algorithm, +there may be rare situations when the resulting triangular set +does not possess the formal property of Gr\"obner bases. +Anyway, we recommend using the GROEBNER package with the result +of the conversion algorithm as input in order either to check +the Gr\"obner bases property or to transform the result into a +lexicographical Gr\"obner basis. +\section{The Basic Operators} +\subsection{Term Ordering} +The following term order modes are available: +$$ REVGRADLEX,\; GRADLEX,\; LEX $$ +These modes have the same meaning as for the GROEBNER package.\\ +All orderings are based on an ordering among the variables. +For each pair of variables an order relation $>$ must be defined, +e.g. $x>y$. The term ordering mode as well as the order of variables +are set by the operator +$$ INVTORDER\,,\{x_1,...,x_n\} $$ +where $$ is one of the term order modes listed above. +The notion of $\{x_1,...,x_n\}$ as a list of variables +at the same time means $x_1>...>x_n$. +\vskip 0.1cm +\noindent +{\bf Example 1.} +$$ INVTORDER\>\,REVGRADLEX,\{x,y,z\} $$ +sets the reverse graduated term ordering based on the variable +order $x>y>z$.\\ +The operator $INVTORDER$ may be omitted. The default term order mode +is $REV\-GRADLEX$ and the default decreasing variable order is +alphabetical (or, more generally, the default REDUCE kernel order). +Furthermore, the list of variables in the $INVTORDER$ may be omitted. +In this case the default variable order is used. +\subsection{Computing Involutive Bases} +To compute the involutive basis of ideal generated by the set of +polynomials $\{p_1,...,p_m\}$ one should type the command +$$ INVBASE \> \{p_1,...,p_m\} $$ +where $p_i$ are polynomials in variables listed in the +$INVTORDER$ operator. If some kernels in $p_i$ were not listed +previously in the $INVTORDER$ operator they are considered as +parameters, i.e. they are considered part of the coefficients of +polynomials. If $INVTORDER$ was omitted, all the kernels +in $p_i$ are considered as variables with the default REDUCE +kernel order.\\ +The coefficients of polynomials $p_i$ may be integers as well as +rational numbers (or, accordingly, polynomials and rational functions +in the parametric case). The computations modulo prime numbers are +also available. For this purpose one should type the REDUCE commands +$$ ON \> MODULAR;\> SETMOD \> p; $$ +where $p$ is a prime number.\\ +The value of the $INVBASE$ function is a list of integer polynomials +$\{g_1,...,g_n\}$ representing an involutive basis of a given ideal.\\ +\newpage +\noindent +{\bf Example 2.} +\begin{eqnarray*} +& & INVTORDER \> REVGRADLEX,\{x,y,z\}; \\ +& & g:= INVBASE \> \{4*x**2 + x*y**2 - z + 1/4,\> + 2*x + y**2*z + 1/2,\> \\ +& & x**2*z - 1/2*x - y**2 \}; +\end{eqnarray*} +The resulting involutive basis in the reverse graduate ordering is +\begin{eqnarray*} +g := \{& & 8*x*y*z^3 - 2*x*y*z^2 + 4*y^3 - \\ +& & 4*y*z^2 + 16*x*y + 17*y*z - 4*y,\\ +& & 8*y^4 - 8*x*z^2 - 256*y^2 + 2*x*z + 64*z^2 - 96*x + 20*z - 9,\\ +& & 2*y^3*z + 4*x*y + y,\\ +& & 8*x*z^3 - 2*x*z^2 + 4*y^2 - 4*z^2 + 16*x + 17*z - 4,\\ +& & - 4*y*z^3 - 8*y^3 + 6*x*y*z + y*z^2 - 36*x*y - 8*y,\\ +& & 4*x*y^2 + 32*y^2 - 8*z^2 + 12*x - 2*z + 1,\\ +& & 2*y^2*z + 4*x + 1,\\ +& & - 4*z^3 - 8*y^2 + 6*x*z + z^2 - 36*x - 8,\\ +& & 8*x^2 - 16*y^2 + 4*z^2 - 6*x - z \quad \} +\end{eqnarray*} +To convert it into a lexicographical Gr\"obner basis one should type +$$ h:=INVLEX\>g; $$ +The result is +\begin{eqnarray*} +h :=\{& &3976*x + 37104*z^6 - 600*z^5 + 2111*z^4 + \\ +& & 122062*z^3 + 232833*z^2 - 680336*z + 288814,\\ +& & 1988*y^2 - 76752*z^6 + 1272*z^5 - 4197*z^4 - \\ +& & 251555*z^3 - 481837*z^2 + 1407741*z - 595666,\\ +& & 16*z^7 - 8*z^6 + z^5 + 52*z^4 + + 75*z^3 - 342*z^2 + 266*z - 60 \quad \} +\end{eqnarray*} +In the case of ``sparse'' positive-dimensioned system +when the involutive basis in the sense of \cite{Lille} does not exist, +you get the error message $$ *****\> MAXIMUM \> DEGREE \> BOUND \> +EXCEEDED $$ The resulting list of polynomials which is not an involutive +basis is stored in the share variable INVTEMPBASIS. In this case +it is reasonable to call the GROEBNER package with the value of +INVTEMPBASIS as input under the same variable and term ordering. + +\begin{thebibliography}{99} + +\bibitem{Lille} +Zharkov A.Yu., Blinkov Yu.A. Involution Approach to Solving Systems +of Algebraic Equations. Proceedings of the IMACS '93, 1993, 11-16. + +\bibitem{Buch} +Buchberger B. Gr\"obner bases: an Algorithmic Method in Polynomial +Ideal Theory. In: (Bose N.K., ed.) Recent Trends in Multidimensional +System Theory, Reidel, 1985. + +\bibitem{Laz} +Lazard D. Gr\"obner Bases, Gaussian Elimination and Resolution of +Systems of Algebraic Equations. Proceedings of EUROCAL '83. +Lecture Notes in Computer Science 162, Springer 1983, 146-157. + +\end{thebibliography} + +\end{document} Index: r36/doc/LAPLACE.DOC ================================================================== --- r36/doc/LAPLACE.DOC +++ r36/doc/LAPLACE.DOC @@ -1,71 +1,71 @@ - - SOFIA LAPLACE AND INVERSE LAPLACE TRANSFORM PACKAGE - - C. Kazasov, M. Spiridonova, V. Tomov - - -Reference: Christomir Kazasov, Laplace Transformations in REDUCE 3, Proc. - Eurocal '87, Lecture Notes in Comp. Sci., Springer-Verlag - (1987) 132-133. - -Some hints on how to use to use this package: - -Syntax: - - LAPLACE(,,) - - INVLAP(,,) - -where is the expression to be transformed, is the source -variable (in most cases depends explicitly of this variable) and - is the target variable. If is omitted, the package uses -an internal variable lp!& or il!&, respectively. - -The following switches can be used to control the transformations: - -lmon: If on, sin, cos, sinh and cosh are converted by LAPLACE into - exponentials, - -lhyp: If on, expressions e**(~x) are converted by INVLAP into hyperbolic - functions sinh and cosh, - -ltrig: If on, expressions e**(~x) are converted by INVLAP into - trigonometric functions sin and cos. - -The system can be extended by adding Laplace transformation rules for -single functions by rules or rule sets. In such a rule the source -variable MUST be free, the target variable MUST be il!& for LAPLACE and -lp!& for INVLAP and the third parameter should be omitted. Also rules for -transforming derivatives are entered in such a form. - -Examples: - - let {laplace(log(~x),x) => -log(gam * il!&)/il!&, - invlap(log(gam * ~x)/x,x) => -log(lp!&)}; - - operator f; - let{ - laplace(df(f(~x),x),x) => il!&*laplace(f(x),x) - sub(x=0,f(x)), - - laplace(df(f(~x),x,~n),x) => il!&**n*laplace(f(x),x) - - for i:=n-1 step -1 until 0 sum - sub(x=0, df(f(x),x,n-1-i)) * il!&**i - when fixp n, - - laplace(f(~x),x) = f(il!&) - }; - -Remarks about some functions: - -The DELTA and GAMMA functions are known. - -ONE is the name of the unit step function. - -INTL is a parametrized integral function - - intl(,,0,) - - which means "Integral of wrt taken from 0 to ", -e.g. intl(2*y**2,y,0,x) which is formally a function in x. - -We recommend reading the file LAPLACE.TST for a further introduction. + + SOFIA LAPLACE AND INVERSE LAPLACE TRANSFORM PACKAGE + + C. Kazasov, M. Spiridonova, V. Tomov + + +Reference: Christomir Kazasov, Laplace Transformations in REDUCE 3, Proc. + Eurocal '87, Lecture Notes in Comp. Sci., Springer-Verlag + (1987) 132-133. + +Some hints on how to use to use this package: + +Syntax: + + LAPLACE(,,) + + INVLAP(,,) + +where is the expression to be transformed, is the source +variable (in most cases depends explicitly of this variable) and + is the target variable. If is omitted, the package uses +an internal variable lp!& or il!&, respectively. + +The following switches can be used to control the transformations: + +lmon: If on, sin, cos, sinh and cosh are converted by LAPLACE into + exponentials, + +lhyp: If on, expressions e**(~x) are converted by INVLAP into hyperbolic + functions sinh and cosh, + +ltrig: If on, expressions e**(~x) are converted by INVLAP into + trigonometric functions sin and cos. + +The system can be extended by adding Laplace transformation rules for +single functions by rules or rule sets. In such a rule the source +variable MUST be free, the target variable MUST be il!& for LAPLACE and +lp!& for INVLAP and the third parameter should be omitted. Also rules for +transforming derivatives are entered in such a form. + +Examples: + + let {laplace(log(~x),x) => -log(gam * il!&)/il!&, + invlap(log(gam * ~x)/x,x) => -log(lp!&)}; + + operator f; + let{ + laplace(df(f(~x),x),x) => il!&*laplace(f(x),x) - sub(x=0,f(x)), + + laplace(df(f(~x),x,~n),x) => il!&**n*laplace(f(x),x) - + for i:=n-1 step -1 until 0 sum + sub(x=0, df(f(x),x,n-1-i)) * il!&**i + when fixp n, + + laplace(f(~x),x) = f(il!&) + }; + +Remarks about some functions: + +The DELTA and GAMMA functions are known. + +ONE is the name of the unit step function. + +INTL is a parametrized integral function + + intl(,,0,) + + which means "Integral of wrt taken from 0 to ", +e.g. intl(2*y**2,y,0,x) which is formally a function in x. + +We recommend reading the file LAPLACE.TST for a further introduction. Index: r36/doc/LIE.BIB ================================================================== --- r36/doc/LIE.BIB +++ r36/doc/LIE.BIB @@ -1,22 +1,22 @@ -@INPROCEEDINGS{cssmp92, - AUTHOR = "C. Schoebel", - TITLE = "Classification of Real n-Dimensional Lie Algebras with a - Low-Dimensional Derived Algebra", - BOOKTITLE = "Proc. {Symposium on Mathematical Physics} '92", - YEAR = 1993} - -@ARTICLE{ntz-preprint27/92, - AUTHOR = "F. Schoebel", - TITLE = "The Symbolic Classification of Real Four-Dimensional Lie Algebras", - BOOKTITLE = "NTZ-Preprint Nr.27/92", - PUBLISHER = "Universitaet Leipzig", - ADDRESS = "Leipzig", - YEAR = 1992} - -@ARTICLE{mmpreprint1979, - AUTHOR = "M.A.H. MacCallum", - TITLE = "On the Classification of the Real four-dimensional Lie Algebras", - BOOKTITLE = "Preprint, Queen Mary College", - PUBLISHER = "Queen Mary College", - ADDRESS = "London", - YEAR = 1979} +@INPROCEEDINGS{cssmp92, + AUTHOR = "C. Schoebel", + TITLE = "Classification of Real n-Dimensional Lie Algebras with a + Low-Dimensional Derived Algebra", + BOOKTITLE = "Proc. {Symposium on Mathematical Physics} '92", + YEAR = 1993} + +@ARTICLE{ntz-preprint27/92, + AUTHOR = "F. Schoebel", + TITLE = "The Symbolic Classification of Real Four-Dimensional Lie Algebras", + BOOKTITLE = "NTZ-Preprint Nr.27/92", + PUBLISHER = "Universitaet Leipzig", + ADDRESS = "Leipzig", + YEAR = 1992} + +@ARTICLE{mmpreprint1979, + AUTHOR = "M.A.H. MacCallum", + TITLE = "On the Classification of the Real four-dimensional Lie Algebras", + BOOKTITLE = "Preprint, Queen Mary College", + PUBLISHER = "Queen Mary College", + ADDRESS = "London", + YEAR = 1979} Index: r36/doc/LIE.TEX ================================================================== --- r36/doc/LIE.TEX +++ r36/doc/LIE.TEX @@ -1,155 +1,155 @@ -\documentstyle{article} -\parindent0cm -%\textwidth 15.5cm\textheight 22.0cm\columnwidth\textwidth -%\hoffset-1.5cm\voffset-1.5cm -\begin{document} -%\parskip 10pt plus 1pt \parindent 0pt -\title{The {LIE} Package} -\author{Carsten and Franziska Sch\"obel\\ -The Leipzig University, Computer Science Dept.\\ -Augustusplatz 10/11, O-7010 Leipzig, Germany\\ -Email: cschoeb@aix550.informatik.uni-leipzig.de} -\date{22 January 1993} -\maketitle -{\bf LIE} is a package of functions for the classification of real n-dimensional -Lie algebras. It consists of two modules: {\bf liendmc1} and {\bf lie1234}. -\\[0.3cm]{\large\bf liendmc1}\\[0.1cm] -With the help of the functions in this module real n-dimensional Lie algebras -$L$ with a derived algebra $L^{(1)}$ of dimension 1 can be classified. $L$ has -to be defined by its structure constants $c_{ij}^k$ in the basis -$\{X_1,\ldots,X_n\}$ with $[X_i,X_j]=c_{ij}^k X_k$. The user must define an -ARRAY LIENSTRUCIN($n,n,n$) with n being the dimension of the Lie algebra $L$. -The structure constants LIENSTRUCIN($i,j,k$):=$c_{ij}^k$ for $i). -\end{verbatim} -{\tt } corresponds to the dimension $n$. The procedure simplifies -the structure of $L$ performing real linear transformations. The returned -value is a list of the form -\begin{verbatim} - (i) {LIE_ALGEBRA(2),COMMUTATIVE(n-2)} or - (ii) {HEISENBERG(k),COMMUTATIVE(n-k)} -\end{verbatim} -with $3\leq k\leq n$, $k$ odd.\\ -The concepts correspond to the following theorem ({\tt LIE\_ALGEBRA(2)} -$\rightarrow L_2$, {\tt HEISENBERG(k)} $\rightarrow H_k$ and -{\tt COMMUTATIVE(n-k)} $\rightarrow C_{n-k}$):\\[0.2cm] -{\bf Theorem.} Every real $n$-dimensional Lie algebra $L$ with a 1-dimensional -derived algebra can be decomposed into one of the following forms:\\[0.1cm] -\hspace*{0.3cm} (i) $C(L)\cap L^{(1)}=\{0\}\, :\; L_2\oplus C_{n-2}$ -or\\[0.05cm] -\hspace*{0.3cm} (ii) $C(L)\cap L^{(1)}=L^{(1)}\, :\; H_k\oplus C_{n-k}\quad -(k=2r-1,\, r\geq 2)$, with\newpage -\hspace*{0.3cm} 1. $C(L)=C_j\oplus (L^{(1)}\cap C(L))$ -and dim$\,C_j=j$ ,\\[0.05cm] -\hspace*{0.3cm} 2. $L_2$ is generated by -$Y_1,Y_2$ with $[Y_1,Y_2]=Y_1$ ,\\[0.05cm] -\hspace*{0.3cm} 3. $H_k$ is generated by $\{Y_1,\ldots,Y_k\}$ with\\ -\hspace*{0.7cm} $[Y_2,Y_3]=\cdots =[Y_{k-1},Y_k]=Y_1$.\\[0.2cm] -(cf. \cite{cssmp92})\\[0.2cm] -The returned list is also stored as LIE\_LIST. The matrix LIENTRANS gives the -transformation from the given basis $\{X_1,\ldots ,X_n\}$ into the standard -basis $\{Y_1,\ldots ,Y_n\}$: $Y_j=($LIENTRANS$)_j^k X_k$.\\[0.1cm] -A more detailed output can be obtained by turning on the switch TR\_LIE: -\begin{verbatim} - ON TR_LIE; -\end{verbatim} -before the procedure LIENDIMCOM1 is called.\\[0.1cm] -The returned list could be an input for a data bank in which mathematical -relevant properties of the obtained Lie algebras are stored.\\[0.3cm] -{\large\bf lie1234}\\[0.1cm] -This part of the package classifies real low-dimensional Lie algebras $L$ -of the dimension -$n:=$dim$\,L=1,2,3,4$. $L$ is also given by its structure constants $c_{ij}^k$ -in the basis $\{X_1,\ldots,X_n\}$ with $[X_i,X_j]=c_{ij}^k X_k$. An ARRAY -LIESTRIN($n,n,n$) has to be defined and LIESTRIN($i,j,k$):=$c_{ij}^k$ for -$i). -\end{verbatim} -{\tt } should be the dimension of the Lie algebra $L$. The procedure -stepwise simplifies the commutator relations of $L$ using properties of -invariance like the dimension of the centre, of the derived algebra, -unimodularity etc. The returned value has the form: -\begin{verbatim} - {LIEALG(n),COMTAB(m)}, -\end{verbatim} -where $m$ corresponds to the number of the standard form (basis: -$\{Y_1,\ldots,Y_n\}$) in an enumeration scheme. The corresponding enumeration -schemes are listed below (cf. \cite{ntz-preprint27/92},\cite{mmpreprint1979}). -In case that the standard form in the enumeration scheme depends on one (or two) -parameter(s) $p_1$ (and $p_2$) the list is expanded to: -\begin{verbatim} - {LIEALG(n),COMTAB(m),p1,p2}. -\end{verbatim} -This returned value is also stored as LIE\_CLASS. The linear transformation from -the basis $\{X_1,\ldots,X_n\}$ into the basis of the standard form -$\{Y_1,\ldots,Y_n\}$ is given by the matrix LIEMAT: -$Y_j=($LIEMAT$)_j^k X_k$.\newpage -By turning on the switch TR\_LIE: -\begin{verbatim} - ON TR_LIE; -\end{verbatim} -before the procedure LIECLASS is called the output contains not only the -list LIE\_CLASS but also the non-vanishing commutator relations in the -standard form.\\[0.1cm] -By the value $m$ and the parameters further examinations of the Lie algebra -are possible, especially if in a data bank mathematical relevant properties -of the enumerated standard forms are stored.\\[0.3cm] -{\large\bf Enumeration schemes for lie1234}\\[0.2cm] -\hspace*{0.3cm}\begin{tabular}{l|l}returned list LIE\_CLASS& -the corresponding commutator relations\\[0.1cm]\hline -{LIEALG(1),COMTAB(0)}&commutative case\\[0.1cm]\hline -{LIEALG(2),COMTAB(0)}&commutative case\\[0.1cm] -{LIEALG(2),COMTAB(1)}&$[Y_1,Y_2]=Y_2$\\[0.1cm]\hline -{LIEALG(3),COMTAB(0)}&commutative case\\[0.1cm] -{LIEALG(3),COMTAB(1)}&$[Y_1,Y_2]=Y_3$\\[0.1cm] -{LIEALG(3),COMTAB(2)}&$[Y_1,Y_3]=Y_3$\\[0.1cm] -{LIEALG(3),COMTAB(3)}&$[Y_1,Y_3]=Y_1,[Y_2,Y_3]=Y_2$\\[0.1cm] -{LIEALG(3),COMTAB(4)}&$[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(3),COMTAB(5)}&$[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(3),COMTAB(6)}&$[Y_1,Y_3]=-Y_1+p_1 Y_2,[Y_2,Y_3]=Y_1,p_1\neq 0$\\[0.1cm] -{LIEALG(3),COMTAB(7)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(3),COMTAB(8)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm]\hline -{LIEALG(4),COMTAB(0)}&commutative case\\[0.1cm] -{LIEALG(4),COMTAB(1)}&$[Y_1,Y_4]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(2)}&$[Y_2,Y_4]=Y_1$\\[0,1cm] -{LIEALG(4),COMTAB(3)}&$[Y_1,Y_3]=Y_1,[Y_2,Y_4]=Y_2$\\[0.1cm] -{LIEALG(4),COMTAB(4)}&$[Y_1,Y_3]=-Y_2,[Y_2,Y_4]=Y_2,$\\ - &$[Y_1,Y_4]=[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(5)}&$[Y_2,Y_4]=Y_2,[Y_1,Y_4]=[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(6)}&$[Y_2,Y_4]=Y_1,[Y_3,Y_4]=Y_2$\\[0.1cm] -{LIEALG(4),COMTAB(7)}&$[Y_2,Y_4]=Y_2,[Y_3,Y_4]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(8)}&$[Y_1,Y_4]=-Y_2,[Y_2,Y_4]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(9)}&$[Y_1,Y_4]=-Y_1+p_1 Y_2,[Y_2,Y_4]=Y_1,p_1\neq 0$\\[0.1cm] -{LIEALG(4),COMTAB(10)}&$[Y_1,Y_4]=Y_1,[Y_2,Y_4]=Y_2$\\[0.1cm] -{LIEALG(4),COMTAB(11)}&$[Y_1,Y_4]=Y_2,[Y_2,Y_4]=Y_1$ -\end{tabular}\\ -\hspace*{0.3cm}\begin{tabular}{l|l}returned list LIE\_CLASS& -the corresponding commutator relations\\[0.1cm]\hline -{LIEALG(4),COMTAB(12)}&$[Y_1,Y_4]=Y_1+Y_2,[Y_2,Y_4]=Y_2+Y_3,$\\ - &$[Y_3,Y_4]=Y_3$\\[0.1cm] -{LIEALG(4),COMTAB(13)}&$[Y_1,Y_4]=Y_1,[Y_2,Y_4]=p_1 Y_2,[Y_3,Y_4]=p_2 Y_3,$\\ - &$p_1,p_2\neq 0$\\[0.1cm] -{LIEALG(4),COMTAB(14)}&$[Y_1,Y_4]=p_1 Y_1+Y_2,[Y_2,Y_4]=-Y_1+p_1 Y_2,$\\ - &$[Y_3,Y_4]=p_2 Y_3,p_2\neq 0$\\[0.1cm] -{LIEALG(4),COMTAB(15)}&$[Y_1,Y_4]=p_1 Y_1+Y_2,[Y_2,Y_4]=p_1 Y_2,$\\ - &$[Y_3,Y_4]=Y_3,p_1\neq 0$\\[0.1cm] -{LIEALG(4),COMTAB(16)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ - &$[Y_2,Y_4]=(1+p_1) Y_2,[Y_3,Y_4]=(1-p_1) Y_3,$\\ - &$p_1\geq 0$\\[0.1cm] -{LIEALG(4),COMTAB(17)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ - &$[Y_2,Y_4]=Y_2-p_1 Y_3,[Y_3,Y_4]=p_1 Y_2+Y_3,$\\ - &$p_1\neq 0$\\[0.1cm] -{LIEALG(4),COMTAB(18)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ - &$[Y_2,Y_4]=Y_2+Y_3,[Y_3,Y_4]=Y_3$\\[0.1cm] -{LIEALG(4),COMTAB(19)}&$[Y_2,Y_3]=Y_1,[Y_2,Y_4]=Y_3,[Y_3,Y_4]=Y_2$\\[0.1cm] -{LIEALG(4),COMTAB(20)}&$[Y_2,Y_3]=Y_1,[Y_2,Y_4]=-Y_3,[Y_3,Y_4]=Y_2$\\[0.1cm] -{LIEALG(4),COMTAB(21)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] -{LIEALG(4),COMTAB(22)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$ -\end{tabular} -\bibliography{lie} -\bibliographystyle{plain} -\end{document} +\documentstyle{article} +\parindent0cm +%\textwidth 15.5cm\textheight 22.0cm\columnwidth\textwidth +%\hoffset-1.5cm\voffset-1.5cm +\begin{document} +%\parskip 10pt plus 1pt \parindent 0pt +\title{The {LIE} Package} +\author{Carsten and Franziska Sch\"obel\\ +The Leipzig University, Computer Science Dept.\\ +Augustusplatz 10/11, O-7010 Leipzig, Germany\\ +Email: cschoeb@aix550.informatik.uni-leipzig.de} +\date{22 January 1993} +\maketitle +{\bf LIE} is a package of functions for the classification of real n-dimensional +Lie algebras. It consists of two modules: {\bf liendmc1} and {\bf lie1234}. +\\[0.3cm]{\large\bf liendmc1}\\[0.1cm] +With the help of the functions in this module real n-dimensional Lie algebras +$L$ with a derived algebra $L^{(1)}$ of dimension 1 can be classified. $L$ has +to be defined by its structure constants $c_{ij}^k$ in the basis +$\{X_1,\ldots,X_n\}$ with $[X_i,X_j]=c_{ij}^k X_k$. The user must define an +ARRAY LIENSTRUCIN($n,n,n$) with n being the dimension of the Lie algebra $L$. +The structure constants LIENSTRUCIN($i,j,k$):=$c_{ij}^k$ for $i). +\end{verbatim} +{\tt } corresponds to the dimension $n$. The procedure simplifies +the structure of $L$ performing real linear transformations. The returned +value is a list of the form +\begin{verbatim} + (i) {LIE_ALGEBRA(2),COMMUTATIVE(n-2)} or + (ii) {HEISENBERG(k),COMMUTATIVE(n-k)} +\end{verbatim} +with $3\leq k\leq n$, $k$ odd.\\ +The concepts correspond to the following theorem ({\tt LIE\_ALGEBRA(2)} +$\rightarrow L_2$, {\tt HEISENBERG(k)} $\rightarrow H_k$ and +{\tt COMMUTATIVE(n-k)} $\rightarrow C_{n-k}$):\\[0.2cm] +{\bf Theorem.} Every real $n$-dimensional Lie algebra $L$ with a 1-dimensional +derived algebra can be decomposed into one of the following forms:\\[0.1cm] +\hspace*{0.3cm} (i) $C(L)\cap L^{(1)}=\{0\}\, :\; L_2\oplus C_{n-2}$ +or\\[0.05cm] +\hspace*{0.3cm} (ii) $C(L)\cap L^{(1)}=L^{(1)}\, :\; H_k\oplus C_{n-k}\quad +(k=2r-1,\, r\geq 2)$, with\newpage +\hspace*{0.3cm} 1. $C(L)=C_j\oplus (L^{(1)}\cap C(L))$ +and dim$\,C_j=j$ ,\\[0.05cm] +\hspace*{0.3cm} 2. $L_2$ is generated by +$Y_1,Y_2$ with $[Y_1,Y_2]=Y_1$ ,\\[0.05cm] +\hspace*{0.3cm} 3. $H_k$ is generated by $\{Y_1,\ldots,Y_k\}$ with\\ +\hspace*{0.7cm} $[Y_2,Y_3]=\cdots =[Y_{k-1},Y_k]=Y_1$.\\[0.2cm] +(cf. \cite{cssmp92})\\[0.2cm] +The returned list is also stored as LIE\_LIST. The matrix LIENTRANS gives the +transformation from the given basis $\{X_1,\ldots ,X_n\}$ into the standard +basis $\{Y_1,\ldots ,Y_n\}$: $Y_j=($LIENTRANS$)_j^k X_k$.\\[0.1cm] +A more detailed output can be obtained by turning on the switch TR\_LIE: +\begin{verbatim} + ON TR_LIE; +\end{verbatim} +before the procedure LIENDIMCOM1 is called.\\[0.1cm] +The returned list could be an input for a data bank in which mathematical +relevant properties of the obtained Lie algebras are stored.\\[0.3cm] +{\large\bf lie1234}\\[0.1cm] +This part of the package classifies real low-dimensional Lie algebras $L$ +of the dimension +$n:=$dim$\,L=1,2,3,4$. $L$ is also given by its structure constants $c_{ij}^k$ +in the basis $\{X_1,\ldots,X_n\}$ with $[X_i,X_j]=c_{ij}^k X_k$. An ARRAY +LIESTRIN($n,n,n$) has to be defined and LIESTRIN($i,j,k$):=$c_{ij}^k$ for +$i). +\end{verbatim} +{\tt } should be the dimension of the Lie algebra $L$. The procedure +stepwise simplifies the commutator relations of $L$ using properties of +invariance like the dimension of the centre, of the derived algebra, +unimodularity etc. The returned value has the form: +\begin{verbatim} + {LIEALG(n),COMTAB(m)}, +\end{verbatim} +where $m$ corresponds to the number of the standard form (basis: +$\{Y_1,\ldots,Y_n\}$) in an enumeration scheme. The corresponding enumeration +schemes are listed below (cf. \cite{ntz-preprint27/92},\cite{mmpreprint1979}). +In case that the standard form in the enumeration scheme depends on one (or two) +parameter(s) $p_1$ (and $p_2$) the list is expanded to: +\begin{verbatim} + {LIEALG(n),COMTAB(m),p1,p2}. +\end{verbatim} +This returned value is also stored as LIE\_CLASS. The linear transformation from +the basis $\{X_1,\ldots,X_n\}$ into the basis of the standard form +$\{Y_1,\ldots,Y_n\}$ is given by the matrix LIEMAT: +$Y_j=($LIEMAT$)_j^k X_k$.\newpage +By turning on the switch TR\_LIE: +\begin{verbatim} + ON TR_LIE; +\end{verbatim} +before the procedure LIECLASS is called the output contains not only the +list LIE\_CLASS but also the non-vanishing commutator relations in the +standard form.\\[0.1cm] +By the value $m$ and the parameters further examinations of the Lie algebra +are possible, especially if in a data bank mathematical relevant properties +of the enumerated standard forms are stored.\\[0.3cm] +{\large\bf Enumeration schemes for lie1234}\\[0.2cm] +\hspace*{0.3cm}\begin{tabular}{l|l}returned list LIE\_CLASS& +the corresponding commutator relations\\[0.1cm]\hline +{LIEALG(1),COMTAB(0)}&commutative case\\[0.1cm]\hline +{LIEALG(2),COMTAB(0)}&commutative case\\[0.1cm] +{LIEALG(2),COMTAB(1)}&$[Y_1,Y_2]=Y_2$\\[0.1cm]\hline +{LIEALG(3),COMTAB(0)}&commutative case\\[0.1cm] +{LIEALG(3),COMTAB(1)}&$[Y_1,Y_2]=Y_3$\\[0.1cm] +{LIEALG(3),COMTAB(2)}&$[Y_1,Y_3]=Y_3$\\[0.1cm] +{LIEALG(3),COMTAB(3)}&$[Y_1,Y_3]=Y_1,[Y_2,Y_3]=Y_2$\\[0.1cm] +{LIEALG(3),COMTAB(4)}&$[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(3),COMTAB(5)}&$[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(3),COMTAB(6)}&$[Y_1,Y_3]=-Y_1+p_1 Y_2,[Y_2,Y_3]=Y_1,p_1\neq 0$\\[0.1cm] +{LIEALG(3),COMTAB(7)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(3),COMTAB(8)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm]\hline +{LIEALG(4),COMTAB(0)}&commutative case\\[0.1cm] +{LIEALG(4),COMTAB(1)}&$[Y_1,Y_4]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(2)}&$[Y_2,Y_4]=Y_1$\\[0,1cm] +{LIEALG(4),COMTAB(3)}&$[Y_1,Y_3]=Y_1,[Y_2,Y_4]=Y_2$\\[0.1cm] +{LIEALG(4),COMTAB(4)}&$[Y_1,Y_3]=-Y_2,[Y_2,Y_4]=Y_2,$\\ + &$[Y_1,Y_4]=[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(5)}&$[Y_2,Y_4]=Y_2,[Y_1,Y_4]=[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(6)}&$[Y_2,Y_4]=Y_1,[Y_3,Y_4]=Y_2$\\[0.1cm] +{LIEALG(4),COMTAB(7)}&$[Y_2,Y_4]=Y_2,[Y_3,Y_4]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(8)}&$[Y_1,Y_4]=-Y_2,[Y_2,Y_4]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(9)}&$[Y_1,Y_4]=-Y_1+p_1 Y_2,[Y_2,Y_4]=Y_1,p_1\neq 0$\\[0.1cm] +{LIEALG(4),COMTAB(10)}&$[Y_1,Y_4]=Y_1,[Y_2,Y_4]=Y_2$\\[0.1cm] +{LIEALG(4),COMTAB(11)}&$[Y_1,Y_4]=Y_2,[Y_2,Y_4]=Y_1$ +\end{tabular}\\ +\hspace*{0.3cm}\begin{tabular}{l|l}returned list LIE\_CLASS& +the corresponding commutator relations\\[0.1cm]\hline +{LIEALG(4),COMTAB(12)}&$[Y_1,Y_4]=Y_1+Y_2,[Y_2,Y_4]=Y_2+Y_3,$\\ + &$[Y_3,Y_4]=Y_3$\\[0.1cm] +{LIEALG(4),COMTAB(13)}&$[Y_1,Y_4]=Y_1,[Y_2,Y_4]=p_1 Y_2,[Y_3,Y_4]=p_2 Y_3,$\\ + &$p_1,p_2\neq 0$\\[0.1cm] +{LIEALG(4),COMTAB(14)}&$[Y_1,Y_4]=p_1 Y_1+Y_2,[Y_2,Y_4]=-Y_1+p_1 Y_2,$\\ + &$[Y_3,Y_4]=p_2 Y_3,p_2\neq 0$\\[0.1cm] +{LIEALG(4),COMTAB(15)}&$[Y_1,Y_4]=p_1 Y_1+Y_2,[Y_2,Y_4]=p_1 Y_2,$\\ + &$[Y_3,Y_4]=Y_3,p_1\neq 0$\\[0.1cm] +{LIEALG(4),COMTAB(16)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ + &$[Y_2,Y_4]=(1+p_1) Y_2,[Y_3,Y_4]=(1-p_1) Y_3,$\\ + &$p_1\geq 0$\\[0.1cm] +{LIEALG(4),COMTAB(17)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ + &$[Y_2,Y_4]=Y_2-p_1 Y_3,[Y_3,Y_4]=p_1 Y_2+Y_3,$\\ + &$p_1\neq 0$\\[0.1cm] +{LIEALG(4),COMTAB(18)}&$[Y_1,Y_4]=2 Y_1,[Y_2,Y_3]=Y_1,$\\ + &$[Y_2,Y_4]=Y_2+Y_3,[Y_3,Y_4]=Y_3$\\[0.1cm] +{LIEALG(4),COMTAB(19)}&$[Y_2,Y_3]=Y_1,[Y_2,Y_4]=Y_3,[Y_3,Y_4]=Y_2$\\[0.1cm] +{LIEALG(4),COMTAB(20)}&$[Y_2,Y_3]=Y_1,[Y_2,Y_4]=-Y_3,[Y_3,Y_4]=Y_2$\\[0.1cm] +{LIEALG(4),COMTAB(21)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=-Y_2,[Y_2,Y_3]=Y_1$\\[0.1cm] +{LIEALG(4),COMTAB(22)}&$[Y_1,Y_2]=Y_3,[Y_1,Y_3]=Y_2,[Y_2,Y_3]=Y_1$ +\end{tabular} +\bibliography{lie} +\bibliographystyle{plain} +\end{document} Index: r36/doc/LIMITS.TEX ================================================================== --- r36/doc/LIMITS.TEX +++ r36/doc/LIMITS.TEX @@ -1,83 +1,83 @@ -\documentstyle[11pt,reduce]{article} -\title{A REDUCE Limits Package} -\date{} -\author{Stanley L. Kameny \\ Email: stan\%valley.uucp@rand.org} -\begin{document} -\maketitle - -\index{LIMITS package} -LIMITS is a fast limit package for REDUCE for functions which are -continuous except for computable poles and singularities, based on some -earlier work by Ian Cohen and John P. Fitch. The Truncated Power Series -package is used for non-critical points, at which the value of the -function is the constant term in the expansion around that point. -\index{l'H\^opital's rule} -l'H\^opital's rule is used in critical cases, with preprocessing of -$\infty - \infty$ forms and reformatting of product forms in order -to apply l'H\^opital's rule. A limited amount of bounded arithmetic -is also employed where applicable. - -\section{Normal entry points} -\ttindex{LIMIT} -\vspace{.1in} -\noindent {\tt LIMIT}(EXPRN:{\em algebraic}, VAR:{\em kernel}, -LIMPOINT:{\em algebraic}):{\em algebraic} -\vspace{.1in} - -This is the standard way of calling limit, applying all of the methods. The -result is the limit of EXPRN as VAR approaches LIMPOINT. - - -\section{Direction-dependent limits} - -\ttindex{LIMIT+} \ttindex{LIMIT-} -\vspace{.1in} -\noindent {\tt LIMIT!+}(EXPRN:{\em algebraic}, VAR:{\em kernel}, -LIMPOINT:{\em algebraic}):{\em algebraic} \\ -\noindent {\tt LIMIT!-}(EXPRN:{\em algebraic}, VAR:{\em kernel}, -LIMPOINT:{\em algebraic}):{\em algebraic} -\vspace{.1in} - -If the limit depends upon the direction of approach to the {\tt LIMPOINT}, -the functions {\tt LIMIT!+} and {\tt LIMIT!-} may be used. They are -defined by: - -\vspace{.1in} -\noindent{\tt LIMIT!+ (LIMIT!-)} (EXP,VAR,LIMPOINT) $\rightarrow$ \\ -\hspace*{2em}{\tt LIMIT}(EXP*,$\epsilon$,0) -EXP*=sub(VAR=VAR+(-)$\epsilon^2$,EXP) - -\section{Diagnostic Functions} - -\ttindex{LIMIT0} -\vspace{.1in} -\noindent {\tt LIMIT0}(EXPRN:{\em algebraic}, VAR:{\em kernel}, -LIMPOINT:{\em algebraic}):{\em algebraic} -\vspace{.1in} - -This function will use all parts of the limits package, but it does not -combine log terms before taking limits, so it may fail if there is a sum -of log terms which have a removable singularity in some of the terms. - -\ttindex{LIMIT1} -\vspace{.1in} -\noindent {\tt LIMIT1}(EXPRN:{\em algebraic}, VAR:{\em kernel}, -LIMPOINT:{\em algebraic}):{\em algebraic} -\vspace{.1in} - -\index{TPS package} -This function uses the TPS branch only, and will fail if the limit point is -singular. - -\ttindex{LIMIT2} -\vspace{.1in} -\begin{tabbing} -{\tt LIMIT2}(\=TOP:{\em algebraic}, \\ -\>BOT:{\em algebraic}, \\ -\>VAR:{\em kernel}, \\ -\>LIMPOINT:{\em algebraic}):{\em algebraic} -\end{tabbing} -\vspace{.1in} - -This function applies l'H\^opital's rule to the quotient (TOP/BOT). -\end{document} +\documentstyle[11pt,reduce]{article} +\title{A REDUCE Limits Package} +\date{} +\author{Stanley L. Kameny \\ Email: stan\%valley.uucp@rand.org} +\begin{document} +\maketitle + +\index{LIMITS package} +LIMITS is a fast limit package for REDUCE for functions which are +continuous except for computable poles and singularities, based on some +earlier work by Ian Cohen and John P. Fitch. The Truncated Power Series +package is used for non-critical points, at which the value of the +function is the constant term in the expansion around that point. +\index{l'H\^opital's rule} +l'H\^opital's rule is used in critical cases, with preprocessing of +$\infty - \infty$ forms and reformatting of product forms in order +to apply l'H\^opital's rule. A limited amount of bounded arithmetic +is also employed where applicable. + +\section{Normal entry points} +\ttindex{LIMIT} +\vspace{.1in} +\noindent {\tt LIMIT}(EXPRN:{\em algebraic}, VAR:{\em kernel}, +LIMPOINT:{\em algebraic}):{\em algebraic} +\vspace{.1in} + +This is the standard way of calling limit, applying all of the methods. The +result is the limit of EXPRN as VAR approaches LIMPOINT. + + +\section{Direction-dependent limits} + +\ttindex{LIMIT+} \ttindex{LIMIT-} +\vspace{.1in} +\noindent {\tt LIMIT!+}(EXPRN:{\em algebraic}, VAR:{\em kernel}, +LIMPOINT:{\em algebraic}):{\em algebraic} \\ +\noindent {\tt LIMIT!-}(EXPRN:{\em algebraic}, VAR:{\em kernel}, +LIMPOINT:{\em algebraic}):{\em algebraic} +\vspace{.1in} + +If the limit depends upon the direction of approach to the {\tt LIMPOINT}, +the functions {\tt LIMIT!+} and {\tt LIMIT!-} may be used. They are +defined by: + +\vspace{.1in} +\noindent{\tt LIMIT!+ (LIMIT!-)} (EXP,VAR,LIMPOINT) $\rightarrow$ \\ +\hspace*{2em}{\tt LIMIT}(EXP*,$\epsilon$,0) +EXP*=sub(VAR=VAR+(-)$\epsilon^2$,EXP) + +\section{Diagnostic Functions} + +\ttindex{LIMIT0} +\vspace{.1in} +\noindent {\tt LIMIT0}(EXPRN:{\em algebraic}, VAR:{\em kernel}, +LIMPOINT:{\em algebraic}):{\em algebraic} +\vspace{.1in} + +This function will use all parts of the limits package, but it does not +combine log terms before taking limits, so it may fail if there is a sum +of log terms which have a removable singularity in some of the terms. + +\ttindex{LIMIT1} +\vspace{.1in} +\noindent {\tt LIMIT1}(EXPRN:{\em algebraic}, VAR:{\em kernel}, +LIMPOINT:{\em algebraic}):{\em algebraic} +\vspace{.1in} + +\index{TPS package} +This function uses the TPS branch only, and will fail if the limit point is +singular. + +\ttindex{LIMIT2} +\vspace{.1in} +\begin{tabbing} +{\tt LIMIT2}(\=TOP:{\em algebraic}, \\ +\>BOT:{\em algebraic}, \\ +\>VAR:{\em kernel}, \\ +\>LIMPOINT:{\em algebraic}):{\em algebraic} +\end{tabbing} +\vspace{.1in} + +This function applies l'H\^opital's rule to the quotient (TOP/BOT). +\end{document} Index: r36/doc/LINALG.TEX ================================================================== --- r36/doc/LINALG.TEX +++ r36/doc/LINALG.TEX @@ -1,2358 +1,2358 @@ -\documentstyle[11pt,reduce,fancyheadings]{article} -\title{A Linear Algebra package for \REDUCE{}} -\author{Matt Rebbeck \\ - Konrad-Zuse-Zentrum f\"ur Informationstechnik Berlin} -\date{July 1994} - -\def\foottitle{The Linear Algebra Package} -\pagestyle{fancy} -\lhead[]{{\footnotesize\leftmark}{}} -\rhead[]{\thepage} -\setlength{\headrulewidth}{0.6pt} -\setlength{\footrulewidth}{0.6pt} -\cfoot{} -\rfoot{\small\foottitle} - -%decided against using these. -%\def\ltri{$\triangleleft$} -%\def\rtri{$\triangleright$} -%\newcommand{\tribound}[1]{\rtri#1\ltri} - -\def\exprlist {expr$_{1}$,expr$_{2}$, \ldots ,expr$_{{\tt n}}$} -\def\lineqlist {lin\_eqn$_{1}$,lin\_eqn$_{2}$, \ldots ,lin\_eqn$_{n}$} -\def\matlist {mat$_{1}$,mat$_{2}$, \ldots ,mat$_{n}$} -\def\veclist {vec$_{1}$,vec$_{2}$, \ldots ,vec$_{n}$} - -\def\lazyfootnote{\footnote{If you're feeling lazy then the \{\}'s can - be omitted.}} - -\renewcommand{\thefootnote}{\fnsymbol{footnote}} - -\begin{document} -\maketitle -\index{Linear Algebra package} - -\section{Introduction} -This package provides a selection of functions that are useful -in the world of linear algebra. These functions are described -alphabetically in section 3 of this document and are labelled 3.1 to -3.51. They can be classified into four sections(n.b: the numbers after -the dots signify the function label in section 3). - -\subsection{Basic matrix handling} - -\begin{center} -\begin{tabular}{l l l l l l} -add\_columns & \ldots & 3.1 & -add\_rows & \ldots & 3.2 \\ -add\_to\_columns & \ldots & 3.3 & -add\_to\_rows & \ldots & 3.4 \\ -augment\_columns & \ldots & 3.5 & -char\_poly & \ldots & 3.9 \\ -column\_dim & \ldots & 3.12 & -copy\_into & \ldots & 3.14 \\ -diagonal & \ldots & 3.15 & -extend & \ldots & 3.16 \\ -find\_companion & \ldots & 3.17 & -get\_columns & \ldots & 3.18 \\ -get\_rows & \ldots & 3.19 & -hermitian\_tp & \ldots & 3.21 \\ -matrix\_augment & \ldots & 3.28 & -matrix\_stack & \ldots & 3.30 \\ -minor & \ldots & 3.31 & -mult\_columns & \ldots & 3.32 \\ -mult\_rows & \ldots & 3.33 & -pivot & \ldots & 3.34 \\ -remove\_columns & \ldots & 3.37 & -remove\_rows & \ldots & 3.38 \\ -row\_dim & \ldots & 3.39 & -rows\_pivot & \ldots & 3.40 \\ -stack\_rows & \ldots & 3.43 & -sub\_matrix & \ldots & 3.44 \\ -swap\_columns & \ldots & 3.46 & -swap\_entries & \ldots & 3.47 \\ -swap\_rows & \ldots & 3.48 & -\end{tabular} -\end{center} - -\subsection{Constructors} - -Functions that create matrices. - -\begin{center} -\begin{tabular}{l l l l l l} -band\_matrix & \ldots & 3. 6 & -block\_matrix & \ldots & 3. 7 \\ -char\_matrix & \ldots & 3. 8 & -coeff\_matrix & \ldots & 3. 11 \\ -companion & \ldots & 3. 13 & -hessian & \ldots & 3. 22 \\ -hilbert & \ldots & 3. 23 & -jacobian & \ldots & 3. 24 \\ -jordan\_block & \ldots & 3. 25 & -make\_identity & \ldots & 3. 27 \\ -random\_matrix & \ldots & 3. 36 & -toeplitz & \ldots & 3. 50 \\ -Vandermonde & \ldots & 3. 51 & -Kronecker\_Product & \ldots & 3. 52 -\end{tabular} -\end{center} - -\subsection{High level algorithms} - -\begin{center} -\begin{tabular}{l l l l l l} -char\_poly & \ldots & 3.9 & -cholesky & \ldots & 3.10 \\ -gram\_schmidt & \ldots & 3.20 & -lu\_decom & \ldots & 3.26 \\ -pseudo\_inverse & \ldots & 3.35 & -simplex & \ldots & 3.41 \\ -svd & \ldots & 3.45 & -\end{tabular} -\end{center} - -\vspace*{5mm} -There is a separate {\small NORMFORM}[1] package for computing -the following matrix normal forms in \REDUCE. - -\begin{center} -smithex, smithex\_int, frobenius, ratjordan, jordansymbolic, jordan. -\end{center} - -\subsection{Predicates} - -\begin{center} -\begin{tabular}{l l l l l l} -matrixp & \ldots & 3.29 & -squarep & \ldots & 3.42 \\ -symmetricp & \ldots & 3.49 & -\end{tabular} -\end{center} - -\subsection*{Note on examples:} - -In the examples the matrix ${\cal A}$ will be - -\begin{flushleft} -\begin{math} -{\cal A} = \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 -\end{array} \right) -\end{math} -\end{flushleft} - - -\subsection*{Notation} - -Throughout ${\cal I}$ is used to indicate the identity matrix and -${\cal A}^T$ to indicate the transpose of the matrix ${\cal A}$. - -\section{Getting started} - -If you have not used matrices within {\REDUCE} before then the -following may be helpful. - -\subsection*{Creating matrices} - -Initialisation of matrices takes the following syntax: - -{\tt mat1 := mat((a,b,c),(d,e,f),(g,h,i));} - -will produce - -\begin{flushleft} -\begin{math} -mat1 := \left( \begin{array}{ccc} a & b & c \\ d & e & f \\ g & h & i -\end{array} \right) -\end{math} -\end{flushleft} - -\subsection*{Getting at the entries} - -The (i,$\,$j)'th entry can be accessed by: - -{\tt mat1(i,j);} - -\subsection*{Loading the linear\_algebra package} - -The package is loaded by: - -{\tt load\_package linalg;} - - -\section{What's available} - -\subsection{add\_columns, add\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt add\_columns(${\cal A}$,c1,c2,expr);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ & :- & a matrix. \\ -c1,c2 & :- & positive integers. \\ -expr & :- & a scalar expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -\parbox[t]{0.95\linewidth}{{\tt add\_columns} replaces column c2 of -${\cal A}$ by expr $*$ column(${\cal A}$,c1) $+$ column(${\cal A}$,c2).} - -{\tt add\_rows} performs the equivalent task on the rows of ${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\begin{math} -\hspace*{0.16in} -\begin{array}{ccc} -{\tt add\_columns}({\cal A},1,2,x) & = & -\left( \begin{array}{ccc} 1 & x+2 & 3 \\ 4 & 4*x+5 & 6 \\ 7 & 7*x+8 & 9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt add\_rows}({\cal A},2,3,5) & = & -\left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 27 & 33 & 39 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt add\_to\_columns}, {\tt add\_to\_rows}, -{\tt mult\_columns}, {\tt mult\_rows}. - - -\subsection{add\_rows} - -\hspace*{0.175in} see: {\tt add\_columns}. - - -\subsection{add\_to\_columns, add\_to\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt add\_to\_columns(${\cal A}$,column\_list,expr);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -column\_list &:-& a positive integer or a list of positive integers. \\ -expr &:-& a scalar expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt add\_to\_columns} adds expr to each column specified in -column\_list of ${\cal A}$. - -{\tt add\_to\_rows} performs the equivalent task on the rows of -${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -\begin{array}{ccc} -{\tt add\_to\_columns}({\cal A},\{1,2\},10) & = & -\left( \begin{array}{ccc} 11 & 12 & 3 \\ 14 & 15 & 6 \\ 17 & 18 & 9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -\begin{array}{ccc} -{\tt add\_to\_rows}({\cal A},2,-x) & = & -\left( \begin{array}{ccc} 1 & 2 & 3 \\ -x+4 & -x+5 & -x+6 \\ 7 & 8 & 9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} -{\tt add\_columns}, {\tt add\_rows}, {\tt mult\_rows}, -{\tt mult\_columns}. - - -\subsection{add\_to\_rows} - -\hspace*{0.175in} see: {\tt add\_to\_columns}. - - -\subsection{augment\_columns, stack\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt augment\_columns(${\cal A}$,column\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -column\_list &:-& either a positive integer or a list of positive - integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt augment\_columns} gets hold of the columns of ${\cal A}$ specified -in column\_list and sticks them together. - -{\tt stack\_rows} performs the same task on rows of - ${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt augment\_columns}({\cal A},\{1,2\}) & = & -\left( \begin{array}{cc} 1 & 2 \\ 4 & 5 \\ 7 & 8 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt stack\_rows}({\cal A},\{1,3\}) & = & -\left( \begin{array}{ccc} 1 & 2 & 3 \\ 7 & 8 & 9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt get\_columns}, {\tt get\_rows}, -{\tt sub\_matrix}. - - -\subsection{band\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt band\_matrix(expr\_list,square\_size);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -expr\_list \hspace*{0.088in} &:-& \parbox[t]{.72\linewidth} -{either a single scalar expression or a list of an odd number of scalar -expressions.} -\end{tabular} - -\vspace*{0.04in} -\hspace*{0.1in} -\begin{tabular}{l l l} -square\_size &:-& a positive integer. -\end{tabular} - - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt band\_matrix} creates a square matrix of dimension - square\_size. The diagonal consists of the middle expr - of the expr\_list. The exprs to the left of this fill - the required number of sub\_diagonals and the exprs - to the right the super\_diagonals. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt band\_matrix}(\{x,y,z\},6) & = & -\left( \begin{array}{cccccc} y & z & 0 & 0 & 0 & 0 \\ x & y & z & 0 & 0 -& 0 \\ 0 & x & y & z & 0 & 0 \\ 0 & 0 & x & y & z & 0 \\ 0 & 0 & 0 & x & - y & z \\ 0 & 0 & 0 & 0 & x & y -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt diagonal}. - - -\subsection{block\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt block\_matrix(r,c,matrix\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -r,c &:-& positive integers. \\ -matrix\_list &:-& a list of matrices. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt block\_matrix} creates a matrix that consists of r by c matrices -filled from the matrix\_list row wise. - -\end{addtolength} - - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\cal B} = \left( \begin{array}{cc} 1 & 0 \\ 0 & 1 -\end{array} \right), & -{\cal C} = \left( \begin{array}{c} 5 \\ 5 -\end{array} \right), & -{\cal D} = \left( \begin{array}{cc} 22 & 33 \\ 44 & 55 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.175in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt block\_matrix}(2,3,\{{\cal B,C,D,D,C,B}\}) & = & -\left( \begin{array}{ccccc} 1 & 0 & 5 & 22 & 33 \\ 0 & 1 & 5 & 44 & 55 -\\ -22 & 33 & 5 & 1 & 0 \\ 44 & 55 & 5 & 0 & 1 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - - -\subsection{char\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt char\_matrix(${\cal A},\lambda$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a square matrix. \\ -$\lambda$ &:-& a symbol or algebraic expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt char\_matrix} creates the characteristic matrix ${\cal C}$ of -${\cal A}$. - -This is ${\cal C} = \lambda * {\cal I} - {\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt char\_matrix}({\cal A},x) & = & -\left( \begin{array}{ccc} x-1 & -2 & -3 \\ -4 & x-5 & -6 \\ -7 & -8 & -x-9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt char\_poly}. - - -\subsection{char\_poly} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt char\_poly(${\cal A},\lambda$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a square matrix. \\ -$\lambda$ &:-& a symbol or algebraic expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt char\_poly} finds the characteristic polynomial of - ${\cal A}$. - -This is the determinant of $\lambda * {\cal I} - {\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\hspace*{0.175in} -{\tt char\_poly({\cal A},$x$) $= x^3-15*x^2-18*x$} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt char\_matrix}. - - -\subsection{cholesky} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt cholesky(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a positive definite matrix containing numeric entries. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt cholesky} computes the cholesky decomposition of ${\cal A}$. - -It returns \{${\cal L,U}$\} where ${\cal L}$ -is a lower matrix, ${\cal U}$ is an upper matrix, \\ ${\cal A} = -{\cal LU}$, and ${\cal U} = {\cal L}^T$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal F} = \left( \begin{array}{ccc} 1 & 1 & 0 \\ 1 & 3 & 1 \\ 0 & 1 & -1 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -${\tt cholesky}$({\cal F}) & = & -\left\{ \left( \begin{array}{ccc} 1 & 0 & 0 \\ 1 & \sqrt{2} & 0 \\ -0 & \frac{1}{\sqrt{2}} & \frac{1}{\sqrt{2}} \end{array} \right), \left( -\begin{array}{ccc} 1 & 1 & 0 \\ 0 & \sqrt{2} & \frac{1}{\sqrt{2}} \\ 0 -& 0 & \frac{1}{\sqrt{2}} \end{array} \right) -\right\} \end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt lu\_decom}. - - -\subsection{coeff\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt coeff\_matrix(\{\lineqlist{}\});} -\lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\lineqlist &:-& \parbox[t]{.435\linewidth}{linear equations. Can be -of the form {\it equation $=$ number} or just {\it equation}.} -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt coeff\_matrix} creates the coefficient matrix - ${\cal C}$ of the linear equations. - -It returns \{${\cal C,X,B}$\} such that ${\cal CX} = {\cal B}$. - -\end{addtolength} - - -{\bf Examples:} - -\begin{math} -\hspace*{0.175in} -{\tt coeff\_matrix}(\{x+y+4*z=10,y+x-z=20,x+y+4\}) = -\end{math} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -\left\{ \left( \begin{array}{ccc} 4 & 1 & 1 \\ -1 & 1 & 1 \\ 0 & 1 & 1 -\end{array} \right), \left( \begin{array}{c} z \\ y \\ x \end{array} -\right), \left( \begin{array}{c} 10 \\ 20 \\ -4 -\end{array} \right) \right\} -\end{math} -\end{flushleft} - -\subsection{column\_dim, row\_dim} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt column\_dim(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt column\_dim} finds the column dimension of - ${\cal A}$. - -\hspace*{0.175in} {\tt row\_dim} finds the row dimension of ${\cal A}$. - -{\bf Examples:} - -\hspace*{0.175in} -{\tt column\_dim}(${\cal A}$) = 3 - -\subsection{companion} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt companion(poly,x);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -poly &:-& a monic univariate polynomial in x. \\ -x &:-& the variable. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - - -\begin{addtolength}{\leftskip}{0.22in} - {\tt companion} creates the companion matrix ${\cal C}$ - of poly. - -This is the square matrix of dimension n, where n is the degree of poly -w.r.t. x. - -The entries of ${\cal C}$ are: - ${\cal C}$(i,n) = -coeffn(poly,x,i-1) for i = 1 - \ldots n, ${\cal C}$(i,i-1) = 1 for i = 2 \ldots n and - the rest are 0. - -\end{addtolength} - - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt companion}(x^4+17*x^3-9*x^2+11,x) & = & -\left( \begin{array}{cccc} 0 & 0 & 0 & -11 \\ 1 & 0 & 0 & 0 \\ -0 & 1 & 0 & 9 \\ 0 & 0 & 1 & -17 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt find\_companion}. - - -\subsection{copy\_into} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt copy\_into(${\cal A,B}$,r,c);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A,B}$ &:-& matrices. \\ -r,c &:-& positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt copy\_into} copies matrix ${\cal A}$ into - ${\cal B}$ with ${\cal A}$(1,1) at ${\cal B}$(r,c). - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal G} = \left( \begin{array}{cccc} 0 & 0 & 0 & 0 \\ 0 & 0 & 0 & 0 \\ -0 & 0 & 0 & 0 \\ 0 & 0 & 0 & 0 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt copy\_into}({\cal A,G},1,2) & = & -\left( \begin{array}{cccc} 0 & 1 & 2 & 3 \\ 0 & 4 & 5 & 6 \\ 0 & 7 & 8 -& 9 \\ 0 & 0 & 0 & 0 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt augment\_columns}, {\tt extend}, {\tt matrix\_augment}, -{\tt matrix\_stack}, {\tt stack\_rows}, {\tt sub\_matrix}. - -\end{addtolength} - - -\subsection{diagonal} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt diagonal(\{\matlist{}\});}\lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\matlist &:-& \parbox[t]{.58\linewidth}{each can be either a scalar -expr or a square matrix. } -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt diagonal} creates a matrix that contains the -input on the diagonal. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal H} = \left( \begin{array}{cc} 66 & 77 \\ 88 & 99 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt diagonal}(\{{\cal A},x,{\cal H}\}) & = & -\left( \begin{array}{cccccc} 1 & 2 & 3 & 0 & 0 & 0 \\ 4 & 5 & 6 & 0 & 0 -& 0 \\ 7 & 8 & 9 & 0 & 0 & 0 \\ 0 & 0 & 0 & x & 0 & 0 \\ 0 & 0 & 0 & 0 -& 66 & 77 \\ 0 & 0 & 0 & 0 & 88 & 99 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt jordan\_block}. - - -\subsection{extend} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt extend(${\cal A}$,r,c,expr);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -r,c &:-& positive integers. \\ -expr &:-& algebraic expression or symbol. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt extend} returns a copy of ${\cal A}$ that has been - extended by r rows and c columns. The new entries are - made equal to expr. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt extend}({\cal A},1,2,x) & = & -\left( \begin{array}{ccccc} 1 & 2 & 3 & x & x \\ 4 & 5 & 6 & x & x -\\ 7 & 8 & 9 & x & x \\ x & x & x & x & x -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\begin{addtolength}{\leftskip}{0.22in} -\parbox[t]{0.95\linewidth}{{\tt copy\_into}, {\tt matrix\_augment}, -{\tt matrix\_stack}, {\tt remove\_columns}, {\tt remove\_rows}.} - -\end{addtolength} - - -\subsection{find\_companion} - -\hspace*{0.175in} {\tt find\_companion(${\cal A}$,x);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -x &:-& the variable. -\end{tabular} - -{\bf Synopsis:} - -\begin{addtolength}{\leftskip}{0.22in} - Given a companion matrix, {\tt find\_companion} finds the polynomial -from which it was made. - -\end{addtolength} - - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal C} = \left( \begin{array}{cccc} 0 & 0 & 0 & -11 \\ 1 & 0 & 0 & 0 -\\ 0 & 1 & 0 & 9 \\ 0 & 0 & 1 & -17 -\end{array} \right) -\end{math} -\end{flushleft} - -\vspace*{3mm} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\tt find\_companion}({\cal C},x) = x^4+17*x^3-9*x^2+11 -\end{math} -\end{flushleft} - -\vspace*{3mm} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt companion}. - -\subsection{get\_columns, get\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt get\_columns(${\cal A}$,column\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -c &:-& either a positive integer or a list of positive - integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt get\_columns} removes the columns of ${\cal A}$ specified in - column\_list and returns them as a list of column - matrices. - -\end{addtolength} -\hspace*{0.175in} {\tt get\_rows} performs the same task on the rows of - ${\cal A}$. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt get\_columns}({\cal A},\{1,3\}) & = & -\left\{ - \left( \begin{array}{c} 1 \\ 4 \\ 7 \end{array} \right), - \left( \begin{array}{c} 3 \\ 6 \\ 9 \end{array} \right) -\right\} -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt get\_rows}({\cal A},2) & = & -\left\{ - \left( \begin{array}{ccc} 4 & 5 & 6 \end{array} \right) -\right\} -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}, -{\tt sub\_matrix}. - - -\subsection{get\_rows} - -\hspace*{0.175in} see: {\tt get\_columns}. - - -\subsection{gram\_schmidt} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt gram\_schmidt(\{\veclist{}\});} \lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\veclist &:-& \parbox[t]{.62\linewidth}{linearly independent vectors. - Each vector must be written as a list, - eg:\{1,0,0\}. } -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt gram\_schmidt} performs the gram\_schmidt - orthonormalisation on the input vectors. - -It returns a list of orthogonal normalised vectors. - -\end{addtolength} - -{\bf Examples:} - -\hspace*{0.175in} -{\tt gram\_schmidt(\{\{1,0,0\},\{1,1,0\},\{1,1,1\}\})} = -\{\{1,0,0\},\{0,1,0\},\{0,0,1\}\} - -\hspace*{0.175in} -{\tt gram\_schmidt(\{\{1,2\},\{3,4\}\})} $= -\{\{ \frac{1}{{\sqrt{5}}} , \frac{2}{\sqrt{5}} \}, -\{ \frac{2*\sqrt{5}}{5} , \frac{-\sqrt{5}}{5} \}\}$ - -\subsection{hermitian\_tp} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt hermitian\_tp(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt hermitian\_tp} computes the hermitian transpose of - ${\cal A}$. - -This is a matrix in which the (i,$\,$j)'th entry is the conjugate of -the (j,$\,$i)'th entry of ${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal J} = \left( \begin{array}{ccc} i+1 & i+2 & i+3 \\ 4 & 5 & 2 \\ 1 & -i & 0 -\end{array} \right) -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt hermitian\_tp}({\cal J}) & = & -\left( \begin{array}{ccc} -i+1 & 4 & 1 \\ -i+2 & 5 & -i \\-i+3 & 2 & 0 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt tp}\footnote{standard reduce call for the -transpose of a matrix - see {\REDUCE} User's Manual[2].}. - - -\subsection{hessian} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt hessian(expr,variable\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -expr &:-& a scalar expression. \\ -variable\_list &:-& either a single variable or a list of variables. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt hessian} computes the hessian matrix of expr w.r.t. - the varibles in variable\_list. - -This is an n by n matrix - where n is the number of variables and the (i,$\,$j)'th - entry is df(expr,variable\_list(i),variable\_list(j)). - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt hessian}(x*y*z+x^2,\{w,x,y,z\}) & = & -\left( \begin{array}{cccc} 0 & 0 & 0 & 0 \\ 0 & 2 & z & y \\ 0 & z & 0 -& x \\ 0 & y & x & 0 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - - -{\bf Related functions:} - -\hspace*{0.175in} {\tt df}\footnote{standard reduce call for -differentiation - see {\REDUCE} User's Manual[2]}. - - -\subsection{hilbert} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt hilbert(square\_size,expr);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -square\_size &:-& a positive integer. \\ -expr &:-& an algebraic expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt hilbert} computes the square hilbert matrix of - dimension square\_size. - -This is the symmetric matrix in - which the (i,$\,$j)'th entry is 1/(i+j-expr). - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt hilbert}(3,y+x) & = & -\left( \begin{array}{ccc} \frac{-1}{x+y-2} & \frac{-1}{x+y-3} -& \frac{-1}{x+y-4} \\ \frac{-1}{x+y-3} & \frac{-1}{x+y-4} & -\frac{-1}{x+y-5} \\ \frac{-1}{x+y-4} & \frac{-1}{x+y-5} & -\frac{-1}{x+y-6} -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - - -\subsection{jacobian} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt jacobian(expr\_list,variable\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -expr\_list \hspace*{0.175in} &:-& \parbox[t]{.72\linewidth}{either a -single algebraic expression or a list of algebraic expressions.} -\end{tabular} - -\vspace*{0.04in} -\hspace*{0.1in} -\begin{tabular}{l l l} -variable\_list &:-& either a single variable or a list of variables. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt jacobian} computes the jacobian matrix of expr\_list w.r.t. -variable\_list. - -This is a matrix whose (i,$\,$j)'th entry is df(expr\_list(i), -variable\_list(j)). - -The matrix is n by m where n is the - number of variables and m the number of expressions. - -\end{addtolength} - -{\bf Examples:} - -\hspace*{0.175in} -{\tt jacobian(\{$x^4,x*y^2,x*y*z^3$\},\{$w,x,y,z$\})} = - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -\left( \begin{array}{cccc} 0 & 4*x^3 & 0 & 0 \\ 0 & y^2 & 2*x*y & 0 \\ -0 & y*z^3 & x*z^3 & 3*x*y*z^2 -\end{array} \right) -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt hessian}, {\tt df}\footnote{standard reduce call -for differentiation - see {\REDUCE} User's Manual[2].}. - - -\subsection{jordan\_block} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt jordan\_block(expr,square\_size);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -expr &:-& an algebraic expression or symbol. \\ -square\_size &:-& a positive integer. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt jordan\_block} computes the square jordan block matrix ${\cal J}$ - of dimension square\_size. - -The entries of ${\cal J}$ are: - ${\cal J}$(i,i) = expr for i=1 - \ldots n, ${\cal J}$(i,i+1) = 1 for i=1 - \ldots n-1, and all other entries are 0. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt jordan\_block(x,5)} & = & -\left( \begin{array}{ccccc} x & 1 & 0 & 0 & 0 \\ 0 & x & 1 & 0 & 0 \\ 0 -& 0 & x & 1 & 0 \\ 0 & 0 & 0 & x & 1 \\ 0 & 0 & 0 & 0 & x -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt diagonal}, {\tt companion}. - - -\subsection{lu\_decom} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt lu\_decom(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& \parbox[t]{.848\linewidth}{a matrix containing either -numeric entries or imaginary entries with numeric coefficients.} -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt lu\_decom} performs LU decomposition on ${\cal A}$, - ie: it returns \{${\cal L,U}$\} where ${\cal L}$ - is a lower diagonal matrix, ${\cal U}$ an upper diagonal - matrix and ${\cal A} = {\cal LU}$. - -\end{addtolength} - -{\bf caution:} - -\begin{addtolength}{\leftskip}{0.22in} -The algorithm used can swap the rows of ${\cal A}$ - during the calculation. This means that ${\cal LU}$ does - not equal ${\cal A}$ but a row equivalent of it. Due to - this, {\tt lu\_decom} returns \{${\cal L,U}$,vec\}. The - call {\tt convert(${\cal A}$,vec)} will return the - matrix that has been decomposed, ie: ${\cal LU} = $ - {\tt convert(${\cal A}$,vec)}. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal K} = \left( \begin{array}{ccc} 1 & 3 & 5 \\ -4 & 3 & 7 \\ 8 & 6 & -4 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{cccc} -${\tt lu} := {\tt lu\_decom}$({\cal K}) & = & -\left\{ - \left( \begin{array}{ccc} 8 & 0 & 0 \\ -4 & 6 & 0 \\ 1 & 2.25 & -1.125 1 \end{array} \right), - \left( \begin{array}{ccc} 1 & 0.75 & 0.5 \\ 0 & 1 & 1.5 \\ 0 & -0 & 1 \end{array} \right), - [\; 3 \; 2 \; 3 \; ] -\right\} -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -${\tt first lu * second lu}$ & = & - \left( \begin{array}{ccc} 8 & 6 & 4 \\ -4 & 3 & 7 \\ 1 & 3 & 5 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -${\tt convert(${\cal K}$,third lu}$) \hspace*{0.055in} & = & - \left( \begin{array}{ccc} 8 & 6 & 4 \\ -4 & 3 & 7 \\ 1 & 3 & 5 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.5in} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal P} = \left( \begin{array}{ccc} i+1 & i+2 & i+3 \\ 4 & 5 & 2 \\ 1 -& i & 0 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{eqnarray} -\hspace*{0.22in} -{\tt lu} := {\tt lu\_decom}({\cal P}) & = & -\left\{ - \left( \begin{array}{ccc} 1 & 0 & 0 \\ 4 & -4*i+5 & 0 \\ i+1 & -3 & 0.41463*i+2.26829 \end{array} \right), \right. \nonumber \\ & & -\left. \: \; \, \left( \begin{array}{ccc} 1 & i & 0 \\ 0 & 1 & -0.19512*i+0.24390 \\ 0 & 0 & 1 \end{array} \right), \hspace*{0.05in} -[\; 3 \; 2 \; 3 \;] \hspace*{0.05in} -\right\} \nonumber -\end{eqnarray} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -${\tt first lu * second lu}$ & = & - \left( \begin{array}{ccc} 1 & i & 0 \\ 4 & 5 & 2 \\ i+1 & i+2 & -i+3 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -${\tt convert({\cal P},third lu}$) \hspace*{0.1in} & = & \left( -\begin{array}{c c c} 1 & i & 0 \\ 4 & 5 & 2 \\ i+1 & i+2 & i+3 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt cholesky}. - - -\subsection{make\_identity} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt make\_identity(square\_size);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -square\_size &:-& a positive integer. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt make\_identity} creates the identity matrix of - dimension square\_size. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt make\_identity}(4) & = & - \left( \begin{array}{cccc} 1 & 0 & 0 & 0 \\ 0 & 1 & 0 & 0 \\ 0 -& 0 & 1 & 0 \\ 0 & 0 & 0 & 1 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt diagonal}. - - -\subsection{matrix\_augment, matrix\_stack} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt matrix\_augment(\{\matlist\});}\lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\matlist &:-& matrices. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt matrix\_augment} sticks the matrices in - matrix\_list together horizontally. - -\hspace*{0.175in} -{\tt matrix\_stack} sticks the matrices in matrix\_list - together vertically. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt matrix\_augment}(\{{\cal A,A}\}) & = & - \left( \begin{array}{cccccc} 1 & 2 & 3 & 1 & 2 & 3 \\ 4 & 4 & 6 -& 4 & 5 & 6 \\ 7 & 8 & 9 & 7 & 8 & 9 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt matrix\_stack}(\{{\cal A,A}\}) & = & - \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 -\\ 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}, -{\tt sub\_matrix}. - - -\subsection{matrixp} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt matrixp(test\_input);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -test\_input &:-& anything you like. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt matrixp} is a boolean function that returns t if - the input is a matrix and nil otherwise. - -\end{addtolength} - -{\bf Examples:} - -\hspace*{0.175in} {\tt matrixp}(${\cal A}$) = t - -\hspace*{0.175in} {\tt matrixp}(doodlesackbanana) = nil - -{\bf Related functions:} - -\hspace*{0.175in} {\tt squarep}, {\tt symmetricp}. - - -\subsection{matrix\_stack} - -\hspace*{0.175in} see: {\tt matrix\_augment}. - - -\subsection{minor} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt minor(${\cal A}$,r,c);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -r,c &:-& positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} - {\tt minor} computes the (r,c)'th minor of ${\cal A}$. - - This is created by removing the r'th row and the c'th - column from ${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt minor}({\cal A},1,3) & = & - \left( \begin{array}{cc} 4 & 5 \\ 7 & 8 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt remove\_columns}, {\tt remove\_rows}. - - -\subsection{mult\_columns, mult\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt mult\_columns(${\cal A}$,column\_list,expr);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -column\_list &:-& a positive integer or a list of positive integers. \\ -expr &:-& an algebraic expression. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt mult\_columns} returns a copy of ${\cal A}$ in which - the columns specified in column\_list have been -multiplied by expr. - -{\tt mult\_rows} performs the same task on the rows of ${\cal A}$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt mult\_columns}({\cal A},\{1,3\},x) & = & - \left( \begin{array}{ccc} x & 2 & 3*x \\ 4*x & 5 & 6*x \\ 7*x & -8 & 9*x - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt mult\_rows}({\cal A},2,10) & = & - \left( \begin{array}{ccc} 1 & 2 & 3 \\ 40 & 50 & 60 \\ 7 & 8 & -9 \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt add\_to\_columns}, {\tt add\_to\_rows}. - - -\subsection{\tt mult\_rows} - -\hspace*{0.175in} see: {\tt mult\_columns}. - - -\subsection{pivot} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt pivot(${\cal A}$,r,c);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -r,c &:-& positive integers such that ${\cal A}$(r,c) neq 0. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt pivot} pivots ${\cal A}$ about its (r,c)'th entry. - -To do this, multiples of the r'th row are added to every - other row in the matrix. - -This means that the c'th column - will be 0 except for the (r,c)'th entry. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt pivot}({\cal A},2,3) & = & - \left( \begin{array}{ccc} -1 & -0.5 & 0 \\ 4 & 5 & 6 \\ 1 & 0.5 -& 0 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt rows\_pivot}. - - -\subsection{pseudo\_inverse} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt pseudo\_inverse(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt pseudo\_inverse}, also known as the Moore-Penrose inverse, computes -the pseudo inverse of ${\cal A}$. - -Given the singular value decomposition of ${\cal A}$, i.e: ${\cal A} = -{\cal U} -\sum {\cal V}^T$, then the pseudo inverse ${\cal A}^{-1}$ is defined -by ${\cal A}^{-1} = {\cal V}^T \sum^{-1} {\cal U}$. - -Thus ${\cal A}$ $ * $ {\tt pseudo\_inverse}$({\cal A}) = {\cal I}$. - -\end{addtolength} - -{\bf Examples:} - -% \begin{flushleft} -% \hspace*{0.175in} -% \begin{math} -% {\cal R} = \left( \begin{array}{cccc} 1 & 2 & 3 & 4 \\ 9 & 8 & 7 & 6 -% \end{array} \right) -% \end{math} -% \end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt pseudo\_inverse}({\cal A}) & = & - \left( \begin{array}{cc} -0.2 & 0.1 \\ -0.05 & 0.05 \\ 0.1 & 0 -\\ 0.25 & -0.05 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt svd}. - -\subsection{random\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt random\_matrix(r,c,limit);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -r,c,$\,$limit &:-& positive integers. \\ -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt random\_matrix} creates an r by c matrix with random - entries in the range $-$limit $<$ entry $<$ limit. - -\end{addtolength} - -{\bf switches:} - -\hspace*{0.1in} -\begin{tabular}{l l l} -{\tt imaginary} \hspace*{0.175in} &:-& \parbox[t]{0.685\linewidth}{if -on then matrix entries are x+i$*$y where $-$limit $<$ x,y $<$ limit.} -\end{tabular} - -\vspace*{0.04in} -\hspace*{0.1in} -\begin{tabular}{l l l} -{\tt not\_negative} &:-& \parbox[t]{0.685\linewidth}{if on then 0 $<$ -entry $<$ limit. In the imaginary case we have 0 $<$ x,y $<$ limit.} -\end{tabular} - -\vspace*{0.04in} -\hspace*{0.1in} -\begin{tabular}{l l l} -{\tt only\_integer} &:-& \parbox[t]{0.685\linewidth}{if on then each -entry is an integer. In the imaginary case x and y are integers.} -\end{tabular} - -\vspace*{0.04in} -\hspace*{0.1in} -\begin{tabular}{l l l} -{\tt symmetric} &:-& if on then the matrix is symmetric. \\ -{\tt upper\_matrix} &:-& \parbox[t]{0.685\linewidth}{if on then the -matrix is upper triangular.} \\ -{\tt lower\_matrix} &:-& if on then the matrix is lower triangular. -\end{tabular} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt random\_matrix}(3,3,10) & = & - \left( \begin{array}{ccc} -4.729721 & 6.987047 & 7.521383 \\ -- 5.224177 & 5.797709 & - 4.321952 \\ -- 9.418455 & - 9.94318 & - 0.730980 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.2in} -\hspace*{0.165in} -{\tt on only\_integer, not\_negative, upper\_matrix, imaginary;} -\begin{flushleft} -\hspace*{0.12in} -\begin{math} -\begin{array}{ccc} -{\tt random\_matrix}(4,4,10) & = & -\left( \begin{array}{cccc} 2*i+5 & 3*i+7 & 7*i+3 & 6 \\ 0 & 2*i+5 & -5*i+1 & 2*i+1 \\ 0 & 0 & 8 & i \\ 0 & 0 & 0& 5*i+9 -\end{array} \right) -\end{array} -\end{math} -\end{flushleft} - - -\subsection{remove\_columns, remove\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt remove\_columns(${\cal A}$,column\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -column\_list &:-& either a positive integer or a list of - positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt remove\_columns} removes the columns specified in - column\_list from ${\cal A}$. - -\hspace*{0.175in} {\tt remove\_rows} performs the same task on the rows - of ${\cal A}$. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt remove\_columns}({\cal A},2) & = & - \left( \begin{array}{cc} 1 & 3 \\ 4 & 6 \\ 7 & 9 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt remove\_rows}({\cal A},\{1,3\}) & = & - \left( \begin{array}{ccc} 4 & 5 & 6 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - - -{\bf Related functions:} - -\hspace*{0.175in} {\tt minor}. - - -\subsection{remove\_rows} - -\hspace*{0.175in} see: {\tt remove\_columns}. - - -\subsection{row\_dim} - -\hspace{0.175in} see: {\tt column\_dim}. - - -\subsection{rows\_pivot} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt rows\_pivot(${\cal A}$,r,c,\{row\_list\});} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -r,c &:-& positive integers such that ${\cal A}$(r,c) neq 0.\\ -row\_list &:-& positive integer or a list of positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt rows\_pivot} performs the same task as {\tt pivot} but applies -the pivot only to the rows specified in row\_list. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal N} = \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & -9 \\1 & 2 & 3 \\ 4 & 5 & 6 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt rows\_pivot}({\cal N},2,3,\{4,5\}) & = & \left( \begin{array} -{c c c}1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 \\ -0.75 & 0 & 0.75 \\ --0.375 & 0 & 0.375 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt pivot}. - - -\subsection{simplex} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt simplex(max/min,objective function,\{linear -inequalities\});} - -\hspace*{0.1in} -\begin{tabular}{l l l} -max/min & :- & \parbox[t]{.63\linewidth}{either max or min - (signifying maximise and minimise).} \\ -objective function & :- & the function you are maximising or - minimising. \\ -linear inequalities & :- & \parbox[t]{.63\linewidth}{the constraint - inequalities. Each one must be of the form - {\it sum of variables ($<=,=,>=$) number}.} -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt simplex} applies the revised simplex algorithm to find the -optimal(either maximum or minimum) value of the objective function -under the linear inequality constraints. - -It returns \{optimal value,\{ values of variables at this optimal\}\}. - -The algorithm implies that all the variables are non-negative. - -\end{addtolength} - -{\bf Examples:} - -\begin{addtolength}{\leftskip}{0.22in} -%\begin{math} -{\tt simplex($max,x+y,\{x>=10,y>=20,x+y<=25\}$);} -%\end{math} - -{\tt ***** Error in simplex: Problem has no feasible solution.} - -\vspace*{0.2in} - -\parbox[t]{0.96\linewidth}{\tt simplex($max,10x+5y+5.5z,\{5x+3z<=200, -x+0.1y+0.5z<=12$,\\ -\hspace*{0.55in} $0.1x+0.2y+0.3z<=9, 30x+10y+50z<=1500\}$);} - -\vspace*{0.1in} -{\tt $\{525.0,\{x=40.0,y=25.0,z=0\}$\}} - -\end{addtolength} - - -\subsection{squarep} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt squarep(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt squarep} is a boolean function that returns t if - the matrix is square and nil otherwise. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal L} = \left( \begin{array}{ccc} 1 & 3 & 5 -\end{array} \right) -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\hspace*{0.175in} {\tt squarep}(${\cal A}$) = t - -\hspace*{0.175in} {\tt squarep}(${\cal L}$) = nil - -{\bf Related functions:} - -\hspace*{0.175in} {\tt matrixp}, {\tt symmetricp}. - - -\subsection{stack\_rows} - -\hspace*{0.175in} see: {\tt augment\_columns}. - - -\subsection{sub\_matrix} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt sub\_matrix(${\cal A}$,row\_list,column\_list);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -row\_list, column\_list &:-& \parbox[t]{.605\linewidth}{either a -positive integer or a list of positive integers.} -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - - -\begin{addtolength}{\leftskip}{0.22in} - -{\tt sub\_matrix} produces the matrix consisting of the - intersection of the rows specified in row\_list and the -columns specified in column\_list. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt sub\_matrix}({\cal A},\{1,3\},\{2,3\}) & = & - \left( \begin{array}{cc} 2 & 3 \\ 8 & 9 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}. - - -\subsection{svd (singular value decomposition)} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt svd(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix containing only numeric entries. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt svd} computes the singular value decomposition of ${\cal A}$. - -It returns \{${\cal U},\sum,{\cal V}$\} where ${\cal A} = {\cal U} -\sum {\cal V}^T$ and $\sum = diag(\sigma_{1}, \ldots ,\sigma_{n}). \; -\sigma_{i}$ for $i= (1 \ldots n)$ are the singular values of ${\cal A}$. - - -n is the column dimension of ${\cal A}$. - -The singular values of ${\cal A}$ are the non-negative square roots of -the eigenvalues of ${\cal A}^T {\cal A}$. - -${\cal U}$ and ${\cal V}$ are such that ${\cal UU}^T = {\cal VV}^T = -{\cal V}^T {\cal V} = {\cal I}_n$. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal Q} = \left( \begin{array}{cc} 1 & 3 \\ -4 & 3 -\end{array} \right) -\end{math} -\end{flushleft} - -\begin{eqnarray} -\hspace*{0.1in} -{\tt svd({\cal Q})} & = & -\left\{ - \left( \begin{array}{cc} 0.289784 & 0.957092 \\ -0.957092 & -0.289784 \end{array} \right), \left( \begin{array}{cc} 5.149162 & 0 \\ -0 & 2.913094 \end{array} \right), \right. \nonumber \\ & & \left. \: \; -\, \left( \begin{array}{cc} -0.687215 & 0.726453 \\ -0.726453 & --0.687215 \end{array} \right) -\right\} \nonumber -\end{eqnarray} - - -\subsection{swap\_columns, swap\_rows} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt swap\_columns(${\cal A}$,c1,c2);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -c1,c1 &:-& positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} -{\tt swap\_columns} swaps column c1 of ${\cal A}$ with column c2. - -\hspace*{0.175in} {\tt swap\_rows} performs the same task on 2 rows of - ${\cal A}$. - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt swap\_columns}({\cal A},2,3) & = & - \left( \begin{array}{ccc} 1 & 3 & 2 \\ 4 & 6 & 5 \\ 7 & 9 & 8 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt swap\_entries}. - - -\subsection{swap\_entries} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt swap\_entries(${\cal A}$,\{r1,c1\},\{r2,c2\});} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. \\ -r1,c1,r2,c2 &:-& positive integers. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\hspace*{0.175in} {\tt swap\_entries} swaps ${\cal A}$(r1,c1) with - ${\cal A}$(r2,c2). - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt swap\_entries}({\cal A},\{1,1\},\{3,3\}) & = & - \left( \begin{array}{ccc} 9 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 1 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -{\bf Related functions:} - -\hspace*{0.175in} {\tt swap\_columns}, {\tt swap\_rows}. - - -\subsection{swap\_rows} - -\hspace*{0.175in} see: {\tt swap\_columns}. - - -\subsection{symmetricp} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt symmetricp(${\cal A}$);} - -\hspace*{0.1in} -\begin{tabular}{l l l} -${\cal A}$ &:-& a matrix. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt symmetricp} is a boolean function that returns t if the - matrix is symmetric and nil otherwise. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.175in} -\begin{math} -{\cal M} = \left( \begin{array}{cc} 1 & 2 \\ 2 & 1 -\end{array} \right) -\end{math} -\end{flushleft} - -\vspace*{0.1in} - -\hspace*{0.175in} {\tt symmetricp}(${\cal A}$) = nil - -\hspace*{0.175in} {\tt symmetricp}(${\cal M}$) = t - -{\bf Related functions:} - -\hspace*{0.175in} {\tt matrixp}, {\tt squarep}. - - -\subsection{toeplitz} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt toeplitz(\{\exprlist{}\});} \lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\exprlist{} &:-& algebraic expressions. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt toeplitz} creates the toeplitz matrix from the - expression list. - -This is a square symmetric matrix in - which the first expression is placed on the diagonal - and the i'th expression is placed on the (i-1)'th sub - and super diagonals. - -It has dimension n where n is the - number of expressions. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt toeplitz}(\{w,x,y,z\}) & = & - \left( \begin{array}{cccc} w & x & y & z \\ x & w & x & y \\ - y & x & w & x \\ z & y & x & w - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\subsection{Vandermonde} - -%{\bf How to use it:} - -\hspace*{0.175in} {\tt vandermonde}(\{\exprlist{}\}); \addtocounter -{footnote}{-1}\footnotemark -%\lazyfootnote{} - -\hspace*{0.1in} -\begin{tabular}{l l l} -\exprlist{} &:-& algebraic expressions. -\end{tabular} - -{\bf Synopsis:} %{\bf What it does:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt Vandermonde} creates the Vandermonde matrix from - the expression list. - -This is the square matrix in which - the (i,$\,$j)'th entry is expr\_list(i) $^{(j-1)}$. - -It has dimension n where n is the number of expressions. - -\end{addtolength} - -{\bf Examples:} - -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -{\tt vandermonde}(\{x,2*y,3*z\}) & = & - \left( \begin{array}{ccc} 1 & x & x^2 \\ 1 & 2*y & 4*y^2 \\ 1 -& 3*z & 9*z^2 - \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\subsection{kronecker\_product} - -\hspace*{0.175in} {\tt kronecker\_product}($Mat_1,Mat_2$) - -\hspace*{0.1in} -\begin{tabular}{l l l} -$Mat_1,Mat_2$ &:-& Matrices -\end{tabular} - -{\bf Synopsis:} - -\begin{addtolength}{\leftskip}{0.22in} -{\tt kronecker\_product} creates a matrix containing the Kronecker product -(also called {\tt direct product} or {\tt tensor product}) of its arguments. - -\end{addtolength} - -{\bf Examples:} -\begin{verbatim} -a1 := mat((1,2),(3,4),(5,6))$ -a2 := mat((1,1,1),(2,z,2),(3,3,3))$ -kronecker_product(a1,a2); -\end{verbatim} -\begin{flushleft} -\hspace*{0.1in} -\begin{math} -\begin{array}{ccc} -\left( \begin{array}{cccccc} 1 & 1 & 1 & 2 & 2 & 2 \\ -2 & z & 2 & 4 &2*z &4 \\ -3 & 3 & 3 & 6 & 6 &6 \\ -3 & 3 & 3 & 4 & 4 &4 \\ -6 & 3*z& 6 & 8 &4*z &8 \\ -9 & 9 & 9 & 12 &12 &12\\ -5 & 5 & 5 & 6 & 6 &6 \\ -10 &5*z& 10& 12 &6*z &12 \\ -15 &15 & 15& 18 &18 &18 \end{array} \right) -\end{array} -\end{math} -\end{flushleft} - -\section{Fast Linear Algebra} - -By turning the {\tt fast\_la} switch on, the speed of the following -functions will be increased: - -\begin{tabular}{l l l l} - add\_columns & add\_rows & augment\_columns & column\_dim \\ - copy\_into & make\_identity & matrix\_augment & matrix\_stack\\ - minor & mult\_column & mult\_row & pivot \\ - remove\_columns & remove\_rows & rows\_pivot & squarep \\ - stack\_rows & sub\_matrix & swap\_columns & swap\_entries\\ - swap\_rows & symmetricp -\end{tabular} - -The increase in speed will be insignificant unless you are making a -significant number(i.e: thousands) of calls. When using this switch, -error checking is minimised. This means that illegal input may give -strange error messages. Beware. - -\newpage - -\section{Acknowledgments} - -Many of the ideas for this package came from the Maple[3] Linalg package -[4]. - -The algorithms for {\tt cholesky}, {\tt lu\_decom}, and {\tt svd} are -taken from the book Linear Algebra - J.H. Wilkinson \& C. Reinsch[5]. - -The {\tt gram\_schmidt} code comes from Karin Gatermann's Symmetry -package[6] for {\REDUCE}. - - -\begin{thebibliography}{} -\bibitem{matt} Matt Rebbeck: NORMFORM: A {\REDUCE} package for the -computation of various matrix normal forms. ZIB, Berlin. (1993) -\bibitem{Reduce} Anthony C. Hearn: {\REDUCE} User's Manual 3.6. - RAND (1995) -\bibitem{Maple} Bruce W. Char\ldots [et al.]: Maple (Computer - Program). Springer-Verlag (1991) -\bibitem{linalg} Linalg - a linear algebra package for Maple[3]. -\bibitem{WiRe} J. H. Wilkinson \& C. Reinsch: Linear Algebra -(volume II). Springer-Verlag (1971) -\bibitem{gat} Karin Gatermann: Symmetry: A {\REDUCE} package for the -computation of linear representations of groups. ZIB, Berlin. (1992) -\end{thebibliography} - -\end{document} - - - +\documentstyle[11pt,reduce,fancyheadings]{article} +\title{A Linear Algebra package for \REDUCE{}} +\author{Matt Rebbeck \\ + Konrad-Zuse-Zentrum f\"ur Informationstechnik Berlin} +\date{July 1994} + +\def\foottitle{The Linear Algebra Package} +\pagestyle{fancy} +\lhead[]{{\footnotesize\leftmark}{}} +\rhead[]{\thepage} +\setlength{\headrulewidth}{0.6pt} +\setlength{\footrulewidth}{0.6pt} +\cfoot{} +\rfoot{\small\foottitle} + +%decided against using these. +%\def\ltri{$\triangleleft$} +%\def\rtri{$\triangleright$} +%\newcommand{\tribound}[1]{\rtri#1\ltri} + +\def\exprlist {expr$_{1}$,expr$_{2}$, \ldots ,expr$_{{\tt n}}$} +\def\lineqlist {lin\_eqn$_{1}$,lin\_eqn$_{2}$, \ldots ,lin\_eqn$_{n}$} +\def\matlist {mat$_{1}$,mat$_{2}$, \ldots ,mat$_{n}$} +\def\veclist {vec$_{1}$,vec$_{2}$, \ldots ,vec$_{n}$} + +\def\lazyfootnote{\footnote{If you're feeling lazy then the \{\}'s can + be omitted.}} + +\renewcommand{\thefootnote}{\fnsymbol{footnote}} + +\begin{document} +\maketitle +\index{Linear Algebra package} + +\section{Introduction} +This package provides a selection of functions that are useful +in the world of linear algebra. These functions are described +alphabetically in section 3 of this document and are labelled 3.1 to +3.51. They can be classified into four sections(n.b: the numbers after +the dots signify the function label in section 3). + +\subsection{Basic matrix handling} + +\begin{center} +\begin{tabular}{l l l l l l} +add\_columns & \ldots & 3.1 & +add\_rows & \ldots & 3.2 \\ +add\_to\_columns & \ldots & 3.3 & +add\_to\_rows & \ldots & 3.4 \\ +augment\_columns & \ldots & 3.5 & +char\_poly & \ldots & 3.9 \\ +column\_dim & \ldots & 3.12 & +copy\_into & \ldots & 3.14 \\ +diagonal & \ldots & 3.15 & +extend & \ldots & 3.16 \\ +find\_companion & \ldots & 3.17 & +get\_columns & \ldots & 3.18 \\ +get\_rows & \ldots & 3.19 & +hermitian\_tp & \ldots & 3.21 \\ +matrix\_augment & \ldots & 3.28 & +matrix\_stack & \ldots & 3.30 \\ +minor & \ldots & 3.31 & +mult\_columns & \ldots & 3.32 \\ +mult\_rows & \ldots & 3.33 & +pivot & \ldots & 3.34 \\ +remove\_columns & \ldots & 3.37 & +remove\_rows & \ldots & 3.38 \\ +row\_dim & \ldots & 3.39 & +rows\_pivot & \ldots & 3.40 \\ +stack\_rows & \ldots & 3.43 & +sub\_matrix & \ldots & 3.44 \\ +swap\_columns & \ldots & 3.46 & +swap\_entries & \ldots & 3.47 \\ +swap\_rows & \ldots & 3.48 & +\end{tabular} +\end{center} + +\subsection{Constructors} + +Functions that create matrices. + +\begin{center} +\begin{tabular}{l l l l l l} +band\_matrix & \ldots & 3. 6 & +block\_matrix & \ldots & 3. 7 \\ +char\_matrix & \ldots & 3. 8 & +coeff\_matrix & \ldots & 3. 11 \\ +companion & \ldots & 3. 13 & +hessian & \ldots & 3. 22 \\ +hilbert & \ldots & 3. 23 & +jacobian & \ldots & 3. 24 \\ +jordan\_block & \ldots & 3. 25 & +make\_identity & \ldots & 3. 27 \\ +random\_matrix & \ldots & 3. 36 & +toeplitz & \ldots & 3. 50 \\ +Vandermonde & \ldots & 3. 51 & +Kronecker\_Product & \ldots & 3. 52 +\end{tabular} +\end{center} + +\subsection{High level algorithms} + +\begin{center} +\begin{tabular}{l l l l l l} +char\_poly & \ldots & 3.9 & +cholesky & \ldots & 3.10 \\ +gram\_schmidt & \ldots & 3.20 & +lu\_decom & \ldots & 3.26 \\ +pseudo\_inverse & \ldots & 3.35 & +simplex & \ldots & 3.41 \\ +svd & \ldots & 3.45 & +\end{tabular} +\end{center} + +\vspace*{5mm} +There is a separate {\small NORMFORM}[1] package for computing +the following matrix normal forms in \REDUCE. + +\begin{center} +smithex, smithex\_int, frobenius, ratjordan, jordansymbolic, jordan. +\end{center} + +\subsection{Predicates} + +\begin{center} +\begin{tabular}{l l l l l l} +matrixp & \ldots & 3.29 & +squarep & \ldots & 3.42 \\ +symmetricp & \ldots & 3.49 & +\end{tabular} +\end{center} + +\subsection*{Note on examples:} + +In the examples the matrix ${\cal A}$ will be + +\begin{flushleft} +\begin{math} +{\cal A} = \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 +\end{array} \right) +\end{math} +\end{flushleft} + + +\subsection*{Notation} + +Throughout ${\cal I}$ is used to indicate the identity matrix and +${\cal A}^T$ to indicate the transpose of the matrix ${\cal A}$. + +\section{Getting started} + +If you have not used matrices within {\REDUCE} before then the +following may be helpful. + +\subsection*{Creating matrices} + +Initialisation of matrices takes the following syntax: + +{\tt mat1 := mat((a,b,c),(d,e,f),(g,h,i));} + +will produce + +\begin{flushleft} +\begin{math} +mat1 := \left( \begin{array}{ccc} a & b & c \\ d & e & f \\ g & h & i +\end{array} \right) +\end{math} +\end{flushleft} + +\subsection*{Getting at the entries} + +The (i,$\,$j)'th entry can be accessed by: + +{\tt mat1(i,j);} + +\subsection*{Loading the linear\_algebra package} + +The package is loaded by: + +{\tt load\_package linalg;} + + +\section{What's available} + +\subsection{add\_columns, add\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt add\_columns(${\cal A}$,c1,c2,expr);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ & :- & a matrix. \\ +c1,c2 & :- & positive integers. \\ +expr & :- & a scalar expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +\parbox[t]{0.95\linewidth}{{\tt add\_columns} replaces column c2 of +${\cal A}$ by expr $*$ column(${\cal A}$,c1) $+$ column(${\cal A}$,c2).} + +{\tt add\_rows} performs the equivalent task on the rows of ${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\begin{math} +\hspace*{0.16in} +\begin{array}{ccc} +{\tt add\_columns}({\cal A},1,2,x) & = & +\left( \begin{array}{ccc} 1 & x+2 & 3 \\ 4 & 4*x+5 & 6 \\ 7 & 7*x+8 & 9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt add\_rows}({\cal A},2,3,5) & = & +\left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 27 & 33 & 39 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt add\_to\_columns}, {\tt add\_to\_rows}, +{\tt mult\_columns}, {\tt mult\_rows}. + + +\subsection{add\_rows} + +\hspace*{0.175in} see: {\tt add\_columns}. + + +\subsection{add\_to\_columns, add\_to\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt add\_to\_columns(${\cal A}$,column\_list,expr);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +column\_list &:-& a positive integer or a list of positive integers. \\ +expr &:-& a scalar expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt add\_to\_columns} adds expr to each column specified in +column\_list of ${\cal A}$. + +{\tt add\_to\_rows} performs the equivalent task on the rows of +${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +\begin{array}{ccc} +{\tt add\_to\_columns}({\cal A},\{1,2\},10) & = & +\left( \begin{array}{ccc} 11 & 12 & 3 \\ 14 & 15 & 6 \\ 17 & 18 & 9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +\begin{array}{ccc} +{\tt add\_to\_rows}({\cal A},2,-x) & = & +\left( \begin{array}{ccc} 1 & 2 & 3 \\ -x+4 & -x+5 & -x+6 \\ 7 & 8 & 9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} +{\tt add\_columns}, {\tt add\_rows}, {\tt mult\_rows}, +{\tt mult\_columns}. + + +\subsection{add\_to\_rows} + +\hspace*{0.175in} see: {\tt add\_to\_columns}. + + +\subsection{augment\_columns, stack\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt augment\_columns(${\cal A}$,column\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +column\_list &:-& either a positive integer or a list of positive + integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt augment\_columns} gets hold of the columns of ${\cal A}$ specified +in column\_list and sticks them together. + +{\tt stack\_rows} performs the same task on rows of + ${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt augment\_columns}({\cal A},\{1,2\}) & = & +\left( \begin{array}{cc} 1 & 2 \\ 4 & 5 \\ 7 & 8 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt stack\_rows}({\cal A},\{1,3\}) & = & +\left( \begin{array}{ccc} 1 & 2 & 3 \\ 7 & 8 & 9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt get\_columns}, {\tt get\_rows}, +{\tt sub\_matrix}. + + +\subsection{band\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt band\_matrix(expr\_list,square\_size);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +expr\_list \hspace*{0.088in} &:-& \parbox[t]{.72\linewidth} +{either a single scalar expression or a list of an odd number of scalar +expressions.} +\end{tabular} + +\vspace*{0.04in} +\hspace*{0.1in} +\begin{tabular}{l l l} +square\_size &:-& a positive integer. +\end{tabular} + + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt band\_matrix} creates a square matrix of dimension + square\_size. The diagonal consists of the middle expr + of the expr\_list. The exprs to the left of this fill + the required number of sub\_diagonals and the exprs + to the right the super\_diagonals. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt band\_matrix}(\{x,y,z\},6) & = & +\left( \begin{array}{cccccc} y & z & 0 & 0 & 0 & 0 \\ x & y & z & 0 & 0 +& 0 \\ 0 & x & y & z & 0 & 0 \\ 0 & 0 & x & y & z & 0 \\ 0 & 0 & 0 & x & + y & z \\ 0 & 0 & 0 & 0 & x & y +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt diagonal}. + + +\subsection{block\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt block\_matrix(r,c,matrix\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +r,c &:-& positive integers. \\ +matrix\_list &:-& a list of matrices. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt block\_matrix} creates a matrix that consists of r by c matrices +filled from the matrix\_list row wise. + +\end{addtolength} + + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\cal B} = \left( \begin{array}{cc} 1 & 0 \\ 0 & 1 +\end{array} \right), & +{\cal C} = \left( \begin{array}{c} 5 \\ 5 +\end{array} \right), & +{\cal D} = \left( \begin{array}{cc} 22 & 33 \\ 44 & 55 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.175in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt block\_matrix}(2,3,\{{\cal B,C,D,D,C,B}\}) & = & +\left( \begin{array}{ccccc} 1 & 0 & 5 & 22 & 33 \\ 0 & 1 & 5 & 44 & 55 +\\ +22 & 33 & 5 & 1 & 0 \\ 44 & 55 & 5 & 0 & 1 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + + +\subsection{char\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt char\_matrix(${\cal A},\lambda$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a square matrix. \\ +$\lambda$ &:-& a symbol or algebraic expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt char\_matrix} creates the characteristic matrix ${\cal C}$ of +${\cal A}$. + +This is ${\cal C} = \lambda * {\cal I} - {\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt char\_matrix}({\cal A},x) & = & +\left( \begin{array}{ccc} x-1 & -2 & -3 \\ -4 & x-5 & -6 \\ -7 & -8 & +x-9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt char\_poly}. + + +\subsection{char\_poly} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt char\_poly(${\cal A},\lambda$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a square matrix. \\ +$\lambda$ &:-& a symbol or algebraic expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt char\_poly} finds the characteristic polynomial of + ${\cal A}$. + +This is the determinant of $\lambda * {\cal I} - {\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\hspace*{0.175in} +{\tt char\_poly({\cal A},$x$) $= x^3-15*x^2-18*x$} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt char\_matrix}. + + +\subsection{cholesky} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt cholesky(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a positive definite matrix containing numeric entries. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt cholesky} computes the cholesky decomposition of ${\cal A}$. + +It returns \{${\cal L,U}$\} where ${\cal L}$ +is a lower matrix, ${\cal U}$ is an upper matrix, \\ ${\cal A} = +{\cal LU}$, and ${\cal U} = {\cal L}^T$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal F} = \left( \begin{array}{ccc} 1 & 1 & 0 \\ 1 & 3 & 1 \\ 0 & 1 & +1 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +${\tt cholesky}$({\cal F}) & = & +\left\{ \left( \begin{array}{ccc} 1 & 0 & 0 \\ 1 & \sqrt{2} & 0 \\ +0 & \frac{1}{\sqrt{2}} & \frac{1}{\sqrt{2}} \end{array} \right), \left( +\begin{array}{ccc} 1 & 1 & 0 \\ 0 & \sqrt{2} & \frac{1}{\sqrt{2}} \\ 0 +& 0 & \frac{1}{\sqrt{2}} \end{array} \right) +\right\} \end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt lu\_decom}. + + +\subsection{coeff\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt coeff\_matrix(\{\lineqlist{}\});} +\lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\lineqlist &:-& \parbox[t]{.435\linewidth}{linear equations. Can be +of the form {\it equation $=$ number} or just {\it equation}.} +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt coeff\_matrix} creates the coefficient matrix + ${\cal C}$ of the linear equations. + +It returns \{${\cal C,X,B}$\} such that ${\cal CX} = {\cal B}$. + +\end{addtolength} + + +{\bf Examples:} + +\begin{math} +\hspace*{0.175in} +{\tt coeff\_matrix}(\{x+y+4*z=10,y+x-z=20,x+y+4\}) = +\end{math} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +\left\{ \left( \begin{array}{ccc} 4 & 1 & 1 \\ -1 & 1 & 1 \\ 0 & 1 & 1 +\end{array} \right), \left( \begin{array}{c} z \\ y \\ x \end{array} +\right), \left( \begin{array}{c} 10 \\ 20 \\ -4 +\end{array} \right) \right\} +\end{math} +\end{flushleft} + +\subsection{column\_dim, row\_dim} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt column\_dim(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt column\_dim} finds the column dimension of + ${\cal A}$. + +\hspace*{0.175in} {\tt row\_dim} finds the row dimension of ${\cal A}$. + +{\bf Examples:} + +\hspace*{0.175in} +{\tt column\_dim}(${\cal A}$) = 3 + +\subsection{companion} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt companion(poly,x);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +poly &:-& a monic univariate polynomial in x. \\ +x &:-& the variable. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + + +\begin{addtolength}{\leftskip}{0.22in} + {\tt companion} creates the companion matrix ${\cal C}$ + of poly. + +This is the square matrix of dimension n, where n is the degree of poly +w.r.t. x. + +The entries of ${\cal C}$ are: + ${\cal C}$(i,n) = -coeffn(poly,x,i-1) for i = 1 + \ldots n, ${\cal C}$(i,i-1) = 1 for i = 2 \ldots n and + the rest are 0. + +\end{addtolength} + + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt companion}(x^4+17*x^3-9*x^2+11,x) & = & +\left( \begin{array}{cccc} 0 & 0 & 0 & -11 \\ 1 & 0 & 0 & 0 \\ +0 & 1 & 0 & 9 \\ 0 & 0 & 1 & -17 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt find\_companion}. + + +\subsection{copy\_into} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt copy\_into(${\cal A,B}$,r,c);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A,B}$ &:-& matrices. \\ +r,c &:-& positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt copy\_into} copies matrix ${\cal A}$ into + ${\cal B}$ with ${\cal A}$(1,1) at ${\cal B}$(r,c). + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal G} = \left( \begin{array}{cccc} 0 & 0 & 0 & 0 \\ 0 & 0 & 0 & 0 \\ +0 & 0 & 0 & 0 \\ 0 & 0 & 0 & 0 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt copy\_into}({\cal A,G},1,2) & = & +\left( \begin{array}{cccc} 0 & 1 & 2 & 3 \\ 0 & 4 & 5 & 6 \\ 0 & 7 & 8 +& 9 \\ 0 & 0 & 0 & 0 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt augment\_columns}, {\tt extend}, {\tt matrix\_augment}, +{\tt matrix\_stack}, {\tt stack\_rows}, {\tt sub\_matrix}. + +\end{addtolength} + + +\subsection{diagonal} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt diagonal(\{\matlist{}\});}\lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\matlist &:-& \parbox[t]{.58\linewidth}{each can be either a scalar +expr or a square matrix. } +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt diagonal} creates a matrix that contains the +input on the diagonal. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal H} = \left( \begin{array}{cc} 66 & 77 \\ 88 & 99 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt diagonal}(\{{\cal A},x,{\cal H}\}) & = & +\left( \begin{array}{cccccc} 1 & 2 & 3 & 0 & 0 & 0 \\ 4 & 5 & 6 & 0 & 0 +& 0 \\ 7 & 8 & 9 & 0 & 0 & 0 \\ 0 & 0 & 0 & x & 0 & 0 \\ 0 & 0 & 0 & 0 +& 66 & 77 \\ 0 & 0 & 0 & 0 & 88 & 99 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt jordan\_block}. + + +\subsection{extend} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt extend(${\cal A}$,r,c,expr);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +r,c &:-& positive integers. \\ +expr &:-& algebraic expression or symbol. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt extend} returns a copy of ${\cal A}$ that has been + extended by r rows and c columns. The new entries are + made equal to expr. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt extend}({\cal A},1,2,x) & = & +\left( \begin{array}{ccccc} 1 & 2 & 3 & x & x \\ 4 & 5 & 6 & x & x +\\ 7 & 8 & 9 & x & x \\ x & x & x & x & x +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\begin{addtolength}{\leftskip}{0.22in} +\parbox[t]{0.95\linewidth}{{\tt copy\_into}, {\tt matrix\_augment}, +{\tt matrix\_stack}, {\tt remove\_columns}, {\tt remove\_rows}.} + +\end{addtolength} + + +\subsection{find\_companion} + +\hspace*{0.175in} {\tt find\_companion(${\cal A}$,x);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +x &:-& the variable. +\end{tabular} + +{\bf Synopsis:} + +\begin{addtolength}{\leftskip}{0.22in} + Given a companion matrix, {\tt find\_companion} finds the polynomial +from which it was made. + +\end{addtolength} + + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal C} = \left( \begin{array}{cccc} 0 & 0 & 0 & -11 \\ 1 & 0 & 0 & 0 +\\ 0 & 1 & 0 & 9 \\ 0 & 0 & 1 & -17 +\end{array} \right) +\end{math} +\end{flushleft} + +\vspace*{3mm} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\tt find\_companion}({\cal C},x) = x^4+17*x^3-9*x^2+11 +\end{math} +\end{flushleft} + +\vspace*{3mm} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt companion}. + +\subsection{get\_columns, get\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt get\_columns(${\cal A}$,column\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +c &:-& either a positive integer or a list of positive + integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt get\_columns} removes the columns of ${\cal A}$ specified in + column\_list and returns them as a list of column + matrices. + +\end{addtolength} +\hspace*{0.175in} {\tt get\_rows} performs the same task on the rows of + ${\cal A}$. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt get\_columns}({\cal A},\{1,3\}) & = & +\left\{ + \left( \begin{array}{c} 1 \\ 4 \\ 7 \end{array} \right), + \left( \begin{array}{c} 3 \\ 6 \\ 9 \end{array} \right) +\right\} +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt get\_rows}({\cal A},2) & = & +\left\{ + \left( \begin{array}{ccc} 4 & 5 & 6 \end{array} \right) +\right\} +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}, +{\tt sub\_matrix}. + + +\subsection{get\_rows} + +\hspace*{0.175in} see: {\tt get\_columns}. + + +\subsection{gram\_schmidt} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt gram\_schmidt(\{\veclist{}\});} \lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\veclist &:-& \parbox[t]{.62\linewidth}{linearly independent vectors. + Each vector must be written as a list, + eg:\{1,0,0\}. } +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt gram\_schmidt} performs the gram\_schmidt + orthonormalisation on the input vectors. + +It returns a list of orthogonal normalised vectors. + +\end{addtolength} + +{\bf Examples:} + +\hspace*{0.175in} +{\tt gram\_schmidt(\{\{1,0,0\},\{1,1,0\},\{1,1,1\}\})} = +\{\{1,0,0\},\{0,1,0\},\{0,0,1\}\} + +\hspace*{0.175in} +{\tt gram\_schmidt(\{\{1,2\},\{3,4\}\})} $= +\{\{ \frac{1}{{\sqrt{5}}} , \frac{2}{\sqrt{5}} \}, +\{ \frac{2*\sqrt{5}}{5} , \frac{-\sqrt{5}}{5} \}\}$ + +\subsection{hermitian\_tp} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt hermitian\_tp(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt hermitian\_tp} computes the hermitian transpose of + ${\cal A}$. + +This is a matrix in which the (i,$\,$j)'th entry is the conjugate of +the (j,$\,$i)'th entry of ${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal J} = \left( \begin{array}{ccc} i+1 & i+2 & i+3 \\ 4 & 5 & 2 \\ 1 & +i & 0 +\end{array} \right) +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt hermitian\_tp}({\cal J}) & = & +\left( \begin{array}{ccc} -i+1 & 4 & 1 \\ -i+2 & 5 & -i \\-i+3 & 2 & 0 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt tp}\footnote{standard reduce call for the +transpose of a matrix - see {\REDUCE} User's Manual[2].}. + + +\subsection{hessian} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt hessian(expr,variable\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +expr &:-& a scalar expression. \\ +variable\_list &:-& either a single variable or a list of variables. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt hessian} computes the hessian matrix of expr w.r.t. + the varibles in variable\_list. + +This is an n by n matrix + where n is the number of variables and the (i,$\,$j)'th + entry is df(expr,variable\_list(i),variable\_list(j)). + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt hessian}(x*y*z+x^2,\{w,x,y,z\}) & = & +\left( \begin{array}{cccc} 0 & 0 & 0 & 0 \\ 0 & 2 & z & y \\ 0 & z & 0 +& x \\ 0 & y & x & 0 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + + +{\bf Related functions:} + +\hspace*{0.175in} {\tt df}\footnote{standard reduce call for +differentiation - see {\REDUCE} User's Manual[2]}. + + +\subsection{hilbert} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt hilbert(square\_size,expr);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +square\_size &:-& a positive integer. \\ +expr &:-& an algebraic expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt hilbert} computes the square hilbert matrix of + dimension square\_size. + +This is the symmetric matrix in + which the (i,$\,$j)'th entry is 1/(i+j-expr). + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt hilbert}(3,y+x) & = & +\left( \begin{array}{ccc} \frac{-1}{x+y-2} & \frac{-1}{x+y-3} +& \frac{-1}{x+y-4} \\ \frac{-1}{x+y-3} & \frac{-1}{x+y-4} & +\frac{-1}{x+y-5} \\ \frac{-1}{x+y-4} & \frac{-1}{x+y-5} & +\frac{-1}{x+y-6} +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + + +\subsection{jacobian} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt jacobian(expr\_list,variable\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +expr\_list \hspace*{0.175in} &:-& \parbox[t]{.72\linewidth}{either a +single algebraic expression or a list of algebraic expressions.} +\end{tabular} + +\vspace*{0.04in} +\hspace*{0.1in} +\begin{tabular}{l l l} +variable\_list &:-& either a single variable or a list of variables. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt jacobian} computes the jacobian matrix of expr\_list w.r.t. +variable\_list. + +This is a matrix whose (i,$\,$j)'th entry is df(expr\_list(i), +variable\_list(j)). + +The matrix is n by m where n is the + number of variables and m the number of expressions. + +\end{addtolength} + +{\bf Examples:} + +\hspace*{0.175in} +{\tt jacobian(\{$x^4,x*y^2,x*y*z^3$\},\{$w,x,y,z$\})} = + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +\left( \begin{array}{cccc} 0 & 4*x^3 & 0 & 0 \\ 0 & y^2 & 2*x*y & 0 \\ +0 & y*z^3 & x*z^3 & 3*x*y*z^2 +\end{array} \right) +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt hessian}, {\tt df}\footnote{standard reduce call +for differentiation - see {\REDUCE} User's Manual[2].}. + + +\subsection{jordan\_block} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt jordan\_block(expr,square\_size);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +expr &:-& an algebraic expression or symbol. \\ +square\_size &:-& a positive integer. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt jordan\_block} computes the square jordan block matrix ${\cal J}$ + of dimension square\_size. + +The entries of ${\cal J}$ are: + ${\cal J}$(i,i) = expr for i=1 + \ldots n, ${\cal J}$(i,i+1) = 1 for i=1 + \ldots n-1, and all other entries are 0. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt jordan\_block(x,5)} & = & +\left( \begin{array}{ccccc} x & 1 & 0 & 0 & 0 \\ 0 & x & 1 & 0 & 0 \\ 0 +& 0 & x & 1 & 0 \\ 0 & 0 & 0 & x & 1 \\ 0 & 0 & 0 & 0 & x +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt diagonal}, {\tt companion}. + + +\subsection{lu\_decom} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt lu\_decom(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& \parbox[t]{.848\linewidth}{a matrix containing either +numeric entries or imaginary entries with numeric coefficients.} +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt lu\_decom} performs LU decomposition on ${\cal A}$, + ie: it returns \{${\cal L,U}$\} where ${\cal L}$ + is a lower diagonal matrix, ${\cal U}$ an upper diagonal + matrix and ${\cal A} = {\cal LU}$. + +\end{addtolength} + +{\bf caution:} + +\begin{addtolength}{\leftskip}{0.22in} +The algorithm used can swap the rows of ${\cal A}$ + during the calculation. This means that ${\cal LU}$ does + not equal ${\cal A}$ but a row equivalent of it. Due to + this, {\tt lu\_decom} returns \{${\cal L,U}$,vec\}. The + call {\tt convert(${\cal A}$,vec)} will return the + matrix that has been decomposed, ie: ${\cal LU} = $ + {\tt convert(${\cal A}$,vec)}. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal K} = \left( \begin{array}{ccc} 1 & 3 & 5 \\ -4 & 3 & 7 \\ 8 & 6 & +4 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{cccc} +${\tt lu} := {\tt lu\_decom}$({\cal K}) & = & +\left\{ + \left( \begin{array}{ccc} 8 & 0 & 0 \\ -4 & 6 & 0 \\ 1 & 2.25 & +1.125 1 \end{array} \right), + \left( \begin{array}{ccc} 1 & 0.75 & 0.5 \\ 0 & 1 & 1.5 \\ 0 & +0 & 1 \end{array} \right), + [\; 3 \; 2 \; 3 \; ] +\right\} +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +${\tt first lu * second lu}$ & = & + \left( \begin{array}{ccc} 8 & 6 & 4 \\ -4 & 3 & 7 \\ 1 & 3 & 5 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +${\tt convert(${\cal K}$,third lu}$) \hspace*{0.055in} & = & + \left( \begin{array}{ccc} 8 & 6 & 4 \\ -4 & 3 & 7 \\ 1 & 3 & 5 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.5in} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal P} = \left( \begin{array}{ccc} i+1 & i+2 & i+3 \\ 4 & 5 & 2 \\ 1 +& i & 0 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{eqnarray} +\hspace*{0.22in} +{\tt lu} := {\tt lu\_decom}({\cal P}) & = & +\left\{ + \left( \begin{array}{ccc} 1 & 0 & 0 \\ 4 & -4*i+5 & 0 \\ i+1 & +3 & 0.41463*i+2.26829 \end{array} \right), \right. \nonumber \\ & & +\left. \: \; \, \left( \begin{array}{ccc} 1 & i & 0 \\ 0 & 1 & +0.19512*i+0.24390 \\ 0 & 0 & 1 \end{array} \right), \hspace*{0.05in} +[\; 3 \; 2 \; 3 \;] \hspace*{0.05in} +\right\} \nonumber +\end{eqnarray} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +${\tt first lu * second lu}$ & = & + \left( \begin{array}{ccc} 1 & i & 0 \\ 4 & 5 & 2 \\ i+1 & i+2 & +i+3 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +${\tt convert({\cal P},third lu}$) \hspace*{0.1in} & = & \left( +\begin{array}{c c c} 1 & i & 0 \\ 4 & 5 & 2 \\ i+1 & i+2 & i+3 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt cholesky}. + + +\subsection{make\_identity} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt make\_identity(square\_size);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +square\_size &:-& a positive integer. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt make\_identity} creates the identity matrix of + dimension square\_size. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt make\_identity}(4) & = & + \left( \begin{array}{cccc} 1 & 0 & 0 & 0 \\ 0 & 1 & 0 & 0 \\ 0 +& 0 & 1 & 0 \\ 0 & 0 & 0 & 1 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt diagonal}. + + +\subsection{matrix\_augment, matrix\_stack} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt matrix\_augment(\{\matlist\});}\lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\matlist &:-& matrices. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt matrix\_augment} sticks the matrices in + matrix\_list together horizontally. + +\hspace*{0.175in} +{\tt matrix\_stack} sticks the matrices in matrix\_list + together vertically. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt matrix\_augment}(\{{\cal A,A}\}) & = & + \left( \begin{array}{cccccc} 1 & 2 & 3 & 1 & 2 & 3 \\ 4 & 4 & 6 +& 4 & 5 & 6 \\ 7 & 8 & 9 & 7 & 8 & 9 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt matrix\_stack}(\{{\cal A,A}\}) & = & + \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 +\\ 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}, +{\tt sub\_matrix}. + + +\subsection{matrixp} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt matrixp(test\_input);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +test\_input &:-& anything you like. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt matrixp} is a boolean function that returns t if + the input is a matrix and nil otherwise. + +\end{addtolength} + +{\bf Examples:} + +\hspace*{0.175in} {\tt matrixp}(${\cal A}$) = t + +\hspace*{0.175in} {\tt matrixp}(doodlesackbanana) = nil + +{\bf Related functions:} + +\hspace*{0.175in} {\tt squarep}, {\tt symmetricp}. + + +\subsection{matrix\_stack} + +\hspace*{0.175in} see: {\tt matrix\_augment}. + + +\subsection{minor} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt minor(${\cal A}$,r,c);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +r,c &:-& positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} + {\tt minor} computes the (r,c)'th minor of ${\cal A}$. + + This is created by removing the r'th row and the c'th + column from ${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt minor}({\cal A},1,3) & = & + \left( \begin{array}{cc} 4 & 5 \\ 7 & 8 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt remove\_columns}, {\tt remove\_rows}. + + +\subsection{mult\_columns, mult\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt mult\_columns(${\cal A}$,column\_list,expr);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +column\_list &:-& a positive integer or a list of positive integers. \\ +expr &:-& an algebraic expression. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt mult\_columns} returns a copy of ${\cal A}$ in which + the columns specified in column\_list have been +multiplied by expr. + +{\tt mult\_rows} performs the same task on the rows of ${\cal A}$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt mult\_columns}({\cal A},\{1,3\},x) & = & + \left( \begin{array}{ccc} x & 2 & 3*x \\ 4*x & 5 & 6*x \\ 7*x & +8 & 9*x + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt mult\_rows}({\cal A},2,10) & = & + \left( \begin{array}{ccc} 1 & 2 & 3 \\ 40 & 50 & 60 \\ 7 & 8 & +9 \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt add\_to\_columns}, {\tt add\_to\_rows}. + + +\subsection{\tt mult\_rows} + +\hspace*{0.175in} see: {\tt mult\_columns}. + + +\subsection{pivot} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt pivot(${\cal A}$,r,c);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +r,c &:-& positive integers such that ${\cal A}$(r,c) neq 0. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt pivot} pivots ${\cal A}$ about its (r,c)'th entry. + +To do this, multiples of the r'th row are added to every + other row in the matrix. + +This means that the c'th column + will be 0 except for the (r,c)'th entry. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt pivot}({\cal A},2,3) & = & + \left( \begin{array}{ccc} -1 & -0.5 & 0 \\ 4 & 5 & 6 \\ 1 & 0.5 +& 0 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt rows\_pivot}. + + +\subsection{pseudo\_inverse} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt pseudo\_inverse(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt pseudo\_inverse}, also known as the Moore-Penrose inverse, computes +the pseudo inverse of ${\cal A}$. + +Given the singular value decomposition of ${\cal A}$, i.e: ${\cal A} = +{\cal U} +\sum {\cal V}^T$, then the pseudo inverse ${\cal A}^{-1}$ is defined +by ${\cal A}^{-1} = {\cal V}^T \sum^{-1} {\cal U}$. + +Thus ${\cal A}$ $ * $ {\tt pseudo\_inverse}$({\cal A}) = {\cal I}$. + +\end{addtolength} + +{\bf Examples:} + +% \begin{flushleft} +% \hspace*{0.175in} +% \begin{math} +% {\cal R} = \left( \begin{array}{cccc} 1 & 2 & 3 & 4 \\ 9 & 8 & 7 & 6 +% \end{array} \right) +% \end{math} +% \end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt pseudo\_inverse}({\cal A}) & = & + \left( \begin{array}{cc} -0.2 & 0.1 \\ -0.05 & 0.05 \\ 0.1 & 0 +\\ 0.25 & -0.05 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt svd}. + +\subsection{random\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt random\_matrix(r,c,limit);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +r,c,$\,$limit &:-& positive integers. \\ +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt random\_matrix} creates an r by c matrix with random + entries in the range $-$limit $<$ entry $<$ limit. + +\end{addtolength} + +{\bf switches:} + +\hspace*{0.1in} +\begin{tabular}{l l l} +{\tt imaginary} \hspace*{0.175in} &:-& \parbox[t]{0.685\linewidth}{if +on then matrix entries are x+i$*$y where $-$limit $<$ x,y $<$ limit.} +\end{tabular} + +\vspace*{0.04in} +\hspace*{0.1in} +\begin{tabular}{l l l} +{\tt not\_negative} &:-& \parbox[t]{0.685\linewidth}{if on then 0 $<$ +entry $<$ limit. In the imaginary case we have 0 $<$ x,y $<$ limit.} +\end{tabular} + +\vspace*{0.04in} +\hspace*{0.1in} +\begin{tabular}{l l l} +{\tt only\_integer} &:-& \parbox[t]{0.685\linewidth}{if on then each +entry is an integer. In the imaginary case x and y are integers.} +\end{tabular} + +\vspace*{0.04in} +\hspace*{0.1in} +\begin{tabular}{l l l} +{\tt symmetric} &:-& if on then the matrix is symmetric. \\ +{\tt upper\_matrix} &:-& \parbox[t]{0.685\linewidth}{if on then the +matrix is upper triangular.} \\ +{\tt lower\_matrix} &:-& if on then the matrix is lower triangular. +\end{tabular} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt random\_matrix}(3,3,10) & = & + \left( \begin{array}{ccc} -4.729721 & 6.987047 & 7.521383 \\ +- 5.224177 & 5.797709 & - 4.321952 \\ +- 9.418455 & - 9.94318 & - 0.730980 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.2in} +\hspace*{0.165in} +{\tt on only\_integer, not\_negative, upper\_matrix, imaginary;} +\begin{flushleft} +\hspace*{0.12in} +\begin{math} +\begin{array}{ccc} +{\tt random\_matrix}(4,4,10) & = & +\left( \begin{array}{cccc} 2*i+5 & 3*i+7 & 7*i+3 & 6 \\ 0 & 2*i+5 & +5*i+1 & 2*i+1 \\ 0 & 0 & 8 & i \\ 0 & 0 & 0& 5*i+9 +\end{array} \right) +\end{array} +\end{math} +\end{flushleft} + + +\subsection{remove\_columns, remove\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt remove\_columns(${\cal A}$,column\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +column\_list &:-& either a positive integer or a list of + positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt remove\_columns} removes the columns specified in + column\_list from ${\cal A}$. + +\hspace*{0.175in} {\tt remove\_rows} performs the same task on the rows + of ${\cal A}$. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt remove\_columns}({\cal A},2) & = & + \left( \begin{array}{cc} 1 & 3 \\ 4 & 6 \\ 7 & 9 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt remove\_rows}({\cal A},\{1,3\}) & = & + \left( \begin{array}{ccc} 4 & 5 & 6 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + + +{\bf Related functions:} + +\hspace*{0.175in} {\tt minor}. + + +\subsection{remove\_rows} + +\hspace*{0.175in} see: {\tt remove\_columns}. + + +\subsection{row\_dim} + +\hspace{0.175in} see: {\tt column\_dim}. + + +\subsection{rows\_pivot} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt rows\_pivot(${\cal A}$,r,c,\{row\_list\});} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +r,c &:-& positive integers such that ${\cal A}$(r,c) neq 0.\\ +row\_list &:-& positive integer or a list of positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt rows\_pivot} performs the same task as {\tt pivot} but applies +the pivot only to the rows specified in row\_list. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal N} = \left( \begin{array}{ccc} 1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & +9 \\1 & 2 & 3 \\ 4 & 5 & 6 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt rows\_pivot}({\cal N},2,3,\{4,5\}) & = & \left( \begin{array} +{c c c}1 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 9 \\ -0.75 & 0 & 0.75 \\ +-0.375 & 0 & 0.375 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt pivot}. + + +\subsection{simplex} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt simplex(max/min,objective function,\{linear +inequalities\});} + +\hspace*{0.1in} +\begin{tabular}{l l l} +max/min & :- & \parbox[t]{.63\linewidth}{either max or min + (signifying maximise and minimise).} \\ +objective function & :- & the function you are maximising or + minimising. \\ +linear inequalities & :- & \parbox[t]{.63\linewidth}{the constraint + inequalities. Each one must be of the form + {\it sum of variables ($<=,=,>=$) number}.} +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt simplex} applies the revised simplex algorithm to find the +optimal(either maximum or minimum) value of the objective function +under the linear inequality constraints. + +It returns \{optimal value,\{ values of variables at this optimal\}\}. + +The algorithm implies that all the variables are non-negative. + +\end{addtolength} + +{\bf Examples:} + +\begin{addtolength}{\leftskip}{0.22in} +%\begin{math} +{\tt simplex($max,x+y,\{x>=10,y>=20,x+y<=25\}$);} +%\end{math} + +{\tt ***** Error in simplex: Problem has no feasible solution.} + +\vspace*{0.2in} + +\parbox[t]{0.96\linewidth}{\tt simplex($max,10x+5y+5.5z,\{5x+3z<=200, +x+0.1y+0.5z<=12$,\\ +\hspace*{0.55in} $0.1x+0.2y+0.3z<=9, 30x+10y+50z<=1500\}$);} + +\vspace*{0.1in} +{\tt $\{525.0,\{x=40.0,y=25.0,z=0\}$\}} + +\end{addtolength} + + +\subsection{squarep} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt squarep(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt squarep} is a boolean function that returns t if + the matrix is square and nil otherwise. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal L} = \left( \begin{array}{ccc} 1 & 3 & 5 +\end{array} \right) +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\hspace*{0.175in} {\tt squarep}(${\cal A}$) = t + +\hspace*{0.175in} {\tt squarep}(${\cal L}$) = nil + +{\bf Related functions:} + +\hspace*{0.175in} {\tt matrixp}, {\tt symmetricp}. + + +\subsection{stack\_rows} + +\hspace*{0.175in} see: {\tt augment\_columns}. + + +\subsection{sub\_matrix} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt sub\_matrix(${\cal A}$,row\_list,column\_list);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +row\_list, column\_list &:-& \parbox[t]{.605\linewidth}{either a +positive integer or a list of positive integers.} +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + + +\begin{addtolength}{\leftskip}{0.22in} + +{\tt sub\_matrix} produces the matrix consisting of the + intersection of the rows specified in row\_list and the +columns specified in column\_list. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt sub\_matrix}({\cal A},\{1,3\},\{2,3\}) & = & + \left( \begin{array}{cc} 2 & 3 \\ 8 & 9 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt augment\_columns}, {\tt stack\_rows}. + + +\subsection{svd (singular value decomposition)} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt svd(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix containing only numeric entries. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt svd} computes the singular value decomposition of ${\cal A}$. + +It returns \{${\cal U},\sum,{\cal V}$\} where ${\cal A} = {\cal U} +\sum {\cal V}^T$ and $\sum = diag(\sigma_{1}, \ldots ,\sigma_{n}). \; +\sigma_{i}$ for $i= (1 \ldots n)$ are the singular values of ${\cal A}$. + + +n is the column dimension of ${\cal A}$. + +The singular values of ${\cal A}$ are the non-negative square roots of +the eigenvalues of ${\cal A}^T {\cal A}$. + +${\cal U}$ and ${\cal V}$ are such that ${\cal UU}^T = {\cal VV}^T = +{\cal V}^T {\cal V} = {\cal I}_n$. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal Q} = \left( \begin{array}{cc} 1 & 3 \\ -4 & 3 +\end{array} \right) +\end{math} +\end{flushleft} + +\begin{eqnarray} +\hspace*{0.1in} +{\tt svd({\cal Q})} & = & +\left\{ + \left( \begin{array}{cc} 0.289784 & 0.957092 \\ -0.957092 & +0.289784 \end{array} \right), \left( \begin{array}{cc} 5.149162 & 0 \\ +0 & 2.913094 \end{array} \right), \right. \nonumber \\ & & \left. \: \; +\, \left( \begin{array}{cc} -0.687215 & 0.726453 \\ -0.726453 & +-0.687215 \end{array} \right) +\right\} \nonumber +\end{eqnarray} + + +\subsection{swap\_columns, swap\_rows} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt swap\_columns(${\cal A}$,c1,c2);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +c1,c1 &:-& positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} +{\tt swap\_columns} swaps column c1 of ${\cal A}$ with column c2. + +\hspace*{0.175in} {\tt swap\_rows} performs the same task on 2 rows of + ${\cal A}$. + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt swap\_columns}({\cal A},2,3) & = & + \left( \begin{array}{ccc} 1 & 3 & 2 \\ 4 & 6 & 5 \\ 7 & 9 & 8 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt swap\_entries}. + + +\subsection{swap\_entries} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt swap\_entries(${\cal A}$,\{r1,c1\},\{r2,c2\});} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. \\ +r1,c1,r2,c2 &:-& positive integers. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\hspace*{0.175in} {\tt swap\_entries} swaps ${\cal A}$(r1,c1) with + ${\cal A}$(r2,c2). + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt swap\_entries}({\cal A},\{1,1\},\{3,3\}) & = & + \left( \begin{array}{ccc} 9 & 2 & 3 \\ 4 & 5 & 6 \\ 7 & 8 & 1 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +{\bf Related functions:} + +\hspace*{0.175in} {\tt swap\_columns}, {\tt swap\_rows}. + + +\subsection{swap\_rows} + +\hspace*{0.175in} see: {\tt swap\_columns}. + + +\subsection{symmetricp} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt symmetricp(${\cal A}$);} + +\hspace*{0.1in} +\begin{tabular}{l l l} +${\cal A}$ &:-& a matrix. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt symmetricp} is a boolean function that returns t if the + matrix is symmetric and nil otherwise. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.175in} +\begin{math} +{\cal M} = \left( \begin{array}{cc} 1 & 2 \\ 2 & 1 +\end{array} \right) +\end{math} +\end{flushleft} + +\vspace*{0.1in} + +\hspace*{0.175in} {\tt symmetricp}(${\cal A}$) = nil + +\hspace*{0.175in} {\tt symmetricp}(${\cal M}$) = t + +{\bf Related functions:} + +\hspace*{0.175in} {\tt matrixp}, {\tt squarep}. + + +\subsection{toeplitz} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt toeplitz(\{\exprlist{}\});} \lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\exprlist{} &:-& algebraic expressions. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt toeplitz} creates the toeplitz matrix from the + expression list. + +This is a square symmetric matrix in + which the first expression is placed on the diagonal + and the i'th expression is placed on the (i-1)'th sub + and super diagonals. + +It has dimension n where n is the + number of expressions. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt toeplitz}(\{w,x,y,z\}) & = & + \left( \begin{array}{cccc} w & x & y & z \\ x & w & x & y \\ + y & x & w & x \\ z & y & x & w + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\subsection{Vandermonde} + +%{\bf How to use it:} + +\hspace*{0.175in} {\tt vandermonde}(\{\exprlist{}\}); \addtocounter +{footnote}{-1}\footnotemark +%\lazyfootnote{} + +\hspace*{0.1in} +\begin{tabular}{l l l} +\exprlist{} &:-& algebraic expressions. +\end{tabular} + +{\bf Synopsis:} %{\bf What it does:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt Vandermonde} creates the Vandermonde matrix from + the expression list. + +This is the square matrix in which + the (i,$\,$j)'th entry is expr\_list(i) $^{(j-1)}$. + +It has dimension n where n is the number of expressions. + +\end{addtolength} + +{\bf Examples:} + +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +{\tt vandermonde}(\{x,2*y,3*z\}) & = & + \left( \begin{array}{ccc} 1 & x & x^2 \\ 1 & 2*y & 4*y^2 \\ 1 +& 3*z & 9*z^2 + \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\subsection{kronecker\_product} + +\hspace*{0.175in} {\tt kronecker\_product}($Mat_1,Mat_2$) + +\hspace*{0.1in} +\begin{tabular}{l l l} +$Mat_1,Mat_2$ &:-& Matrices +\end{tabular} + +{\bf Synopsis:} + +\begin{addtolength}{\leftskip}{0.22in} +{\tt kronecker\_product} creates a matrix containing the Kronecker product +(also called {\tt direct product} or {\tt tensor product}) of its arguments. + +\end{addtolength} + +{\bf Examples:} +\begin{verbatim} +a1 := mat((1,2),(3,4),(5,6))$ +a2 := mat((1,1,1),(2,z,2),(3,3,3))$ +kronecker_product(a1,a2); +\end{verbatim} +\begin{flushleft} +\hspace*{0.1in} +\begin{math} +\begin{array}{ccc} +\left( \begin{array}{cccccc} 1 & 1 & 1 & 2 & 2 & 2 \\ +2 & z & 2 & 4 &2*z &4 \\ +3 & 3 & 3 & 6 & 6 &6 \\ +3 & 3 & 3 & 4 & 4 &4 \\ +6 & 3*z& 6 & 8 &4*z &8 \\ +9 & 9 & 9 & 12 &12 &12\\ +5 & 5 & 5 & 6 & 6 &6 \\ +10 &5*z& 10& 12 &6*z &12 \\ +15 &15 & 15& 18 &18 &18 \end{array} \right) +\end{array} +\end{math} +\end{flushleft} + +\section{Fast Linear Algebra} + +By turning the {\tt fast\_la} switch on, the speed of the following +functions will be increased: + +\begin{tabular}{l l l l} + add\_columns & add\_rows & augment\_columns & column\_dim \\ + copy\_into & make\_identity & matrix\_augment & matrix\_stack\\ + minor & mult\_column & mult\_row & pivot \\ + remove\_columns & remove\_rows & rows\_pivot & squarep \\ + stack\_rows & sub\_matrix & swap\_columns & swap\_entries\\ + swap\_rows & symmetricp +\end{tabular} + +The increase in speed will be insignificant unless you are making a +significant number(i.e: thousands) of calls. When using this switch, +error checking is minimised. This means that illegal input may give +strange error messages. Beware. + +\newpage + +\section{Acknowledgments} + +Many of the ideas for this package came from the Maple[3] Linalg package +[4]. + +The algorithms for {\tt cholesky}, {\tt lu\_decom}, and {\tt svd} are +taken from the book Linear Algebra - J.H. Wilkinson \& C. Reinsch[5]. + +The {\tt gram\_schmidt} code comes from Karin Gatermann's Symmetry +package[6] for {\REDUCE}. + + +\begin{thebibliography}{} +\bibitem{matt} Matt Rebbeck: NORMFORM: A {\REDUCE} package for the +computation of various matrix normal forms. ZIB, Berlin. (1993) +\bibitem{Reduce} Anthony C. Hearn: {\REDUCE} User's Manual 3.6. + RAND (1995) +\bibitem{Maple} Bruce W. Char\ldots [et al.]: Maple (Computer + Program). Springer-Verlag (1991) +\bibitem{linalg} Linalg - a linear algebra package for Maple[3]. +\bibitem{WiRe} J. H. Wilkinson \& C. Reinsch: Linear Algebra +(volume II). Springer-Verlag (1971) +\bibitem{gat} Karin Gatermann: Symmetry: A {\REDUCE} package for the +computation of linear representations of groups. ZIB, Berlin. (1992) +\end{thebibliography} + +\end{document} + + + Index: r36/doc/NCPOLY.TEX ================================================================== --- r36/doc/NCPOLY.TEX +++ r36/doc/NCPOLY.TEX @@ -1,296 +1,296 @@ -\documentstyle[11pt,reduce]{article} -\title{NCPOLY: Computation in non--commutative polynomial ideals} -\date{} -\author{ -Herbert Melenk\\[0.05in] -Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ -Heilbronner Strasse 10 \\ -D--10711 Berlin -- Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -E--mail: melenk@zib--berlin.de \\[0.1in] -Joachim Apel\\[0.05in] -Institut f\"ur Informatik \\[0.05in] -Universit\"at Leipzig \\[0.05in] -Augustusplatz 10--11\\[0.05in] -D--04109 Leipzig \\[0.05in] -Federal Republic of Germany \\[0.05in] -E--mail: apel@informatik.uni--leipzig.de \\[0.05in] -} - -\begin{document} -\maketitle - -\index{Groebner Bases} -\section{Introduction} - -{\small REDUCE} supports a very general mechanism for computing -with objects under a non--commutative multiplication, where -commutator relations must be introduced explicitly by rule -sets when needed. The package {\bf NCPOLY} allows you to -set up automatically a consistent environment for computing in an algebra -where the non--commutativity is defined by Lie-bracket commutators. -The package uses the {\small REDUCE} {\bf noncom} -mechanism for elementary polynomial arithmetic; the commutator -rules are automatically computed from the Lie brackets. -You can perform polynomial arithmetic directly, including -{\bf division} and {\bf factorization}. -Additionally {\bf NCPOLY} supports computations in a one sided ideal (left or right), -especially one sided {\bf Gr\"obner} bases and {\bf polynomial reduction}. - -\section{Setup, Cleanup} - -Before the computations can start the environment for a -non--commutative computation must be defined by a -call to {\bf nc\_setup}: -\begin{verbatim} - nc_setup([,][,]); -\end{verbatim} -where - -$$ is a list of variables; these must include the -non--commutative quantities. - -$$ is a list of equations \verb&* - *=& -where $$ and $$ are members of $$, and $$ is -a polynomial. - -$$ is either $left$ or $right$ selecting a left or a -right one sided ideal. The initial direction is $left$. - -{\bf nc\_setup} generates from $$ the necessary -rules to support an algebra where all monomials are -ordered corresponding to the given variable sequence. -All pairs of variables which are not explicitly covered in -the commutator set are considered as commutative and the -corresponding rules are also activated. - -The second parameter in {\bf nc\_setup} may be -omitted if the operator is called for the second time, -e.g. with a reordered variable sequence. In such a case -the last commutator set is used again. - -Remarks: \begin{itemize} -\item The variables need not be declared {\bf noncom} - - {\bf nc\_setup} performs all necessary declarations. -\item The variables need not be formal operator expressions; - {\bf nc\_setup} encapsulates a variable $x$ internally - as \verb+nc!*(!_x)+ expressions anyway where the operator $nc!*$ - keeps the noncom property. -\item The commands {\bf order} and {\bf korder} should be avoided - because {\bf nc\_setup} sets these such that the computation - results are printed in the correct term order. -\end{itemize} - -Example: -\begin {verbatim} - nc_setup({KK,NN,k,n}, - {NN*n-n*NN= NN, KK*k-k*KK= KK}); - - NN*n; -> NN*n - n*NN; -> NN*n - NN - nc_setup({k,n,KK,NN}); - NN*n - NN -> n*NN; - -\end{verbatim} -Here $KK,NN,k,n$ are non--commutative variables where -the commutators are described as $[NN,n]=NN$, $[KK,k]=KK$. - -The current term order must be compatible with the commutators: -the product $*$ must precede all terms on the right hand -side $$ under the current term order. Consequently -\begin{itemize} -\item the maximal degree of $$ or $$ in $$ is 1, -\item in a total degree ordering the total degree of $$ may be -not higher than 1, -\item in an elimination degree order (e.g. $lex$) all variables in -$$ must be below the minimum of $$ and $$. -\item If $$ does not contain any variables or has at most $$ or -$$, any term order can be selected. -\end{itemize} - -If you want to use the non--commutative variables or results from -non--commutative computations later in commutative operations -it might be necessary to switch off the non--commutative -evaluation mode because not -all operators in REDUCE are prepared for that environment. In -such a case use the command -\begin{verbatim} - nc_cleanup; -\end{verbatim} -without parameters. It removes all internal rules and definitions -which {\bf nc\_setup} had introduced. To reactive non--commutative -call {\bf nc\_setup} again. - -\section{Left and right ideals} - -A (polynomial) left ideal $L$ is defined by the axioms - -$u \in L, v \in L \Longrightarrow u+v \in L$ - -$u \in L \Longrightarrow k*u \in L$ for an arbitrary polynomial $k$ - -where ``*'' is the non--commutative multiplication. Correspondingly, -a right ideal $R$ is defined by - -$u \in R, v \in R \Longrightarrow u+v \in R$ - -$u \in R \Longrightarrow u*k \in R$ for an arbitrary polynomial $k$ - -\section{Gr\"obner bases} - -When a non--commutative environment has been set up -by {\bf nc\_setup}, a basis for a left or right polynomial ideal -can be transformed into a Gr\"obner basis by the operator -{\bf nc\_groebner}: -\begin{verbatim} - nc_groebner(); -\end{verbatim} -Note that the variable set and variable sequence must be -defined before in the {\bf nc\_setup} call. The term order -for the Gr\"obner calculation can be set by using the -{\bf torder} declaration. The internal steps of the -Gr\"obner calculation can be watched by setting the -switches {\bf trgroeb} (=list all internal basis polynomials) -or {\bf trgroebs} (=list additionally the $S$-polynomials) -\footnote{The command \verb+lisp(!*trgroebfull:=t);+ causes additionally -all elementary polynomial operations to be printed.}. - - -For details about {\bf torder}, {\bf trgroeb} and {\bf trgroebs} -see the {\bf {\small REDUCE} GROEBNER} manual. -\begin{verbatim} -2: nc_setup({k,n,NN,KK},{NN*n-n*NN=NN,KK*k-k*KK=KK},left); - -3: p1 := (n-k+1)*NN - (n+1); - -p1 := - k*nn + n*nn - n + nn - 1 - -4: p2 := (k+1)*KK -(n-k); - -p2 := k*kk + k - n + kk - -5: nc_groebner ({p1,p2}); - -{k*nn - n*nn + n - nn + 1, - - k*kk + k - n + kk, - - n*nn*kk - n*kk - n + nn*kk - kk - 1} - -\end{verbatim} -Important: Do not use the operators of the GROEBNER -package directly as they would not consider the non--commutative -multiplication. - -\section{Left or right polynomial division} - -The operator {\bf nc\_divide} computes the one sided quotient and remainder of -two polynomials: -\begin{verbatim} - nc_divide(,); -\end{verbatim} -The result is a list with quotient and remainder. -The division is performed as a pseudo--division, multiplying -$$ by coefficients if necessary. The result $\{,\}$ -is defined by the relation - - $*=* + $ for direction $left$ and - - $*=* + $ for direction $right$, - -where $$ is an expression that does not contain any of the -ideal variables, and the leading term of $$ is lower than -the leading term of $$ according to the actual term order. - -\section{Left or right polynomial reduction} - -For the computation of the one sided remainder of a polynomial -modulo a given set of other polynomials the operator -{\bf nc\_preduce} may be used: -\begin{verbatim} - nc_preduce(,); -\end{verbatim} -The result of the reduction is unique (canonical) if -and only if $$ is a one sided Gr\"obner basis. -Then the computation is at the same time an ideal -membership test: if the result is zero, the -polynomial is member of the ideal, otherwise not. - -\section{Factorization} - -Polynomials in a non--commutative ring cannot be factored -using the ordinary {\bf factorize} command of {\small REDUCE}. -Instead one of the operators of this section must be used: -\begin{verbatim} - nc_factorize(); -\end{verbatim} -The result is a list of factors of $$. A list -with the input expression is returned if it is irreducible. - -As non--commutative factorization is not unique, there is -an additional operator which computes all possible factorizations -\begin{verbatim} - nc_factorize_all(); -\end{verbatim} -The result is a list of factor decompositions of $$. -If there are no factors at all the result list has only one -member which is a list containing the input polynomial. - -In contrast to factoring in commutative polynomial rings, the non--commutative -factorization is rather time consuming. Therefore two additional -operators allow you to reduce the amount of computing time when -you look only for isolated factors in special context, e.g. factors -with a limited degree or factors which contain only explicitly -specified variables: -\begin{verbatim} - left_factor([,[,]]) - right_factor([,[,]]) - left_factors([,[,]]) - right_factors([,[,]]) -\end{verbatim} -where $$ is the form under investigation, -$$ is an optional list of variables which must appear in the -factor, and $$ -is an optional integer degree bound for the total degree of the -factor, a zero for an unbounded search, or a monomial -(product of powers of the variables) where each exponent -is an individual degree bound for its base variable; unmentioned -variables are allowed in arbitrary degree. The operators -$*\_factor$ stop when they have found one factor, while -the operators $*\_factors$ select all one--sided factors -within the given range. If there is no factor of the -desired type, an empty list is returned by $*\_factors$ -while the routines $*\_factor$ return the input polynomial. - - -The share variable $nc\_factor\_time$ sets an upper limit -for the time to be spent for a call to the non--commutative -factorizer. If the value is a positive integer, a -factorization is terminated with an error message as soon -as the time limit is reached. The time units are milliseconds. - -\section{Output of expressions} - -It is often desirable to have the commutative parts (coefficients) -in a non--commutative operation condensed by factorization. The operator -\begin{verbatim} - nc_compact() -\end{verbatim} -collects the coefficients to the powers of the lowest possible -non-commutative variable. -\begin{verbatim} -load ncpoly; - -nc_setup({n,NN},{NN*n-n*NN=NN})$ -p1 := n**4 + n**2*nn + 4*n**2 + 4*n*nn + 4*nn + 4; - - 4 2 2 -p1 := n + n *nn + 4*n + 4*n*nn + 4*nn + 4 - -nc_compact p1; - - 2 2 2 -(n + 2) + (n + 2) *nn -\end{verbatim} -\end{document} - +\documentstyle[11pt,reduce]{article} +\title{NCPOLY: Computation in non--commutative polynomial ideals} +\date{} +\author{ +Herbert Melenk\\[0.05in] +Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ +Heilbronner Strasse 10 \\ +D--10711 Berlin -- Wilmersdorf \\ +Federal Republic of Germany \\[0.05in] +E--mail: melenk@zib--berlin.de \\[0.1in] +Joachim Apel\\[0.05in] +Institut f\"ur Informatik \\[0.05in] +Universit\"at Leipzig \\[0.05in] +Augustusplatz 10--11\\[0.05in] +D--04109 Leipzig \\[0.05in] +Federal Republic of Germany \\[0.05in] +E--mail: apel@informatik.uni--leipzig.de \\[0.05in] +} + +\begin{document} +\maketitle + +\index{Groebner Bases} +\section{Introduction} + +{\small REDUCE} supports a very general mechanism for computing +with objects under a non--commutative multiplication, where +commutator relations must be introduced explicitly by rule +sets when needed. The package {\bf NCPOLY} allows you to +set up automatically a consistent environment for computing in an algebra +where the non--commutativity is defined by Lie-bracket commutators. +The package uses the {\small REDUCE} {\bf noncom} +mechanism for elementary polynomial arithmetic; the commutator +rules are automatically computed from the Lie brackets. +You can perform polynomial arithmetic directly, including +{\bf division} and {\bf factorization}. +Additionally {\bf NCPOLY} supports computations in a one sided ideal (left or right), +especially one sided {\bf Gr\"obner} bases and {\bf polynomial reduction}. + +\section{Setup, Cleanup} + +Before the computations can start the environment for a +non--commutative computation must be defined by a +call to {\bf nc\_setup}: +\begin{verbatim} + nc_setup([,][,]); +\end{verbatim} +where + +$$ is a list of variables; these must include the +non--commutative quantities. + +$$ is a list of equations \verb&* - *=& +where $$ and $$ are members of $$, and $$ is +a polynomial. + +$$ is either $left$ or $right$ selecting a left or a +right one sided ideal. The initial direction is $left$. + +{\bf nc\_setup} generates from $$ the necessary +rules to support an algebra where all monomials are +ordered corresponding to the given variable sequence. +All pairs of variables which are not explicitly covered in +the commutator set are considered as commutative and the +corresponding rules are also activated. + +The second parameter in {\bf nc\_setup} may be +omitted if the operator is called for the second time, +e.g. with a reordered variable sequence. In such a case +the last commutator set is used again. + +Remarks: \begin{itemize} +\item The variables need not be declared {\bf noncom} - + {\bf nc\_setup} performs all necessary declarations. +\item The variables need not be formal operator expressions; + {\bf nc\_setup} encapsulates a variable $x$ internally + as \verb+nc!*(!_x)+ expressions anyway where the operator $nc!*$ + keeps the noncom property. +\item The commands {\bf order} and {\bf korder} should be avoided + because {\bf nc\_setup} sets these such that the computation + results are printed in the correct term order. +\end{itemize} + +Example: +\begin {verbatim} + nc_setup({KK,NN,k,n}, + {NN*n-n*NN= NN, KK*k-k*KK= KK}); + + NN*n; -> NN*n + n*NN; -> NN*n - NN + nc_setup({k,n,KK,NN}); + NN*n - NN -> n*NN; + +\end{verbatim} +Here $KK,NN,k,n$ are non--commutative variables where +the commutators are described as $[NN,n]=NN$, $[KK,k]=KK$. + +The current term order must be compatible with the commutators: +the product $*$ must precede all terms on the right hand +side $$ under the current term order. Consequently +\begin{itemize} +\item the maximal degree of $$ or $$ in $$ is 1, +\item in a total degree ordering the total degree of $$ may be +not higher than 1, +\item in an elimination degree order (e.g. $lex$) all variables in +$$ must be below the minimum of $$ and $$. +\item If $$ does not contain any variables or has at most $$ or +$$, any term order can be selected. +\end{itemize} + +If you want to use the non--commutative variables or results from +non--commutative computations later in commutative operations +it might be necessary to switch off the non--commutative +evaluation mode because not +all operators in REDUCE are prepared for that environment. In +such a case use the command +\begin{verbatim} + nc_cleanup; +\end{verbatim} +without parameters. It removes all internal rules and definitions +which {\bf nc\_setup} had introduced. To reactive non--commutative +call {\bf nc\_setup} again. + +\section{Left and right ideals} + +A (polynomial) left ideal $L$ is defined by the axioms + +$u \in L, v \in L \Longrightarrow u+v \in L$ + +$u \in L \Longrightarrow k*u \in L$ for an arbitrary polynomial $k$ + +where ``*'' is the non--commutative multiplication. Correspondingly, +a right ideal $R$ is defined by + +$u \in R, v \in R \Longrightarrow u+v \in R$ + +$u \in R \Longrightarrow u*k \in R$ for an arbitrary polynomial $k$ + +\section{Gr\"obner bases} + +When a non--commutative environment has been set up +by {\bf nc\_setup}, a basis for a left or right polynomial ideal +can be transformed into a Gr\"obner basis by the operator +{\bf nc\_groebner}: +\begin{verbatim} + nc_groebner(); +\end{verbatim} +Note that the variable set and variable sequence must be +defined before in the {\bf nc\_setup} call. The term order +for the Gr\"obner calculation can be set by using the +{\bf torder} declaration. The internal steps of the +Gr\"obner calculation can be watched by setting the +switches {\bf trgroeb} (=list all internal basis polynomials) +or {\bf trgroebs} (=list additionally the $S$-polynomials) +\footnote{The command \verb+lisp(!*trgroebfull:=t);+ causes additionally +all elementary polynomial operations to be printed.}. + + +For details about {\bf torder}, {\bf trgroeb} and {\bf trgroebs} +see the {\bf {\small REDUCE} GROEBNER} manual. +\begin{verbatim} +2: nc_setup({k,n,NN,KK},{NN*n-n*NN=NN,KK*k-k*KK=KK},left); + +3: p1 := (n-k+1)*NN - (n+1); + +p1 := - k*nn + n*nn - n + nn - 1 + +4: p2 := (k+1)*KK -(n-k); + +p2 := k*kk + k - n + kk + +5: nc_groebner ({p1,p2}); + +{k*nn - n*nn + n - nn + 1, + + k*kk + k - n + kk, + + n*nn*kk - n*kk - n + nn*kk - kk - 1} + +\end{verbatim} +Important: Do not use the operators of the GROEBNER +package directly as they would not consider the non--commutative +multiplication. + +\section{Left or right polynomial division} + +The operator {\bf nc\_divide} computes the one sided quotient and remainder of +two polynomials: +\begin{verbatim} + nc_divide(,); +\end{verbatim} +The result is a list with quotient and remainder. +The division is performed as a pseudo--division, multiplying +$$ by coefficients if necessary. The result $\{,\}$ +is defined by the relation + + $*=* + $ for direction $left$ and + + $*=* + $ for direction $right$, + +where $$ is an expression that does not contain any of the +ideal variables, and the leading term of $$ is lower than +the leading term of $$ according to the actual term order. + +\section{Left or right polynomial reduction} + +For the computation of the one sided remainder of a polynomial +modulo a given set of other polynomials the operator +{\bf nc\_preduce} may be used: +\begin{verbatim} + nc_preduce(,); +\end{verbatim} +The result of the reduction is unique (canonical) if +and only if $$ is a one sided Gr\"obner basis. +Then the computation is at the same time an ideal +membership test: if the result is zero, the +polynomial is member of the ideal, otherwise not. + +\section{Factorization} + +Polynomials in a non--commutative ring cannot be factored +using the ordinary {\bf factorize} command of {\small REDUCE}. +Instead one of the operators of this section must be used: +\begin{verbatim} + nc_factorize(); +\end{verbatim} +The result is a list of factors of $$. A list +with the input expression is returned if it is irreducible. + +As non--commutative factorization is not unique, there is +an additional operator which computes all possible factorizations +\begin{verbatim} + nc_factorize_all(); +\end{verbatim} +The result is a list of factor decompositions of $$. +If there are no factors at all the result list has only one +member which is a list containing the input polynomial. + +In contrast to factoring in commutative polynomial rings, the non--commutative +factorization is rather time consuming. Therefore two additional +operators allow you to reduce the amount of computing time when +you look only for isolated factors in special context, e.g. factors +with a limited degree or factors which contain only explicitly +specified variables: +\begin{verbatim} + left_factor([,[,]]) + right_factor([,[,]]) + left_factors([,[,]]) + right_factors([,[,]]) +\end{verbatim} +where $$ is the form under investigation, +$$ is an optional list of variables which must appear in the +factor, and $$ +is an optional integer degree bound for the total degree of the +factor, a zero for an unbounded search, or a monomial +(product of powers of the variables) where each exponent +is an individual degree bound for its base variable; unmentioned +variables are allowed in arbitrary degree. The operators +$*\_factor$ stop when they have found one factor, while +the operators $*\_factors$ select all one--sided factors +within the given range. If there is no factor of the +desired type, an empty list is returned by $*\_factors$ +while the routines $*\_factor$ return the input polynomial. + + +The share variable $nc\_factor\_time$ sets an upper limit +for the time to be spent for a call to the non--commutative +factorizer. If the value is a positive integer, a +factorization is terminated with an error message as soon +as the time limit is reached. The time units are milliseconds. + +\section{Output of expressions} + +It is often desirable to have the commutative parts (coefficients) +in a non--commutative operation condensed by factorization. The operator +\begin{verbatim} + nc_compact() +\end{verbatim} +collects the coefficients to the powers of the lowest possible +non-commutative variable. +\begin{verbatim} +load ncpoly; + +nc_setup({n,NN},{NN*n-n*NN=NN})$ +p1 := n**4 + n**2*nn + 4*n**2 + 4*n*nn + 4*nn + 4; + + 4 2 2 +p1 := n + n *nn + 4*n + 4*n*nn + 4*nn + 4 + +nc_compact p1; + + 2 2 2 +(n + 2) + (n + 2) *nn +\end{verbatim} +\end{document} + Index: r36/doc/NORMFORM.TEX ================================================================== --- r36/doc/NORMFORM.TEX +++ r36/doc/NORMFORM.TEX @@ -1,664 +1,664 @@ -\documentstyle[11pt,reduce]{article} -\title{A \REDUCE{} package for the computation of several matrix -normal forms} -\author{Matt Rebbeck \\ -Konrad-Zuse-Zentrum f\"ur Informationstechnik Berlin} -Heilbronner Strasse 10 \\ -D--10711 Berlin -- Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -E--mail: neun@sc.zib--berlin.de \\[0.05in] -} -\date{February 1994} -\begin{document} -\maketitle -\index{NORMFORM package} - - -\section{Introduction} -When are two given matrices similar? Similar matrices have the same -trace, determinant, \hspace{0in} characteristic polynomial, -\hspace{0in} and eigenvalues, \hspace{0in} but the matrices -\begin{displaymath} -\begin{array}{ccc} {\cal U} = \left( \begin{array}{cc} 0 & 1 \\ 0 & -0 \end{array} \right) & $and$ & {\cal V} = \left( \begin{array}{cc} -0 & 0 \\ 0 & 0 \end{array} \right) \end{array} -\end{displaymath} -are the same in all four of the above but are not similar. Otherwise -there could exist a nonsingular ${\cal N} {\in} M_{2}$ (the set of -all $2 \times 2$ matrices) such that ${\cal U} = {\cal N} \, {\cal V} -\, {\cal N}^{-1} = {\cal N} \, {\it 0} \, {\cal N}^{-1} = {\it 0}$, -which is a contradiction since ${\cal U} \neq {\it 0}$. - -Two matrices can look very different but still be similar. One -approach to determining whether two given matrices are similar is to -compute the normal form of them. If both matrices reduce to the same -normal form they must be similar. - -{\small NORMFORM} is a package for computing the following normal -forms of matrices: - -\begin{itemize} -\begin{verbatim} - - smithex - - smithex_int - - frobenius - - ratjordan - - jordansymbolic - - jordan -\end{verbatim} -\end{itemize} - -The package is loaded by {\tt load\_package normform;} - -By default all calculations are carried out in {\cal Q} (the rational -numbers). For {\tt smithex}, {\tt frobenius}, {\tt ratjordan}, -{\tt jordansymbolic}, and {\tt jordan}, this field can be extended. -Details are given in the respective sections. - -The {\tt frobenius}, {\tt ratjordan}, and {\tt jordansymbolic} normal -forms can also be computed in a modular base. Again, details are given -in the respective sections. - -The algorithms for each routine are contained in the source code. - -{\small NORMFORM} has been converted from the normform and Normform -packages written by T.M.L. Mulders and A.H.M. Levelt. These have been -implemented in Maple [4]. - - -\section{smithex} - -\subsection{function} - -{\tt smithex}(${\cal A},\, x$) computes the Smith normal form ${\cal S}$ -of the matrix ${\cal A}$. - -It returns \{${\cal S}, {\cal P}, {\cal P}^{-1}$\} where ${\cal S}, -{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P S P}^{-1} = -{\cal A}$. - -${\cal A}$ is a rectangular matrix of univariate polynomials in $x$. - -$x$ is the variable name. - -\subsection{field extensions} - -Calculations are performed in ${\cal Q}$. To extend this field the -{\small ARNUM} package can be used. For details see {\it section} 8. - -\subsection{synopsis} - -\begin{itemize} -\item The Smith normal form ${\cal S}$ of an n by m matrix ${\cal A}$ -with univariate polynomial entries in $x$ over a field {\it F} is -computed. That is, the polynomials are then regarded as elements of the -{\it E}uclidean domain {\it F}($x$). - -\item The Smith normal form is a diagonal matrix ${\cal S}$ where: - - \begin{itemize} - \item rank(${\cal A}$) = number of nonzero rows (columns) of - ${\cal S}$. - \item ${\cal S}(i,\, i)$ is a monic polynomial for 0 $< i \leq $ - rank(${\cal A}$). - \item ${\cal S}(i,\, i)$ divides ${\cal S}(i+1,\, i+1)$ for 0 $< i - <$ rank(${\cal A}$). - \item ${\cal S}(i,\,i)$ is the greatest common divisor of all $i$ by - $i$ minors of ${\cal A}$. - \end{itemize} - - Hence, if we have the case that $n = m$, as well as - rank(${\cal A}$) $= n$, then product (${\cal S}(i,\,i), - i=1\ldots n$) = det(${\cal A}$) / lcoeff(det$({\cal A}), \, x$). - -\item The Smith normal form is obtained by doing elementary row and - column operations. This includes interchanging rows (columns), - multiplying through a row (column) by $-1$, and adding integral - multiples of one row (column) to another. - -\item Although the rank and determinant can be easily obtained from - ${\cal S}$, this is not an efficient method for computing these - quantities except that this may yield a partial factorization of - det(${\cal A}$) without doing any explicit factorizations. - -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cc} x & x+1 \\ 0 & 3*x^2 \end{array} -\right) -\end{displaymath} - -\begin{displaymath} -\hspace{-0.5in} -\begin{array}{ccc} -{\tt smithex}({\cal A},\, x) & = & -\left\{ \left( \begin{array}{cc} 1 & 0 \\ -0 & x^3 \end{array} \right), \left( \begin{array}{cc} 1 & 0 \\ 3*x^2 -& 1 \end{array} \right), \left( \begin{array}{cc} x & x+1 \\ -3 & -3 -\end{array} \right) \right\} \end{array} -\end{displaymath} - - -\section{smithex\_int} - -\subsection{function} - -Given an $n$ by $m$ rectangular matrix ${\cal A}$ that contains -{\it only} integer entries, {\tt smithex\_int}(${\cal A}$) computes the -Smith normal form ${\cal S}$ of ${\cal A}$. - -It returns \{${\cal S}, {\cal P}, {\cal P}^{-1}$\} where ${\cal S}, -{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P S P}^{-1} = -{\cal A}$. - - -\subsection{synopsis} - -\begin{itemize} -\item The Smith normal form ${\cal S}$ of an $n$ by $m$ matrix -${\cal A}$ with integer entries is computed. - -\item The Smith normal form is a diagonal matrix ${\cal S}$ where: - - \begin{itemize} - \item rank(${\cal A}$) = number of nonzero rows (columns) of - ${\cal S}$. - \item sign(${\cal S}(i,\, i)$) = 1 for 0 $< i \leq $ rank(${\cal A}$). - \item ${\cal S}(i,\, i)$ divides ${\cal S}(i+1,\, i+1)$ for 0 $< i - <$ rank(${\cal A}$). - \item ${\cal S}(i,\,i)$ is the greatest common divisor of all $i$ by - $i$ minors of ${\cal A}$. - \end{itemize} - - Hence, if we have the case that $n = m$, as well as - rank(${\cal A}$) $= n$, then abs(det(${\cal A}$)) = - product(${\cal S}(i,\,i),i=1\ldots n$). - -\item The Smith normal form is obtained by doing elementary row and - column operations. This includes interchanging rows (columns), - multiplying through a row (column) by $-1$, and adding integral - multiples of one row (column) to another. -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{ccc} 9 & -36 & 30 \\ -36 & 192 & -180 \\ -30 & -180 & 180 \end{array} -\right) -\end{displaymath} - -{\tt smithex\_int}(${\cal A}$) = -\begin{center} -\begin{displaymath} -\left\{ \left( \begin{array}{ccc} 3 & 0 & 0 \\ 0 & 12 & 0 \\ 0 & 0 & 60 -\end{array} \right), \left( \begin{array}{ccc} -17 & -5 & -4 \\ 64 & 19 -& 15 \\ -50 & -15 & -12 \end{array} \right), \left( \begin{array}{ccc} -1 & -24 & 30 \\ -1 & 25 & -30 \\ 0 & -1 & 1 \end{array} \right) \right\} -\end{displaymath} -\end{center} - - -\section{frobenius} - -\subsection{function} - -{\tt frobenius}(${\cal A}$) computes the Frobenius normal form -${\cal F}$ of the matrix ${\cal A}$. - -It returns \{${\cal F}, {\cal P}, {\cal P}^{-1}$\} where ${\cal F}, -{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P F P}^{-1} = -{\cal A}$. - -${\cal A}$ is a square matrix. - -\subsection{field extensions} - -Calculations are performed in ${\cal Q}$. To extend this field the -{\small ARNUM} package can be used. For details see {\it section} 8. - -\subsection{modular arithmetic} - -{\tt frobenius} can be calculated in a modular base. For details see -{\it section} 9. - -\subsection{synopsis} - -\begin{itemize} -\item ${\cal F}$ has the following structure: - \begin{displaymath} - {\cal F} = \left( \begin{array}{cccc} {\cal C}{\it p_{1}} & & & - \\ & {\cal C}{\it p_{2}} & & \\ & & \ddots & \\ & & & - {\cal C}{\it p_{k}} \end{array} \right) - \end{displaymath} - where the ${\cal C}({\it p_{i}})$'s are companion matrices - associated with polynomials ${\it p_{1}, p_{2}},\ldots, - {\it p_{k}}$, with the property that ${\it p_{i}}$ divides - ${\it p_{i+1}}$ for $i =1\ldots k-1$. All unmarked entries are - zero. - -\item The Frobenius normal form defined in this way is unique (ie: if - we require that ${\it p_{i}}$ divides ${\it p_{i+1}}$ as above). -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cc} \frac{-x^2+y^2+y}{y} & -\frac{-x^2+x+y^2-y}{y} \\ \frac{-x^2-x+y^2+y}{y} & \frac{-x^2+x+y^2-y} -{y} \end{array} \right) -\end{displaymath} - -{\tt frobenius}(${\cal A}$) = -\begin{center} -\begin{displaymath} -\left\{ \left( \begin{array}{cc} 0 & \frac{x*(x^2-x-y^2+y)}{y} \\ 1 & -\frac{-2*x^2+x+2*y^2}{y} \end{array} \right), \left( \begin{array}{cc} -1 & \frac{-x^2+y^2+y}{y} \\ 0 & \frac{-x^2-x+y^2+y}{y} \end{array} -\right), \left( \begin{array}{cc} 1 & \frac{-x^2+y^2+y}{x^2+x-y^2-y} \\ -0 & \frac{-y}{x^2+x-y^2-y} \end{array} \right) \right\} -\end{displaymath} -\end{center} - - -\section{ratjordan} - -\subsection{function} - -{\tt ratjordan}(${\cal A}$) computes the rational Jordan normal form -${\cal R}$ of the matrix ${\cal A}$. - -It returns \{${\cal R}, {\cal P}, {\cal P}^{-1}$\} where ${\cal R}, -{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P R P}^{-1} = -{\cal A}$. - -${\cal A}$ is a square matrix. - -\subsection{field extensions} - -Calculations are performed in ${\cal Q}$. To extend this field the -{\small ARNUM} package can be used. For details see {\it section} 8. - -\subsection{modular arithmetic} - -{\tt ratjordan} can be calculated in a modular base. For details see -{\it section} 9. - -\subsection{synopsis} - -\begin{itemize} -\item ${\cal R}$ has the following structure: - \begin{displaymath} - {\cal R} = \left( \begin{array}{cccccc} {\it r_{11}} \\ & - {\it r_{12}} \\ & & \ddots \\ & & & {\it r_{21}} \\ & & - & & {\it r_{22}} \\ & & & & & \ddots \end{array} \right) - \end{displaymath} - - The ${\it r_{ij}}$'s have the following shape: - \begin{displaymath} - {\it r_{ij}} = \left( \begin{array}{ccccc} {\cal C}({\it p}) & - {\cal I} & & & \\ & {\cal C}({\it p}) & {\cal I} & & \\ & - & \ddots & \ddots & \\ & & & {\cal C}({\it p}) & {\cal I} \\ & - & & & {\cal C}({\it p}) \end{array} \right) - \end{displaymath} - - where there are e${\it ij}$ times ${\cal C}({\it p})$ blocks - along the diagonal and ${\cal C}({\it p})$ is the companion - matrix associated with the irreducible polynomial ${\it p}$. All - unmarked entries are zero. -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cc} x+y & 5 \\ y & x^2 \end{array} -\right) -\end{displaymath} - -{\tt ratjordan}(${\cal A}$) = -\begin{center} -\begin{displaymath} -\left\{ \left( \begin{array}{cc} 0 & -x^3-x^2*y+5*y \\ 1 & -x^2+x+y \end{array} \right), \left( \begin{array}{cc} -1 & x+y \\ 0 & y \end{array} \right), \left( \begin{array}{cc} 1 & -\frac{-(x+y)}{y} \\ 0 & \hspace{0.2in} \frac{1}{y} \end{array} \right) -\right\} -\end{displaymath} -\end{center} - - -\section{jordansymbolic} - -\subsection{function} - -{\tt jordansymbolic}(${\cal A}$) \hspace{0in} computes the Jordan -normal form ${\cal J}$of the matrix ${\cal A}$. - -It returns \{${\cal J}, {\cal L}, {\cal P}, {\cal P}^{-1}$\}, where -${\cal J}, {\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P J P}^ -{-1} = {\cal A}$. ${\cal L}$ = \{ {\it ll} , $\xi$ \}, where $\xi$ is -a name and {\it ll} is a list of irreducible factors of ${\it p}(\xi)$. - -${\cal A}$ is a square matrix. - -\subsection{field extensions} - -Calculations are performed in ${\cal Q}$. To extend this field the -{\small ARNUM} package can be used. For details see {\it section} 8. - -\subsection{modular arithmetic} - -{\tt jordansymbolic} can be calculated in a modular base. For details -see {\it section} 9. - -\subsection{extras} - -If using {\tt xr}, the X interface for \REDUCE, the appearance of the -output can be improved by switching {\tt on looking\_good;}. This -converts all lambda to $\xi$ and improves the indexing, eg: lambda12 -$\Rightarrow \xi_{12}$. The example ({\it section} 6.6) shows the -output when this switch is on. - -\subsection{synopsis} - -\begin{itemize} -\item A {\it Jordan block} ${\jmath}_{k}(\lambda)$ is a $k$ by $k$ - upper triangular matrix of the form: - - \begin{displaymath} - {\jmath}_{k}(\lambda) = \left( \begin{array}{ccccc} \lambda & 1 - & & & \\ & \lambda & 1 & & \\ & - & \ddots & \ddots & \\ & & & \lambda & 1 \\ & - & & & \lambda \end{array} \right) - \end{displaymath} - - There are $k-1$ terms ``$+1$'' in the superdiagonal; the scalar - $\lambda$ appears $k$ times on the main diagonal. All other - matrix entries are zero, and ${\jmath}_{1}(\lambda) = (\lambda)$. - -\item A Jordan matrix ${\cal J} \in M_{n}$ (the set of all $n$ by $n$ - matrices) is a direct sum of {\it jordan blocks}. - - \begin{displaymath} - {\cal J} = \left( \begin{array}{cccc} \jmath_{n_1}(\lambda_{1}) - \\ & \jmath_{n_2}(\lambda_{2}) \\ & & \ddots \\ & & & - \jmath_{n_k}(\lambda_{k}) \end{array} \right), - {\it n}_{1}+{\it n}_{2}+\cdots +{\it n}_{k} = n - \end{displaymath} - - in which the orders ${\it n}_{i}$ may not be distinct and the - values ${\lambda_{i}}$ need not be distinct. - -\item Here ${\lambda}$ is a zero of the characteristic polynomial - ${\it p}$ of ${\cal A}$. If ${\it p}$ does not split completely, - symbolic names are chosen for the missing zeroes of ${\it p}$. - If, by some means, one knows such missing zeroes, they can be - substituted for the symbolic names. For this, - {\tt jordansymbolic} actually returns $\{ {\cal J,L,P,P}^{-1} \}$. - ${\cal J}$ is the Jordan normal form of ${\cal A}$ (using - symbolic names if necessary). ${\cal L} = \{ {\it ll}, \xi \}$, - where $\xi$ is a name and ${\it ll}$ is a list of irreducible - factors of ${\it p}(\xi)$. If symbolic names are used then - ${\xi}_{ij}$ is a zero of ${\it ll}_{i}$. ${\cal P}$ and - ${\cal P}^{-1}$ are as above. -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;}\\ -{\tt on looking\_good;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cc} 1 & y \\ y^2 & 3 \end{array} -\right) -\end{displaymath} - -{\tt jordansymbolic}(${\cal A}$) = -\begin{eqnarray} - & & \left\{ \left( \begin{array}{cc} \xi_{11} & 0 \\ 0 & \xi_{12} -\end{array} \right) , -\left\{ \left\{ -y^3+\xi^2-4*\xi+3 \right\}, \xi \right\}, \right. -\nonumber \\ & & \hspace{0.1in} \left. \left( \begin{array}{cc} -\xi_{11} -3 & \xi_{12} -3 \\ y^2 & y^2 -\end{array} \right), \left( \begin{array}{cc} \frac{\xi_{11} -2} -{2*(y^3-1)} & \frac{\xi_{11} + y^3 -1}{2*y^2*(y^3+1)} \\ -\frac{\xi_{12} -2}{2*(y^3-1)} & \frac{\xi_{12}+y^3-1}{2*y^2*(y^3+1)} -\end{array} \right) \right\} \nonumber -\end{eqnarray} - -\vspace{0.2in} -\begin{flushleft} -\begin{math} -{\tt solve(-y^3+xi^2-4*xi+3,xi)}${\tt ;}$ -\end{math} -\end{flushleft} - -\vspace{0.1in} -\begin{center} -\begin{math} -\{ \xi = \sqrt{y^3+1} + 2,\, \xi = -\sqrt{y^3+1}+2 \} -\end{math} -\end{center} - -\vspace{0.1in} -\begin{math} -{\tt {\cal J} = sub}{\tt (}{\tt \{ xi(1,1)=sqrt(y^3+1)+2,\, xi(1,2) = --sqrt(y^3+1)+2\},} -\end{math} -\\ \hspace*{0.29in} {\tt first jordansymbolic (${\cal A}$));} - -\vspace{0.2in} -\begin{displaymath} -{\cal J} = \left( \begin{array}{cc} \sqrt{y^3+1} + 2 & 0 \\ 0 & --\sqrt{y^3+1} + 2 \end{array} \right) -\end{displaymath} - -\vspace{0.2in} -For a similar example ot this in standard {\REDUCE} (ie: not using -{\tt xr}), see the {\it normform.log} file. - -\vspace{0.5in} - -\section{jordan} - -\subsection{function} - -{\tt jordan}(${\cal A}$) computes the Jordan normal form -${\cal J}$ of the matrix ${\cal A}$. - -It returns \{${\cal J}, {\cal P}, {\cal P}^{-1}$\}, where -${\cal J}, {\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P J P}^ -{-1} = {\cal A}$. - -${\cal A}$ is a square matrix. - -\subsection{field extensions} - -Calculations are performed in ${\cal Q}$. To extend this field the -{\small ARNUM} package can be used. For details see {\it section} 8. - -\subsection{note} -In certain polynomial cases {\tt fullroots} is turned on to compute the -zeroes. This can lead to the calculation taking a long time, as well as -the output being very large. In this case a message {\tt ***** WARNING: -fullroots turned on. May take a while.} will be printed. It may be -better to kill the calculation and compute {\tt jordansymbolic} instead. - -\subsection{synopsis} - -\begin{itemize} -\item The Jordan normal form ${\cal J}$ with entries in an algebraic - extension of ${\cal Q}$ is computed. - -\item A {\it Jordan block} ${\jmath}_{k}(\lambda)$ is a $k$ by $k$ - upper triangular matrix of the form: - - \begin{displaymath} - {\jmath}_{k}(\lambda) = \left( \begin{array}{ccccc} \lambda & 1 - & & & \\ & \lambda & 1 & & \\ & - & \ddots & \ddots & \\ & & & \lambda & 1 \\ & - & & & \lambda \end{array} \right) - \end{displaymath} - - There are $k-1$ terms ``$+1$'' in the superdiagonal; the scalar - $\lambda$ appears $k$ times on the main diagonal. All other - matrix entries are zero, and ${\jmath}_{1}(\lambda) = (\lambda)$. - -\item A Jordan matrix ${\cal J} \in M_{n}$ (the set of all $n$ by $n$ - matrices) is a direct sum of {\it jordan blocks}. - - \begin{displaymath} - {\cal J} = \left( \begin{array}{cccc} \jmath_{n_1}(\lambda_{1}) - \\ & \jmath_{n_2}(\lambda_{2}) \\ & & \ddots \\ & & & - \jmath_{n_k}(\lambda_{k}) \end{array} \right), - {\it n}_{1}+{\it n}_{2}+\cdots +{\it n}_{k} = n - \end{displaymath} - - in which the orders ${\it n}_{i}$ may not be distinct and the - values ${\lambda_{i}}$ need not be distinct. - -\item Here ${\lambda}$ is a zero of the characteristic polynomial - ${\it p}$ of ${\cal A}$. The zeroes of the characteristic - polynomial are computed exactly, if possible. Otherwise they are - approximated by floating point numbers. -\end{itemize} - -\subsection{example} - -{\tt load\_package normform;} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cccccc} -9 & -21 & -15 & 4 & 2 & 0 \\ --10 & 21 & -14 & 4 & 2 & 0 \\ -8 & 16 & -11 & 4 & 2 & 0 \\ -6 & 12 & -9 -& 3 & 3 & 0 \\ -4 & 8 & -6 & 0 & 5 & 0 \\ -2 & 4 & -3 & 0 & 1 & 3 -\end{array} \right) -\end{displaymath} - -\begin{flushleft} -{\tt ${\cal J}$ = first jordan$({\cal A})$;} -\end{flushleft} - -\begin{displaymath} -{\cal J} = \left( \begin{array}{cccccc} 3 & 0 & 0 & 0 & 0 & 0 \\ 0 & 3 -& 0 & 0 & 0 & 0 \\ 0 & 0 & 1 & 1 & 0 & 0 \\ 0 & 0 & 0 & 1 & 0 & 0 \\ - 0 & 0 & 0 & 0 & i+2 & 0 \\ 0 & 0 & 0 & 0 & 0 & -i+2 -\end{array} \right) -\end{displaymath} - -\newpage - - -\section{arnum} - -The package is loaded by {\tt load\_package arnum;}. The algebraic -field ${\cal Q}$ can now be extended. For example, {\tt defpoly -sqrt2**2-2;} will extend it to include ${\sqrt{2}}$ (defined here by -{\tt sqrt2}). The {\small ARNUM} package was written by Eberhard -Schr\"ufer and is described in the {\it arnum.tex} file. - -\subsection{example} - -{\tt load\_package normform;} \\ -{\tt load\_package arnum;} \\ -{\tt defpoly sqrt2**2-2;} \\ -(sqrt2 now changed to ${\sqrt{2}}$ for looks!) -\vspace{0.2in} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{ccc} 4*{\sqrt{2}}-6 & -4*{\sqrt{2}}+7 & --3*{\sqrt{2}}+6 \\ 3*{\sqrt{2}}-6 & -3*{\sqrt{2}}+7 & -3*{\sqrt{2}}+6 -\\ 3*{\sqrt{2}} & 1-3*{\sqrt{2}} & -2*{\sqrt{2}} \end{array} \right) -\end{displaymath} -\vspace{0.2in} - -\begin{eqnarray} -{\tt ratjordan}({\cal A}) & = & -\left\{ \left( \begin{array}{ccc} {\sqrt{2}} & 0 & 0 \\ 0 & {\sqrt{2}} -& 0 \\ 0 & 0 & -3*{\sqrt{2}}+1 \end{array} \right), \right. \nonumber -\\ & & \hspace{0.1in} \left. \left( \begin{array}{ccc} 7*{\sqrt{2}}-6 -& \frac{2*{\sqrt{2}}-49}{31} & \frac{-21*{\sqrt{2}}+18}{31} \\ -3*{\sqrt{2}}-6 & \frac{21*{\sqrt{2}}-18}{31} & \frac{-21*{\sqrt{2}}+18} -{31} \\ 3*{\sqrt{2}}+1 & \frac{-3*{\sqrt{2}}+24}{31} & -\frac{3*{\sqrt{2}}-24}{31} \end{array} \right), \right. \nonumber \\ & -& \hspace{0.1in} \left. \left( \begin{array}{ccc} 0 & {\sqrt{2}}+1 & -1 \\ -1 & 4*{\sqrt{2}}+9 & 4*{\sqrt{2}} \\ -1 & -\frac{1}{6}*{\sqrt{2}} -+1 & 1 \end{array} \right) \right\} \nonumber -\end{eqnarray} - -\newpage - - -\section{modular} - -Calculations can be performed in a modular base by switching {\tt on -modular;}. The base can then be set by {\tt setmod p;} (p a prime). The -normal form will then have entries in ${\cal Z}/$p${\cal Z}$. - -By also switching {\tt on balanced\_mod;} the output will be shown using -a symmetric modular representation. - -Information on this modular manipulation can be found in {\it chapter} -9 (Polynomials and Rationals) of the {\REDUCE} User's Manual [5]. - -\subsection{example} - -{\tt load\_package normform;} \\ -{\tt on modular;} \\ -{\tt setmod 23;} -\vspace{0.1in} - -\begin{displaymath} -{\cal A} = \left( \begin{array}{cc} 10 & 18 \\ 17 & 20 \end{array} -\right) -\end{displaymath} - -{\tt jordansymbolic}(${\cal A}$) = -\begin{center} -\begin{displaymath} -\left\{ \left( \begin{array}{cc} 18 & 0 \\ 0 & 12 \end{array} \right), -\left\{ \left\{ \lambda + 5, \lambda + 11 \right\}, \lambda \right\}, -\left( \begin{array}{cc} 15 & 9 \\ 22 & 1 \end{array} \right), \left( -\begin{array}{cc} 1 & 14 \\ 1 & 15 \end{array} \right) \right\} -\end{displaymath} -\end{center} -\vspace{0.2in} - -{\tt on balanced\_mod;} -\vspace{0.2in} - -{\tt jordansymbolic}(${\cal A}$) = -\begin{center} -\begin{displaymath} -\left\{ \left( \begin{array}{cc} -5 & 0 \\ 0 & -11 \end{array} \right), -\left\{ \left\{ \lambda + 5, \lambda + 11 \right\}, \lambda \right\}, -\left( \begin{array}{cc} -8 & 9 \\ -1 & 1 \end{array} \right), \left( -\begin{array}{cc} 1 & -9 \\ 1 & -8 \end{array} \right) \right\} -\end{displaymath} -\end{center} - -\newpage -\begin{thebibliography}{6} -\bibitem{MulLev} T.M.L.Mulders and A.H.M. Levelt: {\it The Maple - normform and Normform packages.} (1993) -\bibitem{Mulders} T.M.L.Mulders: {\it Algoritmen in De Algebra, A - Seminar on Algebraic Algorithms, Nigmegen.} (1993) -\bibitem{HoJo} Roger A. Horn and Charles A. Johnson: {\it Matrix - Analysis.} Cambridge University Press (1990) -\bibitem{Maple} Bruce W. Chat\ldots [et al.]: {\it Maple (Computer - Program)}. Springer-Verlag (1991) -\bibitem{Reduce} Anthony C. Hearn: {\REDUCE} {\it User's Manual 3.6.} - RAND (1995) -\end{thebibliography} - -\end{document} - +\documentstyle[11pt,reduce]{article} +\title{A \REDUCE{} package for the computation of several matrix +normal forms} +\author{Matt Rebbeck \\ +Konrad-Zuse-Zentrum f\"ur Informationstechnik Berlin} +Heilbronner Strasse 10 \\ +D--10711 Berlin -- Wilmersdorf \\ +Federal Republic of Germany \\[0.05in] +E--mail: neun@sc.zib--berlin.de \\[0.05in] +} +\date{February 1994} +\begin{document} +\maketitle +\index{NORMFORM package} + + +\section{Introduction} +When are two given matrices similar? Similar matrices have the same +trace, determinant, \hspace{0in} characteristic polynomial, +\hspace{0in} and eigenvalues, \hspace{0in} but the matrices +\begin{displaymath} +\begin{array}{ccc} {\cal U} = \left( \begin{array}{cc} 0 & 1 \\ 0 & +0 \end{array} \right) & $and$ & {\cal V} = \left( \begin{array}{cc} +0 & 0 \\ 0 & 0 \end{array} \right) \end{array} +\end{displaymath} +are the same in all four of the above but are not similar. Otherwise +there could exist a nonsingular ${\cal N} {\in} M_{2}$ (the set of +all $2 \times 2$ matrices) such that ${\cal U} = {\cal N} \, {\cal V} +\, {\cal N}^{-1} = {\cal N} \, {\it 0} \, {\cal N}^{-1} = {\it 0}$, +which is a contradiction since ${\cal U} \neq {\it 0}$. + +Two matrices can look very different but still be similar. One +approach to determining whether two given matrices are similar is to +compute the normal form of them. If both matrices reduce to the same +normal form they must be similar. + +{\small NORMFORM} is a package for computing the following normal +forms of matrices: + +\begin{itemize} +\begin{verbatim} + - smithex + - smithex_int + - frobenius + - ratjordan + - jordansymbolic + - jordan +\end{verbatim} +\end{itemize} + +The package is loaded by {\tt load\_package normform;} + +By default all calculations are carried out in {\cal Q} (the rational +numbers). For {\tt smithex}, {\tt frobenius}, {\tt ratjordan}, +{\tt jordansymbolic}, and {\tt jordan}, this field can be extended. +Details are given in the respective sections. + +The {\tt frobenius}, {\tt ratjordan}, and {\tt jordansymbolic} normal +forms can also be computed in a modular base. Again, details are given +in the respective sections. + +The algorithms for each routine are contained in the source code. + +{\small NORMFORM} has been converted from the normform and Normform +packages written by T.M.L. Mulders and A.H.M. Levelt. These have been +implemented in Maple [4]. + + +\section{smithex} + +\subsection{function} + +{\tt smithex}(${\cal A},\, x$) computes the Smith normal form ${\cal S}$ +of the matrix ${\cal A}$. + +It returns \{${\cal S}, {\cal P}, {\cal P}^{-1}$\} where ${\cal S}, +{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P S P}^{-1} = +{\cal A}$. + +${\cal A}$ is a rectangular matrix of univariate polynomials in $x$. + +$x$ is the variable name. + +\subsection{field extensions} + +Calculations are performed in ${\cal Q}$. To extend this field the +{\small ARNUM} package can be used. For details see {\it section} 8. + +\subsection{synopsis} + +\begin{itemize} +\item The Smith normal form ${\cal S}$ of an n by m matrix ${\cal A}$ +with univariate polynomial entries in $x$ over a field {\it F} is +computed. That is, the polynomials are then regarded as elements of the +{\it E}uclidean domain {\it F}($x$). + +\item The Smith normal form is a diagonal matrix ${\cal S}$ where: + + \begin{itemize} + \item rank(${\cal A}$) = number of nonzero rows (columns) of + ${\cal S}$. + \item ${\cal S}(i,\, i)$ is a monic polynomial for 0 $< i \leq $ + rank(${\cal A}$). + \item ${\cal S}(i,\, i)$ divides ${\cal S}(i+1,\, i+1)$ for 0 $< i + <$ rank(${\cal A}$). + \item ${\cal S}(i,\,i)$ is the greatest common divisor of all $i$ by + $i$ minors of ${\cal A}$. + \end{itemize} + + Hence, if we have the case that $n = m$, as well as + rank(${\cal A}$) $= n$, then product (${\cal S}(i,\,i), + i=1\ldots n$) = det(${\cal A}$) / lcoeff(det$({\cal A}), \, x$). + +\item The Smith normal form is obtained by doing elementary row and + column operations. This includes interchanging rows (columns), + multiplying through a row (column) by $-1$, and adding integral + multiples of one row (column) to another. + +\item Although the rank and determinant can be easily obtained from + ${\cal S}$, this is not an efficient method for computing these + quantities except that this may yield a partial factorization of + det(${\cal A}$) without doing any explicit factorizations. + +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cc} x & x+1 \\ 0 & 3*x^2 \end{array} +\right) +\end{displaymath} + +\begin{displaymath} +\hspace{-0.5in} +\begin{array}{ccc} +{\tt smithex}({\cal A},\, x) & = & +\left\{ \left( \begin{array}{cc} 1 & 0 \\ +0 & x^3 \end{array} \right), \left( \begin{array}{cc} 1 & 0 \\ 3*x^2 +& 1 \end{array} \right), \left( \begin{array}{cc} x & x+1 \\ -3 & -3 +\end{array} \right) \right\} \end{array} +\end{displaymath} + + +\section{smithex\_int} + +\subsection{function} + +Given an $n$ by $m$ rectangular matrix ${\cal A}$ that contains +{\it only} integer entries, {\tt smithex\_int}(${\cal A}$) computes the +Smith normal form ${\cal S}$ of ${\cal A}$. + +It returns \{${\cal S}, {\cal P}, {\cal P}^{-1}$\} where ${\cal S}, +{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P S P}^{-1} = +{\cal A}$. + + +\subsection{synopsis} + +\begin{itemize} +\item The Smith normal form ${\cal S}$ of an $n$ by $m$ matrix +${\cal A}$ with integer entries is computed. + +\item The Smith normal form is a diagonal matrix ${\cal S}$ where: + + \begin{itemize} + \item rank(${\cal A}$) = number of nonzero rows (columns) of + ${\cal S}$. + \item sign(${\cal S}(i,\, i)$) = 1 for 0 $< i \leq $ rank(${\cal A}$). + \item ${\cal S}(i,\, i)$ divides ${\cal S}(i+1,\, i+1)$ for 0 $< i + <$ rank(${\cal A}$). + \item ${\cal S}(i,\,i)$ is the greatest common divisor of all $i$ by + $i$ minors of ${\cal A}$. + \end{itemize} + + Hence, if we have the case that $n = m$, as well as + rank(${\cal A}$) $= n$, then abs(det(${\cal A}$)) = + product(${\cal S}(i,\,i),i=1\ldots n$). + +\item The Smith normal form is obtained by doing elementary row and + column operations. This includes interchanging rows (columns), + multiplying through a row (column) by $-1$, and adding integral + multiples of one row (column) to another. +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{ccc} 9 & -36 & 30 \\ -36 & 192 & -180 \\ +30 & -180 & 180 \end{array} +\right) +\end{displaymath} + +{\tt smithex\_int}(${\cal A}$) = +\begin{center} +\begin{displaymath} +\left\{ \left( \begin{array}{ccc} 3 & 0 & 0 \\ 0 & 12 & 0 \\ 0 & 0 & 60 +\end{array} \right), \left( \begin{array}{ccc} -17 & -5 & -4 \\ 64 & 19 +& 15 \\ -50 & -15 & -12 \end{array} \right), \left( \begin{array}{ccc} +1 & -24 & 30 \\ -1 & 25 & -30 \\ 0 & -1 & 1 \end{array} \right) \right\} +\end{displaymath} +\end{center} + + +\section{frobenius} + +\subsection{function} + +{\tt frobenius}(${\cal A}$) computes the Frobenius normal form +${\cal F}$ of the matrix ${\cal A}$. + +It returns \{${\cal F}, {\cal P}, {\cal P}^{-1}$\} where ${\cal F}, +{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P F P}^{-1} = +{\cal A}$. + +${\cal A}$ is a square matrix. + +\subsection{field extensions} + +Calculations are performed in ${\cal Q}$. To extend this field the +{\small ARNUM} package can be used. For details see {\it section} 8. + +\subsection{modular arithmetic} + +{\tt frobenius} can be calculated in a modular base. For details see +{\it section} 9. + +\subsection{synopsis} + +\begin{itemize} +\item ${\cal F}$ has the following structure: + \begin{displaymath} + {\cal F} = \left( \begin{array}{cccc} {\cal C}{\it p_{1}} & & & + \\ & {\cal C}{\it p_{2}} & & \\ & & \ddots & \\ & & & + {\cal C}{\it p_{k}} \end{array} \right) + \end{displaymath} + where the ${\cal C}({\it p_{i}})$'s are companion matrices + associated with polynomials ${\it p_{1}, p_{2}},\ldots, + {\it p_{k}}$, with the property that ${\it p_{i}}$ divides + ${\it p_{i+1}}$ for $i =1\ldots k-1$. All unmarked entries are + zero. + +\item The Frobenius normal form defined in this way is unique (ie: if + we require that ${\it p_{i}}$ divides ${\it p_{i+1}}$ as above). +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cc} \frac{-x^2+y^2+y}{y} & +\frac{-x^2+x+y^2-y}{y} \\ \frac{-x^2-x+y^2+y}{y} & \frac{-x^2+x+y^2-y} +{y} \end{array} \right) +\end{displaymath} + +{\tt frobenius}(${\cal A}$) = +\begin{center} +\begin{displaymath} +\left\{ \left( \begin{array}{cc} 0 & \frac{x*(x^2-x-y^2+y)}{y} \\ 1 & +\frac{-2*x^2+x+2*y^2}{y} \end{array} \right), \left( \begin{array}{cc} +1 & \frac{-x^2+y^2+y}{y} \\ 0 & \frac{-x^2-x+y^2+y}{y} \end{array} +\right), \left( \begin{array}{cc} 1 & \frac{-x^2+y^2+y}{x^2+x-y^2-y} \\ +0 & \frac{-y}{x^2+x-y^2-y} \end{array} \right) \right\} +\end{displaymath} +\end{center} + + +\section{ratjordan} + +\subsection{function} + +{\tt ratjordan}(${\cal A}$) computes the rational Jordan normal form +${\cal R}$ of the matrix ${\cal A}$. + +It returns \{${\cal R}, {\cal P}, {\cal P}^{-1}$\} where ${\cal R}, +{\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P R P}^{-1} = +{\cal A}$. + +${\cal A}$ is a square matrix. + +\subsection{field extensions} + +Calculations are performed in ${\cal Q}$. To extend this field the +{\small ARNUM} package can be used. For details see {\it section} 8. + +\subsection{modular arithmetic} + +{\tt ratjordan} can be calculated in a modular base. For details see +{\it section} 9. + +\subsection{synopsis} + +\begin{itemize} +\item ${\cal R}$ has the following structure: + \begin{displaymath} + {\cal R} = \left( \begin{array}{cccccc} {\it r_{11}} \\ & + {\it r_{12}} \\ & & \ddots \\ & & & {\it r_{21}} \\ & & + & & {\it r_{22}} \\ & & & & & \ddots \end{array} \right) + \end{displaymath} + + The ${\it r_{ij}}$'s have the following shape: + \begin{displaymath} + {\it r_{ij}} = \left( \begin{array}{ccccc} {\cal C}({\it p}) & + {\cal I} & & & \\ & {\cal C}({\it p}) & {\cal I} & & \\ & + & \ddots & \ddots & \\ & & & {\cal C}({\it p}) & {\cal I} \\ & + & & & {\cal C}({\it p}) \end{array} \right) + \end{displaymath} + + where there are e${\it ij}$ times ${\cal C}({\it p})$ blocks + along the diagonal and ${\cal C}({\it p})$ is the companion + matrix associated with the irreducible polynomial ${\it p}$. All + unmarked entries are zero. +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cc} x+y & 5 \\ y & x^2 \end{array} +\right) +\end{displaymath} + +{\tt ratjordan}(${\cal A}$) = +\begin{center} +\begin{displaymath} +\left\{ \left( \begin{array}{cc} 0 & -x^3-x^2*y+5*y \\ 1 & +x^2+x+y \end{array} \right), \left( \begin{array}{cc} +1 & x+y \\ 0 & y \end{array} \right), \left( \begin{array}{cc} 1 & +\frac{-(x+y)}{y} \\ 0 & \hspace{0.2in} \frac{1}{y} \end{array} \right) +\right\} +\end{displaymath} +\end{center} + + +\section{jordansymbolic} + +\subsection{function} + +{\tt jordansymbolic}(${\cal A}$) \hspace{0in} computes the Jordan +normal form ${\cal J}$of the matrix ${\cal A}$. + +It returns \{${\cal J}, {\cal L}, {\cal P}, {\cal P}^{-1}$\}, where +${\cal J}, {\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P J P}^ +{-1} = {\cal A}$. ${\cal L}$ = \{ {\it ll} , $\xi$ \}, where $\xi$ is +a name and {\it ll} is a list of irreducible factors of ${\it p}(\xi)$. + +${\cal A}$ is a square matrix. + +\subsection{field extensions} + +Calculations are performed in ${\cal Q}$. To extend this field the +{\small ARNUM} package can be used. For details see {\it section} 8. + +\subsection{modular arithmetic} + +{\tt jordansymbolic} can be calculated in a modular base. For details +see {\it section} 9. + +\subsection{extras} + +If using {\tt xr}, the X interface for \REDUCE, the appearance of the +output can be improved by switching {\tt on looking\_good;}. This +converts all lambda to $\xi$ and improves the indexing, eg: lambda12 +$\Rightarrow \xi_{12}$. The example ({\it section} 6.6) shows the +output when this switch is on. + +\subsection{synopsis} + +\begin{itemize} +\item A {\it Jordan block} ${\jmath}_{k}(\lambda)$ is a $k$ by $k$ + upper triangular matrix of the form: + + \begin{displaymath} + {\jmath}_{k}(\lambda) = \left( \begin{array}{ccccc} \lambda & 1 + & & & \\ & \lambda & 1 & & \\ & + & \ddots & \ddots & \\ & & & \lambda & 1 \\ & + & & & \lambda \end{array} \right) + \end{displaymath} + + There are $k-1$ terms ``$+1$'' in the superdiagonal; the scalar + $\lambda$ appears $k$ times on the main diagonal. All other + matrix entries are zero, and ${\jmath}_{1}(\lambda) = (\lambda)$. + +\item A Jordan matrix ${\cal J} \in M_{n}$ (the set of all $n$ by $n$ + matrices) is a direct sum of {\it jordan blocks}. + + \begin{displaymath} + {\cal J} = \left( \begin{array}{cccc} \jmath_{n_1}(\lambda_{1}) + \\ & \jmath_{n_2}(\lambda_{2}) \\ & & \ddots \\ & & & + \jmath_{n_k}(\lambda_{k}) \end{array} \right), + {\it n}_{1}+{\it n}_{2}+\cdots +{\it n}_{k} = n + \end{displaymath} + + in which the orders ${\it n}_{i}$ may not be distinct and the + values ${\lambda_{i}}$ need not be distinct. + +\item Here ${\lambda}$ is a zero of the characteristic polynomial + ${\it p}$ of ${\cal A}$. If ${\it p}$ does not split completely, + symbolic names are chosen for the missing zeroes of ${\it p}$. + If, by some means, one knows such missing zeroes, they can be + substituted for the symbolic names. For this, + {\tt jordansymbolic} actually returns $\{ {\cal J,L,P,P}^{-1} \}$. + ${\cal J}$ is the Jordan normal form of ${\cal A}$ (using + symbolic names if necessary). ${\cal L} = \{ {\it ll}, \xi \}$, + where $\xi$ is a name and ${\it ll}$ is a list of irreducible + factors of ${\it p}(\xi)$. If symbolic names are used then + ${\xi}_{ij}$ is a zero of ${\it ll}_{i}$. ${\cal P}$ and + ${\cal P}^{-1}$ are as above. +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;}\\ +{\tt on looking\_good;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cc} 1 & y \\ y^2 & 3 \end{array} +\right) +\end{displaymath} + +{\tt jordansymbolic}(${\cal A}$) = +\begin{eqnarray} + & & \left\{ \left( \begin{array}{cc} \xi_{11} & 0 \\ 0 & \xi_{12} +\end{array} \right) , +\left\{ \left\{ -y^3+\xi^2-4*\xi+3 \right\}, \xi \right\}, \right. +\nonumber \\ & & \hspace{0.1in} \left. \left( \begin{array}{cc} +\xi_{11} -3 & \xi_{12} -3 \\ y^2 & y^2 +\end{array} \right), \left( \begin{array}{cc} \frac{\xi_{11} -2} +{2*(y^3-1)} & \frac{\xi_{11} + y^3 -1}{2*y^2*(y^3+1)} \\ +\frac{\xi_{12} -2}{2*(y^3-1)} & \frac{\xi_{12}+y^3-1}{2*y^2*(y^3+1)} +\end{array} \right) \right\} \nonumber +\end{eqnarray} + +\vspace{0.2in} +\begin{flushleft} +\begin{math} +{\tt solve(-y^3+xi^2-4*xi+3,xi)}${\tt ;}$ +\end{math} +\end{flushleft} + +\vspace{0.1in} +\begin{center} +\begin{math} +\{ \xi = \sqrt{y^3+1} + 2,\, \xi = -\sqrt{y^3+1}+2 \} +\end{math} +\end{center} + +\vspace{0.1in} +\begin{math} +{\tt {\cal J} = sub}{\tt (}{\tt \{ xi(1,1)=sqrt(y^3+1)+2,\, xi(1,2) = +-sqrt(y^3+1)+2\},} +\end{math} +\\ \hspace*{0.29in} {\tt first jordansymbolic (${\cal A}$));} + +\vspace{0.2in} +\begin{displaymath} +{\cal J} = \left( \begin{array}{cc} \sqrt{y^3+1} + 2 & 0 \\ 0 & +-\sqrt{y^3+1} + 2 \end{array} \right) +\end{displaymath} + +\vspace{0.2in} +For a similar example ot this in standard {\REDUCE} (ie: not using +{\tt xr}), see the {\it normform.log} file. + +\vspace{0.5in} + +\section{jordan} + +\subsection{function} + +{\tt jordan}(${\cal A}$) computes the Jordan normal form +${\cal J}$ of the matrix ${\cal A}$. + +It returns \{${\cal J}, {\cal P}, {\cal P}^{-1}$\}, where +${\cal J}, {\cal P}$, and ${\cal P}^{-1}$ are such that ${\cal P J P}^ +{-1} = {\cal A}$. + +${\cal A}$ is a square matrix. + +\subsection{field extensions} + +Calculations are performed in ${\cal Q}$. To extend this field the +{\small ARNUM} package can be used. For details see {\it section} 8. + +\subsection{note} +In certain polynomial cases {\tt fullroots} is turned on to compute the +zeroes. This can lead to the calculation taking a long time, as well as +the output being very large. In this case a message {\tt ***** WARNING: +fullroots turned on. May take a while.} will be printed. It may be +better to kill the calculation and compute {\tt jordansymbolic} instead. + +\subsection{synopsis} + +\begin{itemize} +\item The Jordan normal form ${\cal J}$ with entries in an algebraic + extension of ${\cal Q}$ is computed. + +\item A {\it Jordan block} ${\jmath}_{k}(\lambda)$ is a $k$ by $k$ + upper triangular matrix of the form: + + \begin{displaymath} + {\jmath}_{k}(\lambda) = \left( \begin{array}{ccccc} \lambda & 1 + & & & \\ & \lambda & 1 & & \\ & + & \ddots & \ddots & \\ & & & \lambda & 1 \\ & + & & & \lambda \end{array} \right) + \end{displaymath} + + There are $k-1$ terms ``$+1$'' in the superdiagonal; the scalar + $\lambda$ appears $k$ times on the main diagonal. All other + matrix entries are zero, and ${\jmath}_{1}(\lambda) = (\lambda)$. + +\item A Jordan matrix ${\cal J} \in M_{n}$ (the set of all $n$ by $n$ + matrices) is a direct sum of {\it jordan blocks}. + + \begin{displaymath} + {\cal J} = \left( \begin{array}{cccc} \jmath_{n_1}(\lambda_{1}) + \\ & \jmath_{n_2}(\lambda_{2}) \\ & & \ddots \\ & & & + \jmath_{n_k}(\lambda_{k}) \end{array} \right), + {\it n}_{1}+{\it n}_{2}+\cdots +{\it n}_{k} = n + \end{displaymath} + + in which the orders ${\it n}_{i}$ may not be distinct and the + values ${\lambda_{i}}$ need not be distinct. + +\item Here ${\lambda}$ is a zero of the characteristic polynomial + ${\it p}$ of ${\cal A}$. The zeroes of the characteristic + polynomial are computed exactly, if possible. Otherwise they are + approximated by floating point numbers. +\end{itemize} + +\subsection{example} + +{\tt load\_package normform;} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cccccc} -9 & -21 & -15 & 4 & 2 & 0 \\ +-10 & 21 & -14 & 4 & 2 & 0 \\ -8 & 16 & -11 & 4 & 2 & 0 \\ -6 & 12 & -9 +& 3 & 3 & 0 \\ -4 & 8 & -6 & 0 & 5 & 0 \\ -2 & 4 & -3 & 0 & 1 & 3 +\end{array} \right) +\end{displaymath} + +\begin{flushleft} +{\tt ${\cal J}$ = first jordan$({\cal A})$;} +\end{flushleft} + +\begin{displaymath} +{\cal J} = \left( \begin{array}{cccccc} 3 & 0 & 0 & 0 & 0 & 0 \\ 0 & 3 +& 0 & 0 & 0 & 0 \\ 0 & 0 & 1 & 1 & 0 & 0 \\ 0 & 0 & 0 & 1 & 0 & 0 \\ + 0 & 0 & 0 & 0 & i+2 & 0 \\ 0 & 0 & 0 & 0 & 0 & -i+2 +\end{array} \right) +\end{displaymath} + +\newpage + + +\section{arnum} + +The package is loaded by {\tt load\_package arnum;}. The algebraic +field ${\cal Q}$ can now be extended. For example, {\tt defpoly +sqrt2**2-2;} will extend it to include ${\sqrt{2}}$ (defined here by +{\tt sqrt2}). The {\small ARNUM} package was written by Eberhard +Schr\"ufer and is described in the {\it arnum.tex} file. + +\subsection{example} + +{\tt load\_package normform;} \\ +{\tt load\_package arnum;} \\ +{\tt defpoly sqrt2**2-2;} \\ +(sqrt2 now changed to ${\sqrt{2}}$ for looks!) +\vspace{0.2in} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{ccc} 4*{\sqrt{2}}-6 & -4*{\sqrt{2}}+7 & +-3*{\sqrt{2}}+6 \\ 3*{\sqrt{2}}-6 & -3*{\sqrt{2}}+7 & -3*{\sqrt{2}}+6 +\\ 3*{\sqrt{2}} & 1-3*{\sqrt{2}} & -2*{\sqrt{2}} \end{array} \right) +\end{displaymath} +\vspace{0.2in} + +\begin{eqnarray} +{\tt ratjordan}({\cal A}) & = & +\left\{ \left( \begin{array}{ccc} {\sqrt{2}} & 0 & 0 \\ 0 & {\sqrt{2}} +& 0 \\ 0 & 0 & -3*{\sqrt{2}}+1 \end{array} \right), \right. \nonumber +\\ & & \hspace{0.1in} \left. \left( \begin{array}{ccc} 7*{\sqrt{2}}-6 +& \frac{2*{\sqrt{2}}-49}{31} & \frac{-21*{\sqrt{2}}+18}{31} \\ +3*{\sqrt{2}}-6 & \frac{21*{\sqrt{2}}-18}{31} & \frac{-21*{\sqrt{2}}+18} +{31} \\ 3*{\sqrt{2}}+1 & \frac{-3*{\sqrt{2}}+24}{31} & +\frac{3*{\sqrt{2}}-24}{31} \end{array} \right), \right. \nonumber \\ & +& \hspace{0.1in} \left. \left( \begin{array}{ccc} 0 & {\sqrt{2}}+1 & +1 \\ -1 & 4*{\sqrt{2}}+9 & 4*{\sqrt{2}} \\ -1 & -\frac{1}{6}*{\sqrt{2}} ++1 & 1 \end{array} \right) \right\} \nonumber +\end{eqnarray} + +\newpage + + +\section{modular} + +Calculations can be performed in a modular base by switching {\tt on +modular;}. The base can then be set by {\tt setmod p;} (p a prime). The +normal form will then have entries in ${\cal Z}/$p${\cal Z}$. + +By also switching {\tt on balanced\_mod;} the output will be shown using +a symmetric modular representation. + +Information on this modular manipulation can be found in {\it chapter} +9 (Polynomials and Rationals) of the {\REDUCE} User's Manual [5]. + +\subsection{example} + +{\tt load\_package normform;} \\ +{\tt on modular;} \\ +{\tt setmod 23;} +\vspace{0.1in} + +\begin{displaymath} +{\cal A} = \left( \begin{array}{cc} 10 & 18 \\ 17 & 20 \end{array} +\right) +\end{displaymath} + +{\tt jordansymbolic}(${\cal A}$) = +\begin{center} +\begin{displaymath} +\left\{ \left( \begin{array}{cc} 18 & 0 \\ 0 & 12 \end{array} \right), +\left\{ \left\{ \lambda + 5, \lambda + 11 \right\}, \lambda \right\}, +\left( \begin{array}{cc} 15 & 9 \\ 22 & 1 \end{array} \right), \left( +\begin{array}{cc} 1 & 14 \\ 1 & 15 \end{array} \right) \right\} +\end{displaymath} +\end{center} +\vspace{0.2in} + +{\tt on balanced\_mod;} +\vspace{0.2in} + +{\tt jordansymbolic}(${\cal A}$) = +\begin{center} +\begin{displaymath} +\left\{ \left( \begin{array}{cc} -5 & 0 \\ 0 & -11 \end{array} \right), +\left\{ \left\{ \lambda + 5, \lambda + 11 \right\}, \lambda \right\}, +\left( \begin{array}{cc} -8 & 9 \\ -1 & 1 \end{array} \right), \left( +\begin{array}{cc} 1 & -9 \\ 1 & -8 \end{array} \right) \right\} +\end{displaymath} +\end{center} + +\newpage +\begin{thebibliography}{6} +\bibitem{MulLev} T.M.L.Mulders and A.H.M. Levelt: {\it The Maple + normform and Normform packages.} (1993) +\bibitem{Mulders} T.M.L.Mulders: {\it Algoritmen in De Algebra, A + Seminar on Algebraic Algorithms, Nigmegen.} (1993) +\bibitem{HoJo} Roger A. Horn and Charles A. Johnson: {\it Matrix + Analysis.} Cambridge University Press (1990) +\bibitem{Maple} Bruce W. Chat\ldots [et al.]: {\it Maple (Computer + Program)}. Springer-Verlag (1991) +\bibitem{Reduce} Anthony C. Hearn: {\REDUCE} {\it User's Manual 3.6.} + RAND (1995) +\end{thebibliography} + +\end{document} + Index: r36/doc/NUMERIC.TEX ================================================================== --- r36/doc/NUMERIC.TEX +++ r36/doc/NUMERIC.TEX @@ -1,557 +1,557 @@ -\documentstyle[11pt,reduce]{article} -\date{} -\title{NUMERIC} -\author{Herbert Melenk \\ -Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ -Heilbronner Strasse 10 \\ -D--10711 Berlin -- Wilmersdorf \\ -Federal Republic of Germany \\[0.05in] -E--mail: melenk@sc.zib--berlin.de} -\begin{document} -\maketitle - -\index{NUMERIC package} -The {\small NUMERIC} package implements some numerical (approximative) -algorithms for \REDUCE, based on the \REDUCE\ rounded mode -arithmetic. These algorithms are implemented for standard cases. -They should not be called for ill-conditioned problems; -please use standard mathematical libraries for these. - -\section{Syntax} - -\subsection{Intervals, Starting Points} - -Intervals are generally coded as lower bound and -upper bound connected by the operator \verb+`..'+, usually -associated to a variable in an -equation. E.g. - -\begin{verbatim} - x= (2.5 .. 3.5) -\end{verbatim} - -means that the variable x is taken in the range from 2.5 up to -3.5. Note, that the bounds can be algebraic -expressions, which, however, must evaluate to numeric results. -In cases where an interval is returned as the result, the lower -and upper bounds can be extracted by the \verb+PART+ operator -as the first and second part respectively. -A starting point is specified by an equation with a numeric -righthand side, e.g. - -\begin{verbatim} - x=3.0 -\end{verbatim} - -If for multivariate applications several coordinates must be -specified by intervals or as a starting point, these -specifications can be collected in one parameter (which is then -a list) or they can be given as separate parameters -alternatively. The list form is more appropriate when the -parameters are built from other REDUCE calculations in an -automatic style, while the flat form is more convenient -for direct interactive input. - -\subsection{Accuracy Control} - -The keyword parameters $accuracy=a$ and $iterations=i$, where -$a$ and $i$ must be positive integer numbers, control the -iterative algorithms: the iteration is continued until -the local error is below $10^{-a}$; if that is impossible -within $i$ steps, the iteration is terminated with an -error message. The values reached so far are then returned -as the result. - -\subsection{tracing} - -Normally the algorithms produce only a minimum of printed -output during their operation. In cases of an unsuccessful -or unexpected long operation a trace of the iteration can be -printed by setting - -\begin{verbatim} - on trnumeric; -\end{verbatim} - - -\section{Minima} - -The Fletcher Reeves version of the $steepest\ descent$ -algorithms is used to find the minimum of a -function of one or more variables. The -function must have continuous partial derivatives with respect to all -variables. The starting point of the search can be -specified; if not, random values are taken instead. -The steepest descent algorithms in general find only local -minima. - -Syntax: - -\begin{description} -\item[NUM\_MIN] $(exp, var_1[=val_1] [,var_2[=val_2] \ldots]$ - -$ [,accuracy=a][,iterations=i]) $ - -or - -\item[NUM\_MIN] $(exp, \{ var_1[=val_1] [,var_2[=val_2] \ldots] \}$ - -$ [,accuracy=a][,iterations=i]) $ - - -where $exp$ is a function expression, - -$var_1, var_2, \ldots$ are the variables in $exp$ and -$val_1,val_2, \ldots$ are the (optional) start values. - -NUM\_MIN tries to find the next local minimum along the descending -path starting at the given point. The result is a list -with the minimum function value as first element followed by a list -of equations, where the variables are equated to the coordinates -of the result point. -\end{description} - -Examples: - -\begin{verbatim} - num_min(sin(x)+x/5, x); - - {4.9489585606,{X=29.643767785}} - - num_min(sin(x)+x/5, x=0); - - { - 1.3342267466,{X= - 1.7721582671}} - - % Rosenbrock function (well known as hard to minimize). - fktn := 100*(x1**2-x2)**2 + (1-x1)**2; - num_min(fktn, x1=-1.2, x2=1, iterations=200); - - {0.00000021870228295,{X1=0.99953284494,X2=0.99906807238}} - -\end{verbatim} - -\section{Roots of Functions/ Solutions of Equations} - -An adaptively damped Newton iteration is used to find -an approximative zero of a function, a function vector or the solution -of an equation or an equation system. Equations are -internally converted to a difference of lhs and rhs such -that the Newton method (=zero detection) can be applied. The expressions -must have continuous derivatives for all variables. -A starting point for the iteration can be given. If not given, -random values are taken instead. If the number of -forms is not equal to the number of variables, the -Newton method cannot be applied. Then the minimum -of the sum of absolute squares is located instead. - -With ON COMPLEX solutions with imaginary parts can be -found, if either the expression(s) or the starting point -contain a nonzero imaginary part. - -Syntax: - -\begin{description} -\item[NUM\_SOLVE] $(exp_1, var_1[=val_1][,accuracy=a][,iterations=i])$ - -or - -\item[NUM\_SOLVE] $(\{exp_1,\ldots,exp_n\}, - var_1[=val_1],\ldots,var_1[=val_n]$ -\item[\ \ \ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ - -or - -\item[NUM\_SOLVE] $(\{exp_1,\ldots,exp_n\}, - \{var_1[=val_1],\ldots,var_1[=val_n]\}$ -\item[\ \ \ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ - -where $exp_1, \ldots,exp_n$ are function expressions, - - $var_1, \ldots, var_n$ are the variables, - - $val_1, \ldots, val_n$ are optional start values. - -NUM\_SOLVE tries to find a zero/solution of the expression(s). -Result is a list of equations, where the variables are -equated to the coordinates of the result point. - -The Jacobian matrix is stored as a side effect in the shared -variable JACOBIAN. - -\end{description} - -Example: - -\begin{verbatim} - num_solve({sin x=cos y, x + y = 1},{x=1,y=2}); - - {X= - 1.8561957251,Y=2.856195584} - - jacobian; - - [COS(X) SIN(Y)] - [ ] - [ 1 1 ] -\end{verbatim} - -\section{Integrals} - -For the numerical evaluation of univariate integrals over a finite -interval the following strategy is used: -\begin{enumerate} -\item If the function has an antiderivative in close form - which is bounded in the integration interval, this - is used. -\item Otherwise a Chebyshev approximation is computed, - starting with order 20, eventually up to order 80. - If that is recognized as sufficiently convergent - it is used for computing the integral by directly - integrating the coefficient sequence. -\item If none of these methods is successful, an - adaptive multilevel quadrature algorithm is used. -\end{enumerate} -For multivariate integrals only the adaptive quadrature is used. -This algorithm tolerates isolated singularities. -The value $iterations$ here limits the number of -local interval intersection levels. -$Accuracy$ is a measure for the relative total discretization -error (comparison of order 1 and order 2 approximations). - -Syntax: - -\begin{description} -\item[NUM\_INT] $(exp,var_1=(l_1 .. u_1)[,var_2=(l_2 .. u_2)\ldots]$ -\item[\ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ - -where $exp$ is the function to be integrated, - -$var_1, var_2 , \ldots$ are the integration variables, - -$l_1, l_2 , \ldots$ are the lower bounds, - -$u_1, u_2 , \ldots$ are the upper bounds. - -Result is the value of the integral. - -\end{description} - -Example: - -\begin{verbatim} - num_int(sin x,x=(0 .. pi)); - - 2.0000010334 -\end{verbatim} - -\section{Ordinary Differential Equations} - -A Runge-Kutta method of order 3 finds an approximate graph for -the solution of a ordinary differential equation -real initial value problem. - -Syntax: -\begin{description} -\item[NUM\_ODESOLVE]($exp$,$depvar=dv$,$indepvar$=$(from .. to)$ - -$ [,accuracy=a][,iterations=i]) $ - -where - -$exp$ is the differential expression/equation, - -$depvar$ is an identifier representing the dependent variable -(function to be found), - -$indepvar$ is an identifier representing the independent variable, - -$exp$ is an equation (or an expression implicitly set to zero) which -contains the first derivative of $depvar$ wrt $indepvar$, - -$from$ is the starting point of integration, - -$to$ is the endpoint of integration (allowed to be below $from$), - -$dv$ is the initial value of $depvar$ in the point $indepvar=from$. - -The ODE $exp$ is converted into an explicit form, which then is -used for a Runge Kutta iteration over the given range. The -number of steps is controlled by the value of $i$ -(default: 20). -If the steps are too coarse to reach the desired -accuracy in the neighborhood of the starting point, the number is -increased automatically. - -Result is a list of pairs, each representing a point of the -approximate solution of the ODE problem. -\end{description} - - -Example: - -\begin{verbatim} - - num_odesolve(df(y,x)=y,y=1,x=(0 .. 1), iterations=5); - - {{0.0,1.0},{0.2,1.2214},{0.4,1.49181796},{0.6,1.8221064563}, - - {0.8,2.2255208258},{1.0,2.7182511366}} - -\end{verbatim} - -Remarks: - -\begin{enumerate} - -\item[--] If in $exp$ the differential is not isolated on the lefthand side, -please ensure that the dependent variable is explicitly declared -using a \verb+DEPEND+ statement, e.g. - -\begin{verbatim} - depend y,x; -\end{verbatim} - -otherwise the formal derivative will be computed to zero by REDUCE. - -\item[--] The REDUCE package SOLVE is used to convert the form into -an explicit ODE. If that process fails or has no unique result, -the evaluation is stopped with an error message. - -\end{enumerate} - -\section{Bounds of a Function} - -Upper and lower bounds of a real valued function over an -interval or a rectangular multivariate domain are computed -by the operator BOUNDS. The algorithmic basis is the computation -with inequalities: starting from the interval(s) of the -variables, the bounds are propagated in the expression -using the rules for inequality computation. Some knowledge -about the behavior of special functions like ABS, SIN, COS, EXP, LOG, -fractional exponentials etc. is integrated and can be evaluated -if the operator BOUNDS is called with rounded mode on -(otherwise only algebraic evaluation rules are available). - -If BOUNDS finds a singularity within an interval, the evaluation -is stopped with an error message indicating the problem part -of the expression. - -Syntax: - - -\begin{description} -\item[BOUNDS]$(exp,var_1=(l_1 .. u_1) [,var_2=(l_2 .. u_2) \ldots])$ - -\item[{\it BOUNDS}]$(exp,\{var_1=(l_1 .. u_1) [,var_2=(l_2 .. u_2)\ldots]\})$ - -where $exp$ is the function to be investigated, - -$var_1, var_2 , \ldots$ are the variables of exp, - -$l_1, l_2 , \ldots$ and $u_1, u_2 , \ldots$ specify the area (intervals). - -$BOUNDS$ computes upper and lower bounds for the expression in the -given area. An interval is returned. - -\end{description} - -Example: - -\begin{verbatim} - - bounds(sin x,x=(1 .. 2)); - - {-1,1} - - on rounded; - bounds(sin x,x=(1 .. 2)); - - 0.84147098481 .. 1 - - bounds(x**2+x,x=(-0.5 .. 0.5)); - - - 0.25 .. 0.75 - -\end{verbatim} - -\section{Chebyshev Curve Fitting} - -The operator family $Chebyshev\_\ldots$ implements approximation -and evaluation of functions by the Chebyshev method. -Let $T_n^{(a,b)}(x)$ be the Chebyshev polynomial of order $n$ -transformed to the interval $(a,b)$. Then a function $f(x)$ can be -approximated in $(a,b)$ by a series - -$f(x) \approx \sum_{i=0}^N c_i T_i^{(a,b)}(x)$ - -The operator $Chebyshev\_fit$ computes this approximation and -returns a list, which has as first element the sum expressed -as a polynomial and as second element the sequence -of Chebyshev coefficients ${c_i}$. -$Chebyshev\_df$ and $Chebyshev\_int$ transform a Chebyshev -coefficient list into the coefficients of the corresponding -derivative or integral respectively. For evaluating a Chebyshev -approximation at a given point in the basic interval the -operator $Chebyshev\_eval$ can be used. Note that -$Chebyshev\_eval$ is based on a recurrence relation which is -in general more stable than a direct evaluation of the -complete polynomial. - -\begin{description} -\item[CHEBYSHEV\_FIT] $(fcn,var=(lo .. hi),n)$ - -\item[CHEBYSHEV\_EVAL] $(coeffs,var=(lo .. hi),var=pt)$ - -\item[CHEBYSHEV\_DF] $(coeffs,var=(lo .. hi))$ - -\item[CHEBYSHEV\_INT] $(coeffs,var=(lo .. hi))$ - -where $fcn$ is an algebraic expression (the function to be -fitted), $var$ is the variable of $fcn$, $lo$ and $hi$ are -numerical real values which describe an interval ($lo < hi$), -$n$ is the approximation order,an integer $>0$, set to 20 if missing, -$pt$ is a numerical value in the interval and $coeffs$ is -a series of Chebyshev coefficients, computed by one of -$CHEBYSHEV\_COEFF$, $\_DF$ or $\_INT$. -\end{description} - -Example: - -\begin{verbatim} - -on rounded; - -w:=chebyshev_fit(sin x/x,x=(1 .. 3),5); - - 3 2 -w := {0.03824*x - 0.2398*x + 0.06514*x + 0.9778, - - {0.8991,-0.4066,-0.005198,0.009464,-0.00009511}} - -chebyshev_eval(second w, x=(1 .. 3), x=2.1); - -0.4111 - -\end{verbatim} - -\section{General Curve Fitting} - -The operator $NUM\_FIT$ finds for a set of -points the linear combination of a given set of -functions (function basis) which approximates the -points best under the objective of the least squares -criterion (minimum of the sum of the squares of the deviation). -The solution is found as zero of the -gradient vector of the sum of squared errors. - -Syntax: - -\begin{description} -\item[NUM\_FIT] $(vals,basis,var=pts)$ - -where $vals$ is a list of numeric values, - -$var$ is a variable used for the approximation, - -$pts$ is a list of coordinate values which correspond to $var$, - -$basis$ is a set of functions varying in $var$ which is used - for the approximation. - -\end{description} - -The result is a list containing as first element the -function which approximates the given values, and as -second element a list of coefficients which were used -to build this function from the basis. - -Example: - -\begin{verbatim} - - % approximate a set of factorials by a polynomial - pts:=for i:=1 step 1 until 5 collect i$ - vals:=for i:=1 step 1 until 5 collect - for j:=1:i product j$ - - num_fit(vals,{1,x,x**2},x=pts); - - 2 - {14.571428571*X - 61.428571429*X + 54.6,{54.6, - - - 61.428571429,14.571428571}} - - num_fit(vals,{1,x,x**2,x**3,x**4},x=pts); - - 4 3 - {2.2083333234*X - 20.249999879*X - - 2 - + 67.791666154*X - 93.749999133*X - - + 44.999999525, - - {44.999999525, - 93.749999133,67.791666154, - - - 20.249999879,2.2083333234}} - - -\end{verbatim} - -\section{Function Bases} - -The following procedures compute sets of functions -e.g. to be used for approximation. -All procedures have -two parameters, the expression to be used as $variable$ -(an identifier in most cases) and the -order of the desired system. -The functions are not scaled to a specific interval, but -the $variable$ can be accompanied by a scale factor -and/or a translation -in order to map the generic interval of orthogonality to another -(e.g. $(x- 1/2 ) * 2 pi$). -The result is a function list with ascending order, such that -the first element is the function of order zero and (for -the polynomial systems) the function of order $n$ is the $n+1$-th -element. - -\begin{verbatim} - - monomial_base(x,n) {1,x,...,x**n} - trigonometric_base(x,n) {1,sin x,cos x,sin(2x),cos(2x)...} - Bernstein_base(x,n) Bernstein polynomials - Legendre_base(x,n) Legendre polynomials - Laguerre_base(x,n) Laguerre polynomials - Hermite_base(x,n) Hermite polynomials - Chebyshev_base_T(x,n) Chebyshev polynomials first kind - Chebyshev_base_U(x,n) Chebyshev polynomials second kind - -\end{verbatim} - -Example: - -\begin{verbatim} - Bernstein_base(x,5); - - 5 4 3 2 - { - X + 5*X - 10*X + 10*X - 5*X + 1, - - 4 3 2 - 5*X*(X - 4*X + 6*X - 4*X + 1), - - 2 3 2 - 10*X *( - X + 3*X - 3*X + 1), - - 3 2 - 10*X *(X - 2*X + 1), - - 4 - 5*X *( - X + 1), - - 5 - X } - -\end{verbatim} - -\end{document} - +\documentstyle[11pt,reduce]{article} +\date{} +\title{NUMERIC} +\author{Herbert Melenk \\ +Konrad--Zuse--Zentrum f\"ur Informationstechnik Berlin \\ +Heilbronner Strasse 10 \\ +D--10711 Berlin -- Wilmersdorf \\ +Federal Republic of Germany \\[0.05in] +E--mail: melenk@sc.zib--berlin.de} +\begin{document} +\maketitle + +\index{NUMERIC package} +The {\small NUMERIC} package implements some numerical (approximative) +algorithms for \REDUCE, based on the \REDUCE\ rounded mode +arithmetic. These algorithms are implemented for standard cases. +They should not be called for ill-conditioned problems; +please use standard mathematical libraries for these. + +\section{Syntax} + +\subsection{Intervals, Starting Points} + +Intervals are generally coded as lower bound and +upper bound connected by the operator \verb+`..'+, usually +associated to a variable in an +equation. E.g. + +\begin{verbatim} + x= (2.5 .. 3.5) +\end{verbatim} + +means that the variable x is taken in the range from 2.5 up to +3.5. Note, that the bounds can be algebraic +expressions, which, however, must evaluate to numeric results. +In cases where an interval is returned as the result, the lower +and upper bounds can be extracted by the \verb+PART+ operator +as the first and second part respectively. +A starting point is specified by an equation with a numeric +righthand side, e.g. + +\begin{verbatim} + x=3.0 +\end{verbatim} + +If for multivariate applications several coordinates must be +specified by intervals or as a starting point, these +specifications can be collected in one parameter (which is then +a list) or they can be given as separate parameters +alternatively. The list form is more appropriate when the +parameters are built from other REDUCE calculations in an +automatic style, while the flat form is more convenient +for direct interactive input. + +\subsection{Accuracy Control} + +The keyword parameters $accuracy=a$ and $iterations=i$, where +$a$ and $i$ must be positive integer numbers, control the +iterative algorithms: the iteration is continued until +the local error is below $10^{-a}$; if that is impossible +within $i$ steps, the iteration is terminated with an +error message. The values reached so far are then returned +as the result. + +\subsection{tracing} + +Normally the algorithms produce only a minimum of printed +output during their operation. In cases of an unsuccessful +or unexpected long operation a trace of the iteration can be +printed by setting + +\begin{verbatim} + on trnumeric; +\end{verbatim} + + +\section{Minima} + +The Fletcher Reeves version of the $steepest\ descent$ +algorithms is used to find the minimum of a +function of one or more variables. The +function must have continuous partial derivatives with respect to all +variables. The starting point of the search can be +specified; if not, random values are taken instead. +The steepest descent algorithms in general find only local +minima. + +Syntax: + +\begin{description} +\item[NUM\_MIN] $(exp, var_1[=val_1] [,var_2[=val_2] \ldots]$ + +$ [,accuracy=a][,iterations=i]) $ + +or + +\item[NUM\_MIN] $(exp, \{ var_1[=val_1] [,var_2[=val_2] \ldots] \}$ + +$ [,accuracy=a][,iterations=i]) $ + + +where $exp$ is a function expression, + +$var_1, var_2, \ldots$ are the variables in $exp$ and +$val_1,val_2, \ldots$ are the (optional) start values. + +NUM\_MIN tries to find the next local minimum along the descending +path starting at the given point. The result is a list +with the minimum function value as first element followed by a list +of equations, where the variables are equated to the coordinates +of the result point. +\end{description} + +Examples: + +\begin{verbatim} + num_min(sin(x)+x/5, x); + + {4.9489585606,{X=29.643767785}} + + num_min(sin(x)+x/5, x=0); + + { - 1.3342267466,{X= - 1.7721582671}} + + % Rosenbrock function (well known as hard to minimize). + fktn := 100*(x1**2-x2)**2 + (1-x1)**2; + num_min(fktn, x1=-1.2, x2=1, iterations=200); + + {0.00000021870228295,{X1=0.99953284494,X2=0.99906807238}} + +\end{verbatim} + +\section{Roots of Functions/ Solutions of Equations} + +An adaptively damped Newton iteration is used to find +an approximative zero of a function, a function vector or the solution +of an equation or an equation system. Equations are +internally converted to a difference of lhs and rhs such +that the Newton method (=zero detection) can be applied. The expressions +must have continuous derivatives for all variables. +A starting point for the iteration can be given. If not given, +random values are taken instead. If the number of +forms is not equal to the number of variables, the +Newton method cannot be applied. Then the minimum +of the sum of absolute squares is located instead. + +With ON COMPLEX solutions with imaginary parts can be +found, if either the expression(s) or the starting point +contain a nonzero imaginary part. + +Syntax: + +\begin{description} +\item[NUM\_SOLVE] $(exp_1, var_1[=val_1][,accuracy=a][,iterations=i])$ + +or + +\item[NUM\_SOLVE] $(\{exp_1,\ldots,exp_n\}, + var_1[=val_1],\ldots,var_1[=val_n]$ +\item[\ \ \ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ + +or + +\item[NUM\_SOLVE] $(\{exp_1,\ldots,exp_n\}, + \{var_1[=val_1],\ldots,var_1[=val_n]\}$ +\item[\ \ \ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ + +where $exp_1, \ldots,exp_n$ are function expressions, + + $var_1, \ldots, var_n$ are the variables, + + $val_1, \ldots, val_n$ are optional start values. + +NUM\_SOLVE tries to find a zero/solution of the expression(s). +Result is a list of equations, where the variables are +equated to the coordinates of the result point. + +The Jacobian matrix is stored as a side effect in the shared +variable JACOBIAN. + +\end{description} + +Example: + +\begin{verbatim} + num_solve({sin x=cos y, x + y = 1},{x=1,y=2}); + + {X= - 1.8561957251,Y=2.856195584} + + jacobian; + + [COS(X) SIN(Y)] + [ ] + [ 1 1 ] +\end{verbatim} + +\section{Integrals} + +For the numerical evaluation of univariate integrals over a finite +interval the following strategy is used: +\begin{enumerate} +\item If the function has an antiderivative in close form + which is bounded in the integration interval, this + is used. +\item Otherwise a Chebyshev approximation is computed, + starting with order 20, eventually up to order 80. + If that is recognized as sufficiently convergent + it is used for computing the integral by directly + integrating the coefficient sequence. +\item If none of these methods is successful, an + adaptive multilevel quadrature algorithm is used. +\end{enumerate} +For multivariate integrals only the adaptive quadrature is used. +This algorithm tolerates isolated singularities. +The value $iterations$ here limits the number of +local interval intersection levels. +$Accuracy$ is a measure for the relative total discretization +error (comparison of order 1 and order 2 approximations). + +Syntax: + +\begin{description} +\item[NUM\_INT] $(exp,var_1=(l_1 .. u_1)[,var_2=(l_2 .. u_2)\ldots]$ +\item[\ \ \ \ \ \ ]$[,accuracy=a][,iterations=i])$ + +where $exp$ is the function to be integrated, + +$var_1, var_2 , \ldots$ are the integration variables, + +$l_1, l_2 , \ldots$ are the lower bounds, + +$u_1, u_2 , \ldots$ are the upper bounds. + +Result is the value of the integral. + +\end{description} + +Example: + +\begin{verbatim} + num_int(sin x,x=(0 .. pi)); + + 2.0000010334 +\end{verbatim} + +\section{Ordinary Differential Equations} + +A Runge-Kutta method of order 3 finds an approximate graph for +the solution of a ordinary differential equation +real initial value problem. + +Syntax: +\begin{description} +\item[NUM\_ODESOLVE]($exp$,$depvar=dv$,$indepvar$=$(from .. to)$ + +$ [,accuracy=a][,iterations=i]) $ + +where + +$exp$ is the differential expression/equation, + +$depvar$ is an identifier representing the dependent variable +(function to be found), + +$indepvar$ is an identifier representing the independent variable, + +$exp$ is an equation (or an expression implicitly set to zero) which +contains the first derivative of $depvar$ wrt $indepvar$, + +$from$ is the starting point of integration, + +$to$ is the endpoint of integration (allowed to be below $from$), + +$dv$ is the initial value of $depvar$ in the point $indepvar=from$. + +The ODE $exp$ is converted into an explicit form, which then is +used for a Runge Kutta iteration over the given range. The +number of steps is controlled by the value of $i$ +(default: 20). +If the steps are too coarse to reach the desired +accuracy in the neighborhood of the starting point, the number is +increased automatically. + +Result is a list of pairs, each representing a point of the +approximate solution of the ODE problem. +\end{description} + + +Example: + +\begin{verbatim} + + num_odesolve(df(y,x)=y,y=1,x=(0 .. 1), iterations=5); + + {{0.0,1.0},{0.2,1.2214},{0.4,1.49181796},{0.6,1.8221064563}, + + {0.8,2.2255208258},{1.0,2.7182511366}} + +\end{verbatim} + +Remarks: + +\begin{enumerate} + +\item[--] If in $exp$ the differential is not isolated on the lefthand side, +please ensure that the dependent variable is explicitly declared +using a \verb+DEPEND+ statement, e.g. + +\begin{verbatim} + depend y,x; +\end{verbatim} + +otherwise the formal derivative will be computed to zero by REDUCE. + +\item[--] The REDUCE package SOLVE is used to convert the form into +an explicit ODE. If that process fails or has no unique result, +the evaluation is stopped with an error message. + +\end{enumerate} + +\section{Bounds of a Function} + +Upper and lower bounds of a real valued function over an +interval or a rectangular multivariate domain are computed +by the operator BOUNDS. The algorithmic basis is the computation +with inequalities: starting from the interval(s) of the +variables, the bounds are propagated in the expression +using the rules for inequality computation. Some knowledge +about the behavior of special functions like ABS, SIN, COS, EXP, LOG, +fractional exponentials etc. is integrated and can be evaluated +if the operator BOUNDS is called with rounded mode on +(otherwise only algebraic evaluation rules are available). + +If BOUNDS finds a singularity within an interval, the evaluation +is stopped with an error message indicating the problem part +of the expression. + +Syntax: + + +\begin{description} +\item[BOUNDS]$(exp,var_1=(l_1 .. u_1) [,var_2=(l_2 .. u_2) \ldots])$ + +\item[{\it BOUNDS}]$(exp,\{var_1=(l_1 .. u_1) [,var_2=(l_2 .. u_2)\ldots]\})$ + +where $exp$ is the function to be investigated, + +$var_1, var_2 , \ldots$ are the variables of exp, + +$l_1, l_2 , \ldots$ and $u_1, u_2 , \ldots$ specify the area (intervals). + +$BOUNDS$ computes upper and lower bounds for the expression in the +given area. An interval is returned. + +\end{description} + +Example: + +\begin{verbatim} + + bounds(sin x,x=(1 .. 2)); + + {-1,1} + + on rounded; + bounds(sin x,x=(1 .. 2)); + + 0.84147098481 .. 1 + + bounds(x**2+x,x=(-0.5 .. 0.5)); + + - 0.25 .. 0.75 + +\end{verbatim} + +\section{Chebyshev Curve Fitting} + +The operator family $Chebyshev\_\ldots$ implements approximation +and evaluation of functions by the Chebyshev method. +Let $T_n^{(a,b)}(x)$ be the Chebyshev polynomial of order $n$ +transformed to the interval $(a,b)$. Then a function $f(x)$ can be +approximated in $(a,b)$ by a series + +$f(x) \approx \sum_{i=0}^N c_i T_i^{(a,b)}(x)$ + +The operator $Chebyshev\_fit$ computes this approximation and +returns a list, which has as first element the sum expressed +as a polynomial and as second element the sequence +of Chebyshev coefficients ${c_i}$. +$Chebyshev\_df$ and $Chebyshev\_int$ transform a Chebyshev +coefficient list into the coefficients of the corresponding +derivative or integral respectively. For evaluating a Chebyshev +approximation at a given point in the basic interval the +operator $Chebyshev\_eval$ can be used. Note that +$Chebyshev\_eval$ is based on a recurrence relation which is +in general more stable than a direct evaluation of the +complete polynomial. + +\begin{description} +\item[CHEBYSHEV\_FIT] $(fcn,var=(lo .. hi),n)$ + +\item[CHEBYSHEV\_EVAL] $(coeffs,var=(lo .. hi),var=pt)$ + +\item[CHEBYSHEV\_DF] $(coeffs,var=(lo .. hi))$ + +\item[CHEBYSHEV\_INT] $(coeffs,var=(lo .. hi))$ + +where $fcn$ is an algebraic expression (the function to be +fitted), $var$ is the variable of $fcn$, $lo$ and $hi$ are +numerical real values which describe an interval ($lo < hi$), +$n$ is the approximation order,an integer $>0$, set to 20 if missing, +$pt$ is a numerical value in the interval and $coeffs$ is +a series of Chebyshev coefficients, computed by one of +$CHEBYSHEV\_COEFF$, $\_DF$ or $\_INT$. +\end{description} + +Example: + +\begin{verbatim} + +on rounded; + +w:=chebyshev_fit(sin x/x,x=(1 .. 3),5); + + 3 2 +w := {0.03824*x - 0.2398*x + 0.06514*x + 0.9778, + + {0.8991,-0.4066,-0.005198,0.009464,-0.00009511}} + +chebyshev_eval(second w, x=(1 .. 3), x=2.1); + +0.4111 + +\end{verbatim} + +\section{General Curve Fitting} + +The operator $NUM\_FIT$ finds for a set of +points the linear combination of a given set of +functions (function basis) which approximates the +points best under the objective of the least squares +criterion (minimum of the sum of the squares of the deviation). +The solution is found as zero of the +gradient vector of the sum of squared errors. + +Syntax: + +\begin{description} +\item[NUM\_FIT] $(vals,basis,var=pts)$ + +where $vals$ is a list of numeric values, + +$var$ is a variable used for the approximation, + +$pts$ is a list of coordinate values which correspond to $var$, + +$basis$ is a set of functions varying in $var$ which is used + for the approximation. + +\end{description} + +The result is a list containing as first element the +function which approximates the given values, and as +second element a list of coefficients which were used +to build this function from the basis. + +Example: + +\begin{verbatim} + + % approximate a set of factorials by a polynomial + pts:=for i:=1 step 1 until 5 collect i$ + vals:=for i:=1 step 1 until 5 collect + for j:=1:i product j$ + + num_fit(vals,{1,x,x**2},x=pts); + + 2 + {14.571428571*X - 61.428571429*X + 54.6,{54.6, + + - 61.428571429,14.571428571}} + + num_fit(vals,{1,x,x**2,x**3,x**4},x=pts); + + 4 3 + {2.2083333234*X - 20.249999879*X + + 2 + + 67.791666154*X - 93.749999133*X + + + 44.999999525, + + {44.999999525, - 93.749999133,67.791666154, + + - 20.249999879,2.2083333234}} + + +\end{verbatim} + +\section{Function Bases} + +The following procedures compute sets of functions +e.g. to be used for approximation. +All procedures have +two parameters, the expression to be used as $variable$ +(an identifier in most cases) and the +order of the desired system. +The functions are not scaled to a specific interval, but +the $variable$ can be accompanied by a scale factor +and/or a translation +in order to map the generic interval of orthogonality to another +(e.g. $(x- 1/2 ) * 2 pi$). +The result is a function list with ascending order, such that +the first element is the function of order zero and (for +the polynomial systems) the function of order $n$ is the $n+1$-th +element. + +\begin{verbatim} + + monomial_base(x,n) {1,x,...,x**n} + trigonometric_base(x,n) {1,sin x,cos x,sin(2x),cos(2x)...} + Bernstein_base(x,n) Bernstein polynomials + Legendre_base(x,n) Legendre polynomials + Laguerre_base(x,n) Laguerre polynomials + Hermite_base(x,n) Hermite polynomials + Chebyshev_base_T(x,n) Chebyshev polynomials first kind + Chebyshev_base_U(x,n) Chebyshev polynomials second kind + +\end{verbatim} + +Example: + +\begin{verbatim} + Bernstein_base(x,5); + + 5 4 3 2 + { - X + 5*X - 10*X + 10*X - 5*X + 1, + + 4 3 2 + 5*X*(X - 4*X + 6*X - 4*X + 1), + + 2 3 2 + 10*X *( - X + 3*X - 3*X + 1), + + 3 2 + 10*X *(X - 2*X + 1), + + 4 + 5*X *( - X + 1), + + 5 + X } + +\end{verbatim} + +\end{document} + Index: r36/doc/ODESOLVE.TEX ================================================================== --- r36/doc/ODESOLVE.TEX +++ r36/doc/ODESOLVE.TEX @@ -1,159 +1,159 @@ -\documentstyle[11pt,reduce]{article} -\date{} -\title{ODESOLVE} -\author{Malcolm A.H. MacCallum \\ Queen Mary and Westfield College, London \\ -Email: mm@maths.qmw.ac.uk \\[0.1in] -Other contributors: Francis Wright, Alan Barnes} -\begin{document} -\maketitle - -\index{ODESOLVE package} -\index{ordinary differential equations} -The ODESOLVE package is a solver for ordinary differential equations. -At the present time it has very limited capabilities, - -\begin{enumerate} -\item it can handle only a single scalar equation presented as an -algebraic expression or equation, and -\item it can solve only first-order equations of simple types, -linear equations with constant coefficients and Euler equations. -\end{enumerate} - -\noindent These solvable types are exactly those for -which Lie symmetry techniques give no useful information. - -\section{Use} -The only top-level function the user should normally invoke is: -\ttindex{ODESOLVE} - -\vspace{.1in} -\begin{tabbing} -{\tt ODESOLVE}(\=EXPRN:{\em expression, equation}, \\ -\>VAR1:{\em variable}, \\ -\>VAR2:{\em variable}):{\em list-algebraic} -\end{tabbing} -\vspace{.1in} - -\noindent {\tt ODESOLVE} returns a list containing an equation (like solve): - -\begin{description} -\item[EXPRN] is a single scalar expression such that EXPRN = 0 is the -ordinary differential equation (ODE for short) to be solved, -or is an equivalent equation. -\item[VAR1] is the name of the dependent variable. -\item[VAR2] is the name of the independent variable -\end{description} - -\noindent (For simplicity these will be called y and x in the sequel) -The returned value is a list containing the equation giving the -general solution of the ODE (for simultaneous equations this will be a -list of equations eventually). It will contain occurrences of the -\index{ARBCONST operator} -operator {\tt ARBCONST} for the arbitrary constants in the general solution. -The arguments of {\tt ARBCONST} should be new, as with {\tt ARBINT} etc. -in SOLVE. A counter {\tt !!ARBCONST} is used to arrange this (similar to the -way {\tt ARBINT} is implemented). - -Some other top-level functions may be of use elsewhere, especially: -\ttindex{SORTOUTODE} - -\vspace{.1in} -\noindent{\tt SORTOUTODE}(EXPRN:{\em algebraic}, Y:{\em var}, X:{\em var}): -{\em expression} -\vspace{.1in} - -\noindent which finds the order and degree of the EXPRN as a differential -equation for Y with respect to Y and sets the linearity and highest -derivative occurring in reserved variables ODEORDER, ODEDEGREE, -\ttindex{ODEORDER} \ttindex{ODEDEGREE} \ttindex{ODELINEARITY} -\ttindex{HIGHESTDERIV} -ODELINEARITY and HIGHESTDERIV. An expression equivalent to the ODE is -returned, or zero if EXPRN (equated to 0) is not an ODE in the -given vars. - -"The use of the function\ttindex{COFACTOR} - -\vspace{.1in} -\begin{tabbing} -{\tt COFACTOR}(\=ROW:{\em integer}, \\ -\>COLUMN:{\em integer}, \\ -\>MATRIX:{\em matrix}):{\em algebraic} -\end{tabbing} -\vspace{.1in} - -\noindent which uses variation of parameters, returns the cofactor of the -element in row ROW and column COLUMN of the matrix MATRIX. Errors occur -if ROW or COLUMN do not simplify to integer expressions or if MATRIX is -not square. - -\section{Tracing} - - -Some rudimentary tracing is provided and is activated by the switch TRODE -\index{tracing ! ODESOLVE} -\ttindex{TRODE} -(analogous to TRFAC and TRINT) - -\section{Comments} - -The intention in the long run is to develop a rather general and -powerful ordinary differential equation solver incorporating the -methods detailed below. At present the program has not been optimized -for efficiency and much work remains to be done to convert algebraic -mode procedures to more efficient symbolic mode replacements. - -No attempt is made to extend the REDUCE integrator, although this is -in some sense a problem of ODEs. Thus the equation $\frac{dy}{dx} = g(x)$ will -be solved if and only if $\int g(x) dx$ succeeds. - -The available and planned coverage is as follows: - -\begin{itemize} -\item First-order equations: (first degree unless otherwise stated) - -\begin{itemize} -\item Quadrature of $\frac{df}{dx} = g(x)$ -\item Linear equations -\item Separable equations -\item (Algebraically) homogeneous equations -\item Equations reducible to the previous case by linear transformations -\item Exact equations -\item Bernoulli equations -\end{itemize} - -The above are already implemented. Further 1st order cases are not: -\begin{itemize} -\item Riccati equations using Schmidt's methods and other special cases -\item Hypotheses on the integrating factor following Char (SYMSAC 81) -or Shtokhamer, Glinos and Caviness. -\item Higher degree cases -\end{itemize} -\item Linear equations of higher order -\begin{itemize} -\item Constant coefficients case for driving terms solvable by -variation of parameters using the integrator -(Choice of method is discussed in the source of module lccode). -\end{itemize} -The above is already implemented. Further higher order methods are not: -\begin{itemize} -\item More complex driving terms via Laplace transforms (?) -\item Variable coefficients: Watanabe (EUROSAM 84) methods -including Kovacic's algorithm as extended by Singer -\item Factorization of operators as in Schwarz's ISSAC-89 paper or -Berkovich's 1990 book -\item Other methods based on Galois theory (see Ulmer's preprints -from Karlsruhe, 1989, 1990 and Singer's 1989 review) or -other ways of hunting Liouvillian solutions (see Singer's -review in J. Symb. Comp., 1990). -\end{itemize} -\item Non-linear equations of order 2 and higher -\begin{itemize} -\item Lie algebra of point symmetries e.g. using Wolf's CRACK now available -in REDUCE -\item Other special ansatze (see Wolf. op. cit), in particular -contact transformations for 2nd order cases -\end{itemize} -\item Possibly (?) exploitation of Cartan's methods for equivalence of -differential equations. -\end{itemize} -\end{document} +\documentstyle[11pt,reduce]{article} +\date{} +\title{ODESOLVE} +\author{Malcolm A.H. MacCallum \\ Queen Mary and Westfield College, London \\ +Email: mm@maths.qmw.ac.uk \\[0.1in] +Other contributors: Francis Wright, Alan Barnes} +\begin{document} +\maketitle + +\index{ODESOLVE package} +\index{ordinary differential equations} +The ODESOLVE package is a solver for ordinary differential equations. +At the present time it has very limited capabilities, + +\begin{enumerate} +\item it can handle only a single scalar equation presented as an +algebraic expression or equation, and +\item it can solve only first-order equations of simple types, +linear equations with constant coefficients and Euler equations. +\end{enumerate} + +\noindent These solvable types are exactly those for +which Lie symmetry techniques give no useful information. + +\section{Use} +The only top-level function the user should normally invoke is: +\ttindex{ODESOLVE} + +\vspace{.1in} +\begin{tabbing} +{\tt ODESOLVE}(\=EXPRN:{\em expression, equation}, \\ +\>VAR1:{\em variable}, \\ +\>VAR2:{\em variable}):{\em list-algebraic} +\end{tabbing} +\vspace{.1in} + +\noindent {\tt ODESOLVE} returns a list containing an equation (like solve): + +\begin{description} +\item[EXPRN] is a single scalar expression such that EXPRN = 0 is the +ordinary differential equation (ODE for short) to be solved, +or is an equivalent equation. +\item[VAR1] is the name of the dependent variable. +\item[VAR2] is the name of the independent variable +\end{description} + +\noindent (For simplicity these will be called y and x in the sequel) +The returned value is a list containing the equation giving the +general solution of the ODE (for simultaneous equations this will be a +list of equations eventually). It will contain occurrences of the +\index{ARBCONST operator} +operator {\tt ARBCONST} for the arbitrary constants in the general solution. +The arguments of {\tt ARBCONST} should be new, as with {\tt ARBINT} etc. +in SOLVE. A counter {\tt !!ARBCONST} is used to arrange this (similar to the +way {\tt ARBINT} is implemented). + +Some other top-level functions may be of use elsewhere, especially: +\ttindex{SORTOUTODE} + +\vspace{.1in} +\noindent{\tt SORTOUTODE}(EXPRN:{\em algebraic}, Y:{\em var}, X:{\em var}): +{\em expression} +\vspace{.1in} + +\noindent which finds the order and degree of the EXPRN as a differential +equation for Y with respect to Y and sets the linearity and highest +derivative occurring in reserved variables ODEORDER, ODEDEGREE, +\ttindex{ODEORDER} \ttindex{ODEDEGREE} \ttindex{ODELINEARITY} +\ttindex{HIGHESTDERIV} +ODELINEARITY and HIGHESTDERIV. An expression equivalent to the ODE is +returned, or zero if EXPRN (equated to 0) is not an ODE in the +given vars. + +"The use of the function\ttindex{COFACTOR} + +\vspace{.1in} +\begin{tabbing} +{\tt COFACTOR}(\=ROW:{\em integer}, \\ +\>COLUMN:{\em integer}, \\ +\>MATRIX:{\em matrix}):{\em algebraic} +\end{tabbing} +\vspace{.1in} + +\noindent which uses variation of parameters, returns the cofactor of the +element in row ROW and column COLUMN of the matrix MATRIX. Errors occur +if ROW or COLUMN do not simplify to integer expressions or if MATRIX is +not square. + +\section{Tracing} + + +Some rudimentary tracing is provided and is activated by the switch TRODE +\index{tracing ! ODESOLVE} +\ttindex{TRODE} +(analogous to TRFAC and TRINT) + +\section{Comments} + +The intention in the long run is to develop a rather general and +powerful ordinary differential equation solver incorporating the +methods detailed below. At present the program has not been optimized +for efficiency and much work remains to be done to convert algebraic +mode procedures to more efficient symbolic mode replacements. + +No attempt is made to extend the REDUCE integrator, although this is +in some sense a problem of ODEs. Thus the equation $\frac{dy}{dx} = g(x)$ will +be solved if and only if $\int g(x) dx$ succeeds. + +The available and planned coverage is as follows: + +\begin{itemize} +\item First-order equations: (first degree unless otherwise stated) + +\begin{itemize} +\item Quadrature of $\frac{df}{dx} = g(x)$ +\item Linear equations +\item Separable equations +\item (Algebraically) homogeneous equations +\item Equations reducible to the previous case by linear transformations +\item Exact equations +\item Bernoulli equations +\end{itemize} + +The above are already implemented. Further 1st order cases are not: +\begin{itemize} +\item Riccati equations using Schmidt's methods and other special cases +\item Hypotheses on the integrating factor following Char (SYMSAC 81) +or Shtokhamer, Glinos and Caviness. +\item Higher degree cases +\end{itemize} +\item Linear equations of higher order +\begin{itemize} +\item Constant coefficients case for driving terms solvable by +variation of parameters using the integrator +(Choice of method is discussed in the source of module lccode). +\end{itemize} +The above is already implemented. Further higher order methods are not: +\begin{itemize} +\item More complex driving terms via Laplace transforms (?) +\item Variable coefficients: Watanabe (EUROSAM 84) methods +including Kovacic's algorithm as extended by Singer +\item Factorization of operators as in Schwarz's ISSAC-89 paper or +Berkovich's 1990 book +\item Other methods based on Galois theory (see Ulmer's preprints +from Karlsruhe, 1989, 1990 and Singer's 1989 review) or +other ways of hunting Liouvillian solutions (see Singer's +review in J. Symb. Comp., 1990). +\end{itemize} +\item Non-linear equations of order 2 and higher +\begin{itemize} +\item Lie algebra of point symmetries e.g. using Wolf's CRACK now available +in REDUCE +\item Other special ansatze (see Wolf. op. cit), in particular +contact transformations for 2nd order cases +\end{itemize} +\item Possibly (?) exploitation of Cartan's methods for equivalence of +differential equations. +\end{itemize} +\end{document} Index: r36/doc/ORTHOVEC.BIB ================================================================== --- r36/doc/ORTHOVEC.BIB +++ r36/doc/ORTHOVEC.BIB @@ -1,18 +1,18 @@ -@ARTICLE{Eastwood:87, - AUTHOR = "James W. Eastwood", - TITLE = "Orthovec: A {REDUCE} Program for {3-D} Vector Analysis -in Orthogonal Curvilinear Coordinates", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1987, VOLUME = 47, NUMBER = 1, PAGES = "139-147", MONTH = "October"} - -@ARTICLE{Eastwood:91, - AUTHOR = "James W. Eastwood", - TITLE = "{ORTHOVEC:} version 2 of the {REDUCE} program for {3-D} vector -analysis in orthogonal curvilinear coordinates", - JOURNAL = "Comp. Phys. Commun.", - YEAR = 1991, VOLUME = 64, NUMBER = 1, PAGES = "121-122", MONTH = "April"} - -@BOOK{Speigel:59, - AUTHOR = "M . Speigel", - TITLE = "Vector Analysis", - PUBLISHER = "Scheum Publishing Co.", YEAR = 1959} +@ARTICLE{Eastwood:87, + AUTHOR = "James W. Eastwood", + TITLE = "Orthovec: A {REDUCE} Program for {3-D} Vector Analysis +in Orthogonal Curvilinear Coordinates", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1987, VOLUME = 47, NUMBER = 1, PAGES = "139-147", MONTH = "October"} + +@ARTICLE{Eastwood:91, + AUTHOR = "James W. Eastwood", + TITLE = "{ORTHOVEC:} version 2 of the {REDUCE} program for {3-D} vector +analysis in orthogonal curvilinear coordinates", + JOURNAL = "Comp. Phys. Commun.", + YEAR = 1991, VOLUME = 64, NUMBER = 1, PAGES = "121-122", MONTH = "April"} + +@BOOK{Speigel:59, + AUTHOR = "M . Speigel", + TITLE = "Vector Analysis", + PUBLISHER = "Scheum Publishing Co.", YEAR = 1959} Index: r36/doc/ORTHOVEC.TEX ================================================================== --- r36/doc/ORTHOVEC.TEX +++ r36/doc/ORTHOVEC.TEX @@ -1,571 +1,571 @@ -\documentstyle[11pt,reduce]{article} -\title{ORTHOVEC: Version 2 of the REDUCE program -for 3-D vector analysis in orthogonal curvilinear coordinates} -\date{} -\author{James W.~Eastwood \\ AEA Technology \\ Culham Laboratory \\ -Abingdon \\ Oxon OX14 3DB \\[0.1in] -Email: eastwood\#jim\%nersc.mfenet@ccc.nersc.gov \\[0.1in] June 1990} -\begin{document} -\maketitle -\index{ORTHOVEC package} - -The revised version of ORTHOVEC is a collection of REDUCE 3.4 procedures and -operations which provide a simple to use environment for the manipulation of -scalars and vectors. Operations include addition, subtraction, dot and cross -products, division, modulus, div, grad, curl, laplacian, differentiation, -integration, ${\bf a \cdot \nabla}$ and Taylor expansion. Version 2 is -summarized in \cite{Eastwood:91}. It differs from the original (\cite -{Eastwood:87}) in revised notation and extended capabilities. - -%\begin{center} -%{\Large{\bf New Version Summary}} -%\end{center} -%\begin{tabular}{ll} -%\underline{Title of program}:&ORTHOVEC\\[2ex] -%\underline{Catalogue number}:&AAXY\\[2ex] -%\underline{Program obtainable from}: &CPC Program Library,\\ -%&Queen's University of Belfast, N.~Ireland\\[2ex] -%\underline{Reference to original program}: &CPC 47 (1987) 139-147\\[2ex] -%\underline{Operating system}:&UNIX, MS-DOS + ARM-OS\\[2ex] -%\underline{Programming Language used}: &REDUCE 3.4\\[2ex] -%\underline{High speed storage required}: &As for -%the underlying PSL/REDUCE \\ -%&system, typically $>$ 1 Megabyte\\[2ex] -%\underline{No. of lines in combined programs and test deck}:&600 \\[2ex] -%\underline{Keywords}: & Computer Algebra, Vector Analysis,\\ -%& series Expansion, Plasma Physics, \\ -%&Hydrodynamics, Electromagnetics.\\[2ex] -%\underline{Author of original program}: &James W. EASTWOOD\\[2ex] -%\underline{Nature of Physical Problem}: -%&There is a wide range using vector\\ -%& calculus in orthogonal curvilinear coordinates\\ -%& and vector integration, differentiation\\ -%& and series expansion.\\[2ex] -%\underline{Method of Solution}: & computer aided algebra using\\ -%&standard orthogonal curvilinear coordinates\\ -%&for differential and integral operators.\\[2ex] -%\underline{Typical running time}: -%& This is strongly problem dependent:\\ -%&the test examples given took respectively\\ -%& 10,19 and 48 seconds on a SUN 4/310,\\ -%&SUN 4/110 and ACORN Springboard. \\[2ex] -%\underline{Unusual Features of the Program}: -%&The REDUCE procedures use\\ -%&LISP vectors \cite{r2} -%to provide a compact\\ -%&mathematical notation similar\\ -%& to that normally found in vector\\ -%& analysis textbooks.\\ -%\end{tabular} - -\section{Introduction} -The revised version of ORTHOVEC\cite{Eastwood:91} is, like the -original\cite{Eastwood:87}, a collection of REDUCE procedures and -operators designed to simplify the machine aided manipulation of vectors -and vector expansions frequently met in many areas of applied mathematics. -The revisions have been introduced for two reasons: firstly, to add extra -capabilities missing from the original and secondly, to tidy up input and -output to make the package easier to use. -\newpage -The changes from Version 1 include: - -\begin{enumerate} -\item merging of scalar and vector unary and binary operators, $+, - , *, / -$ -\item extensions of the definitions of division and exponentiation -to vectors -\item new vector dependency procedures -\item application of l'H\^opital's rule in limits and Taylor expansions -\item a new component selector operator -\item algebraic mode output of LISP vector components -\end{enumerate} - -The LISP vector primitives are again used to store vectors, although -with the introduction of LIST types in algebraic mode in REDUCE -3.4, the implementation may have been more simply achieved -using lists to store vector components. - -The philosophy used in Version 2 follows that used in the original: -namely, algebraic mode is used wherever possible. The view is taken -that some computational inefficiencies are acceptable if it allows -coding to be intelligible to (and thence adaptable by) users other -than LISP experts familiar with the internal workings of REDUCE. - -Procedures and operators in ORTHOVEC fall into the five classes: -initialisation, input-output, algebraic operations, differential -operations and integral operations. Definitions are given in -the following sections, and -a summary of the procedure names and their meanings are give in Table 1. -The final section discusses test examples. - -\section{Initialisation}\label{vstart} -\ttindex{VSTART} -The procedure VSTART initialises ORTHOVEC. It may be -called after ORTHOVEC has been INputted (or LOADed if a fast load -version has been made) to reset coordinates. VSTART provides a -menu of standard coordinate systems:- - - -\begin{enumerate} -\index{cartesian coordinates} -\item cartesian $(x, y, z) = $ {\tt (x, y, z)} -\index{cylindrical coordinates} -\item cylindrical $(r, \theta, z) = $ {\tt (r, th, z)} -\index{spherical coordinates} -\item spherical $(r, \theta, \phi) = $ {\tt (r, th, ph) } -\item general $( u_1, u_2, u_3 ) = $ {\tt (u1, u2, u3) } -\item others -\end{enumerate} - -which the user selects by number. Selecting options (1)-(4) -automatically sets up the coordinates and scale factors. Selection -option (5) shows the user how to select another coordinate system. If -VSTART is not called, then the default cartesian coordinates are used. -ORTHOVEC may be re-initialised to a new coordinate system at any time -during a given REDUCE session by typing -\begin{verbatim} -VSTART $. -\end{verbatim} - -\section{Input-Output} - -ORTHOVEC assumes all quantities are either scalars or 3 component -vectors. To define a vector $a$ with components $(c_1, c_2, c_3)$ use -the procedure SVEC as follows \ttindex{SVEC} -\begin{verbatim} -a := svec(c1, c2, c3); -\end{verbatim} - -The standard REDUCE output for vectors when using the terminator ``$;$'' -is to list the three components inside square brackets -$[\cdots]$, with each component in prefix form. A replacement for the -standard REDUCE procedure MAPRIN is included in -the package to change the -output of LISP vector components to algebraic notation. The procedure -\ttindex{VOUT} VOUT (which returns the value of its argument) -can be used to give labelled output of components -in algebraic form: e.g., -\begin{verbatim} -b := svec (sin(x)**2, y**2, z)$ -vout(b)$ -\end{verbatim} - -The operator {\tt \_} can be used to select a particular -component (1, 2 or 3) for output e.g. -\begin{verbatim} -b_1 ; -\end{verbatim} - -\section{Algebraic Operations} - -Six infix operators, sum, difference, quotient, times, exponentiation -and cross product, and four prefix -operators, plus, minus, reciprocal -and modulus are defined in ORTHOVEC. These operators can take suitable -combinations of scalar and vector arguments, -and in the case of scalar arguments reduce to the usual definitions of -$ +, -, *, /, $ etc. - -The operators are represented by symbols -\index{+ ! 3-D vector} \index{- ! 3-D vector} \index{/ ! 3-D vector} -\index{* ! 3-D vector} \index{* ! 3-D vector} \index{"\^{} ! 3-D vector} -\index{$><$ ! 3-D vector} -\begin{verbatim} -+, -, /, *, ^, >< -\end{verbatim} - -\index{$><$ ! diphthong} The composite {\tt ><} is an -attempt to represent the cross product symbol -$\times$ in ASCII characters. -If we let ${\bf v}$ be a vector and $s$ be a scalar, then -valid combinations of arguments of the -procedures and operators and the type of the result -are as summarised below. The notation used is\\ -{\em result :=procedure(left argument, right argument) } or\\ -{\em result :=(left operand) operator (right operand) } . \\ - -\newpage -\underline{Vector Addition} \\ -\ttindex{VECTORPLUS} \ttindex{VECTORADD} \index{vector ! addition} -\begin{tabular}{rclcrcl} -{\bf v} &:=& VECTORPLUS({\bf v}) &{\rm or}& {\bf v} &:=& + {\bf v} \\ - s &:=& VECTORPLUS(s) &{\rm or} & s &:=& + s \\ -{\bf v} &:=& VECTORADD({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& -{\bf v} + {\bf v} \\ - s &:=& VECTORADD(s,s) &{\rm or }& s &:=& s + s \\ -\end{tabular} \\ - -\underline{Vector Subtraction} \\ -\ttindex{VECTORMINUS} \ttindex{VECTORDIFFERENCE} \index{vector ! subtraction} -\begin{tabular}{rclcrcl} -{\bf v} &:=& VECTORMINUS({\bf v}) &{\rm or}& - {\bf v} &:=& - {\bf v} \\ - s &:=& VECTORMINUS(s) &{\rm or} & s &:=& - s \\ -{\bf v} &:=& VECTORDIFFERENCE({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& - {\bf v} - {\bf v} \\ - s &:=& VECTORDIFFERENCE(s,s) &{\rm or }& s &:=& s - s \\ -\end{tabular} \\ - -\underline{Vector Division}\\ -\ttindex{VECTORRECIP} \ttindex{VECTORQUOTIENT} \index{vector ! division} -\begin{tabular}{rclcrcl} -{\bf v} &:=& VECTORRECIP({\bf v}) &{\rm or}& {\bf v} &:=& / -{\bf v} \\ - s &:=& VECTORRECIP(s) &{\rm or} & s &:=& / s \\ -{\bf v} &:=& VECTORQUOTIENT({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& -{\bf v} / {\bf v} \\ -{\bf v} &:=& VECTORQUOTIENT({\bf v}, s ) &{\rm or }& {\bf v} &:=& -{\bf v} / s \\ -{\bf v} &:=& VECTORQUOTIENT( s ,{\bf v}) &{\rm or }& {\bf v} &:=& - s / {\bf v} \\ - s &:=& VECTORQUOTIENT(s,s) &{\rm or }& s &:=& s / s - \\ -\end{tabular} \\ - -\underline{Vector Multiplication}\\ -\ttindex{VECTORTIMES} \index{vector ! multiplication} -\begin{tabular}{rclcrcl} -{\bf v} &:=& VECTORTIMES( s ,{\bf v}) &{\rm or }& {\bf v} &:=& -s * {\bf v} \\ -{\bf v} &:=& VECTORTIMES({\bf v}, s ) &{\rm or }& {\bf v} &:=& {\bf - v} * s \\ - s &:=& VECTORTIMES({\bf v},{\bf v}) &{\rm or }& s &:=& {\bf - v} * {\bf v} \\ - s &:=& VECTORTIMES( s , s ) &{\rm or }& s &:=& -s * s \\ -\end{tabular} \\ - -\underline{Vector Cross Product} \\ -\ttindex{VECTORCROSS} \index{cross product} \index{vector ! cross product} -\begin{tabular}{rclcrcl} -{\bf v} &:=& VECTORCROSS({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& {\bf - v} $\times$ {\bf v} \\ -\end{tabular} \\ - -\underline{Vector Exponentiation}\\ -\ttindex{VECTOREXPT} \index{vector ! exponentiation} -\begin{tabular}{rclcrcl} - s &:=& VECTOREXPT ({\bf v}, s ) &{\rm or }& s &:=& {\bf - v} \^{} s \\ - s &:=& VECTOREXPT ( s , s ) &{\rm or }& s &:=& s - \^{} s \\ -\end{tabular} \\ - -\underline{Vector Modulus}\\ -\ttindex{VMOD} \index{vector ! modulus} -\begin{tabular}{rcl} - s &:=& VMOD (s)\\ - s &:=& VMOD ({\bf v}) \\ -\end{tabular} \\ - -All other combinations of operands for these operators lead to error -messages being issued. The first two instances of vector -multiplication are scalar multiplication of vectors, the third is the -\index{vector ! dot product} \index{vector ! inner product} -\index{inner product} \index{dot product} -product of two scalars and the last is the inner (dot) product. The -prefix operators {\tt +, -, /} can take either scalar or vector -arguments and return results of the same type as their arguments. -VMOD returns a scalar. - -In compound expressions, parentheses may be used to specify the order of -combination. If parentheses are omitted the ordering of the -operators, in increasing order of precedence is -\begin{verbatim} -+ | - | dotgrad | * | >< | ^ | _ -\end{verbatim} -and these are placed in the precedence list defined in REDUCE -after $<$. -The differential operator DOTGRAD is defined in the \index{DOTGRAD operator} -following section, and the component selector {\tt \_} was introduced in -section 3. - -Vector divisions are defined as follows: If ${\bf a}$ and ${\bf b}$ are -vectors and $c$ is a scalar, then -\begin{eqnarray*} -{\bf a} / {\bf b} & = & \frac{{\bf a} \cdot {\bf b}}{ \mid {\bf b} -\mid^2}\\ -c / {\bf a} & = & \frac{c {\bf a} }{ \mid {\bf a} \mid^2} -\end{eqnarray*} - -Both scalar multiplication and dot products are given by the same symbol, -braces are advisable to ensure the correct -precedences in expressions such as $({\bf a} \cdot {\bf b}) -({\bf c} \cdot {\bf d})$. - -Vector exponentiation is defined as the power of the modulus:\\ -${\bf a}^n \equiv {\rm VMOD}(a)^n = \mid {\bf a} \mid^n$ - -\section{Differential Operations} -Differential operators provided are div, grad, curl, delsq, and dotgrad. -\index{div operator} \index{grad operator} \index{curl operator} -\index{delsq operator} \index{dotgrad operator} -All but the last of these are prefix operators having a single -vector or scalar argument as appropriate. Valid combinations of -operator and argument, and the type of the result are shown in table~\ref{vvecttable}. - - -\begin{table} -\begin{center} -\begin{tabular}{rcl} -s & := & div ({\bf v}) \\ -{\bf v} & := & grad(s) \\ -{\bf v} & := & curl({\bf v}) \\ -{\bf v} & := & delsq({\bf v}) \\ - s & := & delsq(s) \\ -{\bf v} & := & {\bf v} dotgrad {\bf v} \\ - s & := & {\bf v} dotgrad s -\end{tabular} -\end{center} -\caption{ORTHOVEC valid combinations of operator and argument}\label{vvecttable} -\end{table} - -All other combinations of operator and argument type cause error -messages to be issued. The differential operators have their usual -meanings~\cite{Speigel:59}. The coordinate system used by these operators is -set by invoking VSTART (cf. Sec.~\ref{vstart}). The names {\tt h1}, -{\tt h2} and {\tt h3 } are -reserved for the scale factors, and {\tt u1}, {\tt u2} and {\tt u3} are -used for the coordinates. - -A vector extension, VDF, of the REDUCE procedure DF allows the -differentiation of a vector (scalar) with respect to a scalar to be -performed. Allowed forms are \ttindex{VDF} -VDF({\bf v}, s) $\rightarrow$ {\bf v} and -VDF(s, s) $\rightarrow$ s , -where, for example\\ -\begin{eqnarray*} -{\tt vdf( B,x)} \equiv \frac{\partial {\bf B}}{\partial x} -\end{eqnarray*} - -The standard REDUCE procedures DEPEND and NODEPEND have been redefined -to allow dependences of vectors to be compactly -defined. For example \index{DEPEND statement} \index{NODEPEND statement} -\begin{verbatim} -a := svec(a1,a2,a3)$; -depend a,x,y; -\end{verbatim} -causes all three components {\tt a1},{\tt a2} and {\tt a3} of {\tt a} -to be treated as functions of {\tt x} and {\tt y}. -Individual component dependences can still be defined if desired. -\begin{verbatim} -depend a3,z; -\end{verbatim} - -The procedure VTAYLOR gives truncated Taylor series expansions of scalar -or vector functions:- \ttindex{VTAYLOR} -\begin{verbatim} -vtaylor(vex,vx,vpt,vorder); -\end{verbatim} -returns the series expansion of the expression -VEX with respect to variable VX \ttindex{VORDER} -about point VPT to order VORDER. Valid -combinations of argument types are shown in table~\ref{ORTHOVEC:validexp}. \\ - -\begin{table} -\begin{center} -\begin{tabular}{cccc} -VEX & VX & VPT & VORDER \\[2ex] -{\bf v} & {\bf v} & {\bf v} & {\bf v}\\ -{\bf v} & {\bf v} & {\bf v} & s\\ -{\bf v} & s & s & s \\ -s & {\bf v} & {\bf v} & {\bf v} \\ -s & {\bf v} & {\bf v} & s\\ -s & s & s & s\\ -\end{tabular} -\end{center} -\caption{ORTHOVEC valid combination of argument types.}\label{ORTHOVEC:validexp} -\end{table} - -Any other combinations cause error messages to be issued. Elements of -VORDER must be non-negative integers, otherwise error messages are -issued. If scalar VORDER is given for a vector expansion, expansions -in each component are truncated at the same order, VORDER. - -The new version of Taylor expansion applies \index{l'H\^opital's rule} -l'H\^opital's rule in evaluating coefficients, so handle cases such as -$\sin(x) / (x) $ , etc. which the original version of ORTHOVEC could -not. The procedure used for this is LIMIT, \ttindex{LIMIT} which can -be used directly to find the limit of a scalar function {\tt ex} of -variable {\tt x} at point {\tt pt}:- - -\begin{verbatim} -ans := limit(ex,x,pt); -\end{verbatim} - -\section{Integral Operations} -Definite and indefinite vector, volume and scalar line integration -procedures are included in ORTHOVEC. They are defined as follows: -\ttindex{VINT} \ttindex{DVINT} -\ttindex{VOLINT} \ttindex{DVOLINT} \ttindex{LINEINT} \ttindex{DLINEINT} -\begin{eqnarray*} -{\rm VINT} ({\bf v},x) & = & \int {\bf v}(x)dx\\ -% -{\rm DVINT} ({\bf v},x, a, b) & = & \int^b_a {\bf v} (x) dx\\ -% -{\rm VOLINT} ({\bf v}) & = & \int {\bf v} h_1 h_2 h_3 du_1 du_2 du_3\\ -% -{\rm DVOLINT}({\bf v},{\bf l},{\bf u},n) & = & \int^{\bf u}_{\bf l} -{\bf v} h_1 h_2 h_3 du_1 du_2 du_3\\ -% -{\rm LINEINT} ({\bf v, \omega}, t) & = & \int {\bf v} \cdot {\bf dr} -\equiv \int v_i h_i \frac{\partial \omega_i}{\partial t} dt\\ -% -{\rm DLINEINT} ({\bf v, \omega} t, a, b) & = & \int^b_a v_i h_i -\frac{\partial \omega_i}{\partial t} dt\\ -\end{eqnarray*} - -In the vector and volume integrals, ${\bf v}$ are vector or scalar, -$a, b,x$ and $n$ are scalar. Vectors ${\bf l}$ and ${\bf u}$ contain -expressions for lower and upper bounds to the integrals. The integer -index $n$ defines the order in which the integrals over $u_1, u_2$ and -$u_3$ are performed in order to allow for functional dependencies in -the integral bounds: - -\begin{center} -\begin{tabular}{ll} -n & order\\ 1 & $u_1~u_2~u_3$\\ -% -2 & $u_3~u_1~u_2$\\ -% -3 & $u_2~u_3~u_1$\\ -% -4 & $u_1~u_3~u_2$\\ -% -5 & $u_2~u_1~u_3$\\ otherwise & $u_3~u_2~u_1$\\ -\end{tabular} -\end{center} - - -The vector ${\bf \omega}$ in the line integral's arguments contain -explicit paramterisation of the coordinates $u_1, u_2, u_3$ of the -line ${\bf u}(t)$ along which the integral is taken. - -\begin{table} -\begin{center} -\begin{tabular}{|l c l|} \hline -\multicolumn{1}{|c}{Procedures} & & \multicolumn{1}{c|}{Description} \\ \hline -VSTART & & select coordinate -system \\ & & \\ SVEC & & set up a vector \\ VOUT & & output a vector -\\ VECTORCOMPONENT & \_ & extract a vector component (1-3) \\ & & \\ -VECTORADD & + & add two vectors or scalars \\ -VECTORPLUS & + & unary vector or scalar plus\\ -VECTORMINUS & - & unary vector or scalar minus\\ -VECTORDIFFERENCE & - & subtract two vectors or scalars \\ -VECTORQUOTIENT & / & vector divided by scalar \\ -VECTORRECIP & / & unary vector or scalar division \\ & & \ \ \ (reciprocal)\\ -VECTORTIMES & * & multiply vector or scalar by \\ & & \ \ \ vector/scalar \\ -VECTORCROSS & $><$ & cross product of two vectors \\ -VECTOREXPT & \^{} & exponentiate vector modulus or scalar \\ -VMOD & & length of vector or scalar \\ \hline -\end{tabular} -\end{center} -\caption{Procedures names and operators used in ORTHOVEC (part 1)} -\end{table} - -\begin{table} -\begin{center} -\begin{tabular}{|l l|} \hline -\multicolumn{1}{|c}{Procedures} & \multicolumn{1}{c|}{Description} \\ \hline -DIV & divergence of vector \\ -GRAD & gradient of scalar \\ -CURL & curl of vector \\ -DELSQ & laplacian of scalar or vector \\ -DOTGRAD & (vector).grad(scalar or vector) \\ & \\ -VTAYLOR & vector or scalar Taylor series of vector or scalar \\ -VPTAYLOR & vector or scalar Taylor series of scalar \\ -TAYLOR & scalar Taylor series of scalar \\ -LIMIT & limit of quotient using l'H\^opital's rule \\ & \\ -VINT & vector integral \\ -DVINT & definite vector integral \\ -VOLINT & volume integral \\ -DVOLINT & definite volume integral \\ -LINEINT & line integral \\ -DLINEINT & definite line integral \\ & \\ -MAPRIN & vector extension of REDUCE MAPRIN \\ -DEPEND & vector extension of REDUCE DEPEND \\ -NODEPEND & vector extension of REDUCE NODEPEND \\ \hline -\end{tabular} -\end{center} -\caption{Procedures names and operators used in ORTHOVEC (part 2)} -\end{table} - - -\section{Test Cases} - -To use the REDUCE source version of ORTHOVEC, initiate a REDUCE -session and then IN the file {\em orthovec.red} containing ORTHOVEC. -However, it is recommended that for efficiency a compiled fast loading -version be made and LOADed when required (see Sec.~18 of the REDUCE -manual). If coordinate dependent differential and integral operators -other than cartesian are needed, then VSTART must be used to reset -coordinates and scale factors. - -Six simple examples are given in the Test Run Output file -{\em orthovectest.log} to illustrate the working of ORTHOVEC. -The input lines were taken from the file -{\em orthovectest.red} (the Test Run Input), but could -equally well be typed in at the Terminal. - -\example\index{ORTHOVEC package ! example} - -Show that -\begin{eqnarray*} -({\bf a} \times {\bf b}) \cdot ({\bf c} \times {\bf d}) - ({\bf a} -\cdot {\bf c})({\bf b} \cdot {\bf d}) - + ({\bf a} \cdot {\bf d})({\bf b} \cdot {\bf c}) \equiv 0 -\end{eqnarray*} - -\example\index{ORTHOVEC package ! example}\label{ORTHOVEC:eqm} - -Write the equation of motion -\begin{eqnarray*} -\frac{\partial {\bf v}}{\partial t} + {\bf v} \cdot {\bf \nabla v} -+ {\bf \nabla} p - curl ({\bf B}) \times {\bf B} -\end{eqnarray*} -in cylindrical coordinates. - -\example\index{ORTHOVEC package ! example}\label{ORTHOVEC:taylor} - -Taylor expand -\begin{itemize} -\item $\sin(x) \cos(y) +e^z$ -about the point $(0,0,0)$ to third order in $x$, fourth order in $y$ and -fifth order in $z$. - -\item $\sin(x)/x$ about $x$ to fifth order. - -\item ${\bf v}$ about ${\bf x}=(x,y,z)$ to fifth order, where -${\bf v} = (x/ \sin(x),(e^y-1)/y,(1+z)^{10})$. -\end{itemize} - -\example\index{ORTHOVEC package ! example} - -Obtain the second component of the equation of motion in -example~\ref{ORTHOVEC:eqm}, and the first component of the final -vector Taylor series in example~\ref{ORTHOVEC:taylor}. - -\example\index{ORTHOVEC package ! example} - -Evaluate the line integral -\begin{eqnarray*} -\int^{{\bf r}_2}_{{\bf r}_1} {\bf A} \cdot d{\bf r} -\end{eqnarray*} -from point ${\bf r}_1 = (1,1,1)$ to point -${\bf r}_2 = (2,4,8)$ along the path $(x,y,z) = (s, s^2, s^3)$ where\\ -\begin{eqnarray*} -{\bf A} = (3x^2 + 5y) {\bf i} - 12xy{\bf j} + 2xyz^2{\bf k} -\end{eqnarray*} -and $({\bf i, j, k})$ are unit vectors in the ($x,y,z$) directions. - -\example\index{ORTHOVEC package ! example} - -Find the volume $V$ common to the intersecting cylinders $x^2 + y^2 -= r^2$ and $x^2 + z^2 = r^2$ i.e. evaluate -\begin{eqnarray*} -V = 8 \int^r_0 dx \int^{ub}_0 dy \int^{ub}_0 dz -\end{eqnarray*} -where $ub = \overline{\sqrt { r^2 - x^2}}$ -\bibliography{orthovec} -\bibliographystyle{plain} -\end{document} +\documentstyle[11pt,reduce]{article} +\title{ORTHOVEC: Version 2 of the REDUCE program +for 3-D vector analysis in orthogonal curvilinear coordinates} +\date{} +\author{James W.~Eastwood \\ AEA Technology \\ Culham Laboratory \\ +Abingdon \\ Oxon OX14 3DB \\[0.1in] +Email: eastwood\#jim\%nersc.mfenet@ccc.nersc.gov \\[0.1in] June 1990} +\begin{document} +\maketitle +\index{ORTHOVEC package} + +The revised version of ORTHOVEC is a collection of REDUCE 3.4 procedures and +operations which provide a simple to use environment for the manipulation of +scalars and vectors. Operations include addition, subtraction, dot and cross +products, division, modulus, div, grad, curl, laplacian, differentiation, +integration, ${\bf a \cdot \nabla}$ and Taylor expansion. Version 2 is +summarized in \cite{Eastwood:91}. It differs from the original (\cite +{Eastwood:87}) in revised notation and extended capabilities. + +%\begin{center} +%{\Large{\bf New Version Summary}} +%\end{center} +%\begin{tabular}{ll} +%\underline{Title of program}:&ORTHOVEC\\[2ex] +%\underline{Catalogue number}:&AAXY\\[2ex] +%\underline{Program obtainable from}: &CPC Program Library,\\ +%&Queen's University of Belfast, N.~Ireland\\[2ex] +%\underline{Reference to original program}: &CPC 47 (1987) 139-147\\[2ex] +%\underline{Operating system}:&UNIX, MS-DOS + ARM-OS\\[2ex] +%\underline{Programming Language used}: &REDUCE 3.4\\[2ex] +%\underline{High speed storage required}: &As for +%the underlying PSL/REDUCE \\ +%&system, typically $>$ 1 Megabyte\\[2ex] +%\underline{No. of lines in combined programs and test deck}:&600 \\[2ex] +%\underline{Keywords}: & Computer Algebra, Vector Analysis,\\ +%& series Expansion, Plasma Physics, \\ +%&Hydrodynamics, Electromagnetics.\\[2ex] +%\underline{Author of original program}: &James W. EASTWOOD\\[2ex] +%\underline{Nature of Physical Problem}: +%&There is a wide range using vector\\ +%& calculus in orthogonal curvilinear coordinates\\ +%& and vector integration, differentiation\\ +%& and series expansion.\\[2ex] +%\underline{Method of Solution}: & computer aided algebra using\\ +%&standard orthogonal curvilinear coordinates\\ +%&for differential and integral operators.\\[2ex] +%\underline{Typical running time}: +%& This is strongly problem dependent:\\ +%&the test examples given took respectively\\ +%& 10,19 and 48 seconds on a SUN 4/310,\\ +%&SUN 4/110 and ACORN Springboard. \\[2ex] +%\underline{Unusual Features of the Program}: +%&The REDUCE procedures use\\ +%&LISP vectors \cite{r2} +%to provide a compact\\ +%&mathematical notation similar\\ +%& to that normally found in vector\\ +%& analysis textbooks.\\ +%\end{tabular} + +\section{Introduction} +The revised version of ORTHOVEC\cite{Eastwood:91} is, like the +original\cite{Eastwood:87}, a collection of REDUCE procedures and +operators designed to simplify the machine aided manipulation of vectors +and vector expansions frequently met in many areas of applied mathematics. +The revisions have been introduced for two reasons: firstly, to add extra +capabilities missing from the original and secondly, to tidy up input and +output to make the package easier to use. +\newpage +The changes from Version 1 include: + +\begin{enumerate} +\item merging of scalar and vector unary and binary operators, $+, - , *, / +$ +\item extensions of the definitions of division and exponentiation +to vectors +\item new vector dependency procedures +\item application of l'H\^opital's rule in limits and Taylor expansions +\item a new component selector operator +\item algebraic mode output of LISP vector components +\end{enumerate} + +The LISP vector primitives are again used to store vectors, although +with the introduction of LIST types in algebraic mode in REDUCE +3.4, the implementation may have been more simply achieved +using lists to store vector components. + +The philosophy used in Version 2 follows that used in the original: +namely, algebraic mode is used wherever possible. The view is taken +that some computational inefficiencies are acceptable if it allows +coding to be intelligible to (and thence adaptable by) users other +than LISP experts familiar with the internal workings of REDUCE. + +Procedures and operators in ORTHOVEC fall into the five classes: +initialisation, input-output, algebraic operations, differential +operations and integral operations. Definitions are given in +the following sections, and +a summary of the procedure names and their meanings are give in Table 1. +The final section discusses test examples. + +\section{Initialisation}\label{vstart} +\ttindex{VSTART} +The procedure VSTART initialises ORTHOVEC. It may be +called after ORTHOVEC has been INputted (or LOADed if a fast load +version has been made) to reset coordinates. VSTART provides a +menu of standard coordinate systems:- + + +\begin{enumerate} +\index{cartesian coordinates} +\item cartesian $(x, y, z) = $ {\tt (x, y, z)} +\index{cylindrical coordinates} +\item cylindrical $(r, \theta, z) = $ {\tt (r, th, z)} +\index{spherical coordinates} +\item spherical $(r, \theta, \phi) = $ {\tt (r, th, ph) } +\item general $( u_1, u_2, u_3 ) = $ {\tt (u1, u2, u3) } +\item others +\end{enumerate} + +which the user selects by number. Selecting options (1)-(4) +automatically sets up the coordinates and scale factors. Selection +option (5) shows the user how to select another coordinate system. If +VSTART is not called, then the default cartesian coordinates are used. +ORTHOVEC may be re-initialised to a new coordinate system at any time +during a given REDUCE session by typing +\begin{verbatim} +VSTART $. +\end{verbatim} + +\section{Input-Output} + +ORTHOVEC assumes all quantities are either scalars or 3 component +vectors. To define a vector $a$ with components $(c_1, c_2, c_3)$ use +the procedure SVEC as follows \ttindex{SVEC} +\begin{verbatim} +a := svec(c1, c2, c3); +\end{verbatim} + +The standard REDUCE output for vectors when using the terminator ``$;$'' +is to list the three components inside square brackets +$[\cdots]$, with each component in prefix form. A replacement for the +standard REDUCE procedure MAPRIN is included in +the package to change the +output of LISP vector components to algebraic notation. The procedure +\ttindex{VOUT} VOUT (which returns the value of its argument) +can be used to give labelled output of components +in algebraic form: e.g., +\begin{verbatim} +b := svec (sin(x)**2, y**2, z)$ +vout(b)$ +\end{verbatim} + +The operator {\tt \_} can be used to select a particular +component (1, 2 or 3) for output e.g. +\begin{verbatim} +b_1 ; +\end{verbatim} + +\section{Algebraic Operations} + +Six infix operators, sum, difference, quotient, times, exponentiation +and cross product, and four prefix +operators, plus, minus, reciprocal +and modulus are defined in ORTHOVEC. These operators can take suitable +combinations of scalar and vector arguments, +and in the case of scalar arguments reduce to the usual definitions of +$ +, -, *, /, $ etc. + +The operators are represented by symbols +\index{+ ! 3-D vector} \index{- ! 3-D vector} \index{/ ! 3-D vector} +\index{* ! 3-D vector} \index{* ! 3-D vector} \index{"\^{} ! 3-D vector} +\index{$><$ ! 3-D vector} +\begin{verbatim} ++, -, /, *, ^, >< +\end{verbatim} + +\index{$><$ ! diphthong} The composite {\tt ><} is an +attempt to represent the cross product symbol +$\times$ in ASCII characters. +If we let ${\bf v}$ be a vector and $s$ be a scalar, then +valid combinations of arguments of the +procedures and operators and the type of the result +are as summarised below. The notation used is\\ +{\em result :=procedure(left argument, right argument) } or\\ +{\em result :=(left operand) operator (right operand) } . \\ + +\newpage +\underline{Vector Addition} \\ +\ttindex{VECTORPLUS} \ttindex{VECTORADD} \index{vector ! addition} +\begin{tabular}{rclcrcl} +{\bf v} &:=& VECTORPLUS({\bf v}) &{\rm or}& {\bf v} &:=& + {\bf v} \\ + s &:=& VECTORPLUS(s) &{\rm or} & s &:=& + s \\ +{\bf v} &:=& VECTORADD({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& +{\bf v} + {\bf v} \\ + s &:=& VECTORADD(s,s) &{\rm or }& s &:=& s + s \\ +\end{tabular} \\ + +\underline{Vector Subtraction} \\ +\ttindex{VECTORMINUS} \ttindex{VECTORDIFFERENCE} \index{vector ! subtraction} +\begin{tabular}{rclcrcl} +{\bf v} &:=& VECTORMINUS({\bf v}) &{\rm or}& + {\bf v} &:=& - {\bf v} \\ + s &:=& VECTORMINUS(s) &{\rm or} & s &:=& - s \\ +{\bf v} &:=& VECTORDIFFERENCE({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& + {\bf v} - {\bf v} \\ + s &:=& VECTORDIFFERENCE(s,s) &{\rm or }& s &:=& s - s \\ +\end{tabular} \\ + +\underline{Vector Division}\\ +\ttindex{VECTORRECIP} \ttindex{VECTORQUOTIENT} \index{vector ! division} +\begin{tabular}{rclcrcl} +{\bf v} &:=& VECTORRECIP({\bf v}) &{\rm or}& {\bf v} &:=& / +{\bf v} \\ + s &:=& VECTORRECIP(s) &{\rm or} & s &:=& / s \\ +{\bf v} &:=& VECTORQUOTIENT({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& +{\bf v} / {\bf v} \\ +{\bf v} &:=& VECTORQUOTIENT({\bf v}, s ) &{\rm or }& {\bf v} &:=& +{\bf v} / s \\ +{\bf v} &:=& VECTORQUOTIENT( s ,{\bf v}) &{\rm or }& {\bf v} &:=& + s / {\bf v} \\ + s &:=& VECTORQUOTIENT(s,s) &{\rm or }& s &:=& s / s + \\ +\end{tabular} \\ + +\underline{Vector Multiplication}\\ +\ttindex{VECTORTIMES} \index{vector ! multiplication} +\begin{tabular}{rclcrcl} +{\bf v} &:=& VECTORTIMES( s ,{\bf v}) &{\rm or }& {\bf v} &:=& +s * {\bf v} \\ +{\bf v} &:=& VECTORTIMES({\bf v}, s ) &{\rm or }& {\bf v} &:=& {\bf + v} * s \\ + s &:=& VECTORTIMES({\bf v},{\bf v}) &{\rm or }& s &:=& {\bf + v} * {\bf v} \\ + s &:=& VECTORTIMES( s , s ) &{\rm or }& s &:=& +s * s \\ +\end{tabular} \\ + +\underline{Vector Cross Product} \\ +\ttindex{VECTORCROSS} \index{cross product} \index{vector ! cross product} +\begin{tabular}{rclcrcl} +{\bf v} &:=& VECTORCROSS({\bf v},{\bf v}) &{\rm or }& {\bf v} &:=& {\bf + v} $\times$ {\bf v} \\ +\end{tabular} \\ + +\underline{Vector Exponentiation}\\ +\ttindex{VECTOREXPT} \index{vector ! exponentiation} +\begin{tabular}{rclcrcl} + s &:=& VECTOREXPT ({\bf v}, s ) &{\rm or }& s &:=& {\bf + v} \^{} s \\ + s &:=& VECTOREXPT ( s , s ) &{\rm or }& s &:=& s + \^{} s \\ +\end{tabular} \\ + +\underline{Vector Modulus}\\ +\ttindex{VMOD} \index{vector ! modulus} +\begin{tabular}{rcl} + s &:=& VMOD (s)\\ + s &:=& VMOD ({\bf v}) \\ +\end{tabular} \\ + +All other combinations of operands for these operators lead to error +messages being issued. The first two instances of vector +multiplication are scalar multiplication of vectors, the third is the +\index{vector ! dot product} \index{vector ! inner product} +\index{inner product} \index{dot product} +product of two scalars and the last is the inner (dot) product. The +prefix operators {\tt +, -, /} can take either scalar or vector +arguments and return results of the same type as their arguments. +VMOD returns a scalar. + +In compound expressions, parentheses may be used to specify the order of +combination. If parentheses are omitted the ordering of the +operators, in increasing order of precedence is +\begin{verbatim} ++ | - | dotgrad | * | >< | ^ | _ +\end{verbatim} +and these are placed in the precedence list defined in REDUCE +after $<$. +The differential operator DOTGRAD is defined in the \index{DOTGRAD operator} +following section, and the component selector {\tt \_} was introduced in +section 3. + +Vector divisions are defined as follows: If ${\bf a}$ and ${\bf b}$ are +vectors and $c$ is a scalar, then +\begin{eqnarray*} +{\bf a} / {\bf b} & = & \frac{{\bf a} \cdot {\bf b}}{ \mid {\bf b} +\mid^2}\\ +c / {\bf a} & = & \frac{c {\bf a} }{ \mid {\bf a} \mid^2} +\end{eqnarray*} + +Both scalar multiplication and dot products are given by the same symbol, +braces are advisable to ensure the correct +precedences in expressions such as $({\bf a} \cdot {\bf b}) +({\bf c} \cdot {\bf d})$. + +Vector exponentiation is defined as the power of the modulus:\\ +${\bf a}^n \equiv {\rm VMOD}(a)^n = \mid {\bf a} \mid^n$ + +\section{Differential Operations} +Differential operators provided are div, grad, curl, delsq, and dotgrad. +\index{div operator} \index{grad operator} \index{curl operator} +\index{delsq operator} \index{dotgrad operator} +All but the last of these are prefix operators having a single +vector or scalar argument as appropriate. Valid combinations of +operator and argument, and the type of the result are shown in table~\ref{vvecttable}. + + +\begin{table} +\begin{center} +\begin{tabular}{rcl} +s & := & div ({\bf v}) \\ +{\bf v} & := & grad(s) \\ +{\bf v} & := & curl({\bf v}) \\ +{\bf v} & := & delsq({\bf v}) \\ + s & := & delsq(s) \\ +{\bf v} & := & {\bf v} dotgrad {\bf v} \\ + s & := & {\bf v} dotgrad s +\end{tabular} +\end{center} +\caption{ORTHOVEC valid combinations of operator and argument}\label{vvecttable} +\end{table} + +All other combinations of operator and argument type cause error +messages to be issued. The differential operators have their usual +meanings~\cite{Speigel:59}. The coordinate system used by these operators is +set by invoking VSTART (cf. Sec.~\ref{vstart}). The names {\tt h1}, +{\tt h2} and {\tt h3 } are +reserved for the scale factors, and {\tt u1}, {\tt u2} and {\tt u3} are +used for the coordinates. + +A vector extension, VDF, of the REDUCE procedure DF allows the +differentiation of a vector (scalar) with respect to a scalar to be +performed. Allowed forms are \ttindex{VDF} +VDF({\bf v}, s) $\rightarrow$ {\bf v} and +VDF(s, s) $\rightarrow$ s , +where, for example\\ +\begin{eqnarray*} +{\tt vdf( B,x)} \equiv \frac{\partial {\bf B}}{\partial x} +\end{eqnarray*} + +The standard REDUCE procedures DEPEND and NODEPEND have been redefined +to allow dependences of vectors to be compactly +defined. For example \index{DEPEND statement} \index{NODEPEND statement} +\begin{verbatim} +a := svec(a1,a2,a3)$; +depend a,x,y; +\end{verbatim} +causes all three components {\tt a1},{\tt a2} and {\tt a3} of {\tt a} +to be treated as functions of {\tt x} and {\tt y}. +Individual component dependences can still be defined if desired. +\begin{verbatim} +depend a3,z; +\end{verbatim} + +The procedure VTAYLOR gives truncated Taylor series expansions of scalar +or vector functions:- \ttindex{VTAYLOR} +\begin{verbatim} +vtaylor(vex,vx,vpt,vorder); +\end{verbatim} +returns the series expansion of the expression +VEX with respect to variable VX \ttindex{VORDER} +about point VPT to order VORDER. Valid +combinations of argument types are shown in table~\ref{ORTHOVEC:validexp}. \\ + +\begin{table} +\begin{center} +\begin{tabular}{cccc} +VEX & VX & VPT & VORDER \\[2ex] +{\bf v} & {\bf v} & {\bf v} & {\bf v}\\ +{\bf v} & {\bf v} & {\bf v} & s\\ +{\bf v} & s & s & s \\ +s & {\bf v} & {\bf v} & {\bf v} \\ +s & {\bf v} & {\bf v} & s\\ +s & s & s & s\\ +\end{tabular} +\end{center} +\caption{ORTHOVEC valid combination of argument types.}\label{ORTHOVEC:validexp} +\end{table} + +Any other combinations cause error messages to be issued. Elements of +VORDER must be non-negative integers, otherwise error messages are +issued. If scalar VORDER is given for a vector expansion, expansions +in each component are truncated at the same order, VORDER. + +The new version of Taylor expansion applies \index{l'H\^opital's rule} +l'H\^opital's rule in evaluating coefficients, so handle cases such as +$\sin(x) / (x) $ , etc. which the original version of ORTHOVEC could +not. The procedure used for this is LIMIT, \ttindex{LIMIT} which can +be used directly to find the limit of a scalar function {\tt ex} of +variable {\tt x} at point {\tt pt}:- + +\begin{verbatim} +ans := limit(ex,x,pt); +\end{verbatim} + +\section{Integral Operations} +Definite and indefinite vector, volume and scalar line integration +procedures are included in ORTHOVEC. They are defined as follows: +\ttindex{VINT} \ttindex{DVINT} +\ttindex{VOLINT} \ttindex{DVOLINT} \ttindex{LINEINT} \ttindex{DLINEINT} +\begin{eqnarray*} +{\rm VINT} ({\bf v},x) & = & \int {\bf v}(x)dx\\ +% +{\rm DVINT} ({\bf v},x, a, b) & = & \int^b_a {\bf v} (x) dx\\ +% +{\rm VOLINT} ({\bf v}) & = & \int {\bf v} h_1 h_2 h_3 du_1 du_2 du_3\\ +% +{\rm DVOLINT}({\bf v},{\bf l},{\bf u},n) & = & \int^{\bf u}_{\bf l} +{\bf v} h_1 h_2 h_3 du_1 du_2 du_3\\ +% +{\rm LINEINT} ({\bf v, \omega}, t) & = & \int {\bf v} \cdot {\bf dr} +\equiv \int v_i h_i \frac{\partial \omega_i}{\partial t} dt\\ +% +{\rm DLINEINT} ({\bf v, \omega} t, a, b) & = & \int^b_a v_i h_i +\frac{\partial \omega_i}{\partial t} dt\\ +\end{eqnarray*} + +In the vector and volume integrals, ${\bf v}$ are vector or scalar, +$a, b,x$ and $n$ are scalar. Vectors ${\bf l}$ and ${\bf u}$ contain +expressions for lower and upper bounds to the integrals. The integer +index $n$ defines the order in which the integrals over $u_1, u_2$ and +$u_3$ are performed in order to allow for functional dependencies in +the integral bounds: + +\begin{center} +\begin{tabular}{ll} +n & order\\ 1 & $u_1~u_2~u_3$\\ +% +2 & $u_3~u_1~u_2$\\ +% +3 & $u_2~u_3~u_1$\\ +% +4 & $u_1~u_3~u_2$\\ +% +5 & $u_2~u_1~u_3$\\ otherwise & $u_3~u_2~u_1$\\ +\end{tabular} +\end{center} + + +The vector ${\bf \omega}$ in the line integral's arguments contain +explicit paramterisation of the coordinates $u_1, u_2, u_3$ of the +line ${\bf u}(t)$ along which the integral is taken. + +\begin{table} +\begin{center} +\begin{tabular}{|l c l|} \hline +\multicolumn{1}{|c}{Procedures} & & \multicolumn{1}{c|}{Description} \\ \hline +VSTART & & select coordinate +system \\ & & \\ SVEC & & set up a vector \\ VOUT & & output a vector +\\ VECTORCOMPONENT & \_ & extract a vector component (1-3) \\ & & \\ +VECTORADD & + & add two vectors or scalars \\ +VECTORPLUS & + & unary vector or scalar plus\\ +VECTORMINUS & - & unary vector or scalar minus\\ +VECTORDIFFERENCE & - & subtract two vectors or scalars \\ +VECTORQUOTIENT & / & vector divided by scalar \\ +VECTORRECIP & / & unary vector or scalar division \\ & & \ \ \ (reciprocal)\\ +VECTORTIMES & * & multiply vector or scalar by \\ & & \ \ \ vector/scalar \\ +VECTORCROSS & $><$ & cross product of two vectors \\ +VECTOREXPT & \^{} & exponentiate vector modulus or scalar \\ +VMOD & & length of vector or scalar \\ \hline +\end{tabular} +\end{center} +\caption{Procedures names and operators used in ORTHOVEC (part 1)} +\end{table} + +\begin{table} +\begin{center} +\begin{tabular}{|l l|} \hline +\multicolumn{1}{|c}{Procedures} & \multicolumn{1}{c|}{Description} \\ \hline +DIV & divergence of vector \\ +GRAD & gradient of scalar \\ +CURL & curl of vector \\ +DELSQ & laplacian of scalar or vector \\ +DOTGRAD & (vector).grad(scalar or vector) \\ & \\ +VTAYLOR & vector or scalar Taylor series of vector or scalar \\ +VPTAYLOR & vector or scalar Taylor series of scalar \\ +TAYLOR & scalar Taylor series of scalar \\ +LIMIT & limit of quotient using l'H\^opital's rule \\ & \\ +VINT & vector integral \\ +DVINT & definite vector integral \\ +VOLINT & volume integral \\ +DVOLINT & definite volume integral \\ +LINEINT & line integral \\ +DLINEINT & definite line integral \\ & \\ +MAPRIN & vector extension of REDUCE MAPRIN \\ +DEPEND & vector extension of REDUCE DEPEND \\ +NODEPEND & vector extension of REDUCE NODEPEND \\ \hline +\end{tabular} +\end{center} +\caption{Procedures names and operators used in ORTHOVEC (part 2)} +\end{table} + + +\section{Test Cases} + +To use the REDUCE source version of ORTHOVEC, initiate a REDUCE +session and then IN the file {\em orthovec.red} containing ORTHOVEC. +However, it is recommended that for efficiency a compiled fast loading +version be made and LOADed when required (see Sec.~18 of the REDUCE +manual). If coordinate dependent differential and integral operators +other than cartesian are needed, then VSTART must be used to reset +coordinates and scale factors. + +Six simple examples are given in the Test Run Output file +{\em orthovectest.log} to illustrate the working of ORTHOVEC. +The input lines were taken from the file +{\em orthovectest.red} (the Test Run Input), but could +equally well be typed in at the Terminal. + +\example\index{ORTHOVEC package ! example} + +Show that +\begin{eqnarray*} +({\bf a} \times {\bf b}) \cdot ({\bf c} \times {\bf d}) - ({\bf a} +\cdot {\bf c})({\bf b} \cdot {\bf d}) + + ({\bf a} \cdot {\bf d})({\bf b} \cdot {\bf c}) \equiv 0 +\end{eqnarray*} + +\example\index{ORTHOVEC package ! example}\label{ORTHOVEC:eqm} + +Write the equation of motion +\begin{eqnarray*} +\frac{\partial {\bf v}}{\partial t} + {\bf v} \cdot {\bf \nabla v} ++ {\bf \nabla} p - curl ({\bf B}) \times {\bf B} +\end{eqnarray*} +in cylindrical coordinates. + +\example\index{ORTHOVEC package ! example}\label{ORTHOVEC:taylor} + +Taylor expand +\begin{itemize} +\item $\sin(x) \cos(y) +e^z$ +about the point $(0,0,0)$ to third order in $x$, fourth order in $y$ and +fifth order in $z$. + +\item $\sin(x)/x$ about $x$ to fifth order. + +\item ${\bf v}$ about ${\bf x}=(x,y,z)$ to fifth order, where +${\bf v} = (x/ \sin(x),(e^y-1)/y,(1+z)^{10})$. +\end{itemize} + +\example\index{ORTHOVEC package ! example} + +Obtain the second component of the equation of motion in +example~\ref{ORTHOVEC:eqm}, and the first component of the final +vector Taylor series in example~\ref{ORTHOVEC:taylor}. + +\example\index{ORTHOVEC package ! example} + +Evaluate the line integral +\begin{eqnarray*} +\int^{{\bf r}_2}_{{\bf r}_1} {\bf A} \cdot d{\bf r} +\end{eqnarray*} +from point ${\bf r}_1 = (1,1,1)$ to point +${\bf r}_2 = (2,4,8)$ along the path $(x,y,z) = (s, s^2, s^3)$ where\\ +\begin{eqnarray*} +{\bf A} = (3x^2 + 5y) {\bf i} - 12xy{\bf j} + 2xyz^2{\bf k} +\end{eqnarray*} +and $({\bf i, j, k})$ are unit vectors in the ($x,y,z$) directions. + +\example\index{ORTHOVEC package ! example} + +Find the volume $V$ common to the intersecting cylinders $x^2 + y^2 += r^2$ and $x^2 + z^2 = r^2$ i.e. evaluate +\begin{eqnarray*} +V = 8 \int^r_0 dx \int^{ub}_0 dy \int^{ub}_0 dz +\end{eqnarray*} +where $ub = \overline{\sqrt { r^2 - x^2}}$ +\bibliography{orthovec} +\bibliographystyle{plain} +\end{document} Index: r36/doc/PHYSOP.TEX ================================================================== --- r36/doc/PHYSOP.TEX +++ r36/doc/PHYSOP.TEX @@ -1,741 +1,741 @@ -\documentstyle[11pt,reduce,makeidx]{article} -\makeindex -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -% The following definitions should be commented out by those -% wishing to use MakeIndeX -\def\indexentry#1#2{{\tt #1} \dotfill\ #2\newline} -\renewcommand{\printindex}{\noindent \@input{\jobname.idx}} -%%%%%%% end of definitions %%%%%%%%%%%%%%%%%%%%% - -\title{PHYSOP \\ A Package for Operator Calculus in Quantum Theory} -\author{User's Manual \\ Version 1.5 \\ January 1992} -\date{Mathias Warns \\ -Physikalisches Institut der Universit\"at Bonn \\ -Endenicher Allee 11--13 \\ -D--5300 BONN 1 \\ -Germany \\*[2\parskip] -Tel: (++49) 228 733724 \\ -Fax: (++49) 228 737869 \\ -e--mail: UNP008@DBNRHRZ1.bitnet} - -\begin{document} -\maketitle -\section{Introduction} -The package PHYSOP has been designed to meet the requirements of -theoretical physicists looking for a -computer algebra tool to perform complicated calculations -in quantum theory -with expressions containing operators. These operations -consist mainly in the calculation of commutators between operator -expressions and in the evaluations of operator matrix elements -in some abstract space. Since the capabilities -of the current \REDUCE\ release to deal with complex -expressions containing noncommutative operators are rather restricted, -the first step was to enhance these possibilities in order to -achieve a better usability of \REDUCE\ for these kind of calculations. -This has led to the development of a first package called -NONCOM2 which is described in section 2. For more complicated -expressions involving both scalar quantities and operators -the need for an additional data type has emerged in order to make a -clear separation between the various objects present in the calculation. -The implementation of this new \REDUCE\ data type is realized by the -PHYSOP (for PHYSical OPerator) package described in section 3. - -\section{The NONCOM2 Package} - -The package NONCOM2 redefines some standard \REDUCE\ routines -in order to modify the way noncommutative operators are handled by the -system. In standard \REDUCE\ declaring an operator to be noncommutative -using the \f{NONCOM} statement puts a global flag on the -operator. This flag is checked when the system has to decide -whether or not two operators commute during the manipulation of an -expression. - -The NONCOM2 package redefines the \f{NONCOM} \index{NONCOM} statement in -a way more suitable for calculations in physics. Operators have now to -be declared noncommutative pairwise, i.e. coding: \\ - -\begin{framedverbatim} -NONCOM A,B; -\end{framedverbatim} -declares the operators \f{A} and \f{B} to be noncommutative but allows them -to commute with any other (noncommutative or not) operator present in -the expression. In a similar way if one wants e.g.\ \f{A(X)} and - \f{A(Y)} not to commute, one has now to code: \\ - -\begin{framedverbatim} - NONCOM A,A; -\end{framedverbatim} -Each operator gets a new property list containing the -operators with which it does not commute. -A final example should make -the use of the redefined \f{NONCOM} statement clear: \\ - -\begin{framedverbatim} -NONCOM A,B,C; -\end{framedverbatim} -declares \f{A} to be noncommutative with \f{B} and \f{C}, -\f{B} to be noncommutative -with \f{A} and \f{C} and \f{C} to be noncommutative -with \f{A} and \f{B}. -Note that after these declaration -e.g.\ \f{A(X)} and \f{A(Y)} -are still commuting kernels. - -Finally to keep the compatibility with standard \REDUCE\, declaring a -\underline{single} identifier using the \f{NONCOM} statement has the same -effect as in -standard \REDUCE\, i.e., the identifier is flagged with the \f{NONCOM} tag. - -From the user's point of view there are no other -new commands implemented by the package. Commutation -relations have to be declared in the standard way as described in -the manual i.e.\ using -\f{LET} statements. The package itself consists of several redefined -standard -\REDUCE\ routines to handle the new definition of noncommutativity in -multiplications and pattern matching processes. - -{\bf CAVEAT: } Due to its nature, the package is highly version -dependent. The current version has been designed for the 3.3 and 3.4 -releases -of \REDUCE\ and may not work with previous versions. Some different -(but still correct) results may occur by using this package in -conjunction with -LET statements since part of the pattern matching routines have been -redesigned. The package has been designed to bridge a deficiency of the -current \REDUCE\ version concerning the notion of noncommutativity - and it is the author's hope that it will be made obsolete -by a future release of \REDUCE. - -\section{The PHYSOP package} - -The package PHYSOP implements a new \REDUCE\ data type to perform -calculations with physical operators. The noncommutativity of -operators is -implemented using the NONCOM2 package so this file should be loaded -prior to the use of PHYSOP\footnote{To build a fast -loading version of PHYSOP the NONCOM2 -source code should be read in prior to the PHYSOP -code}. -In the following the new commands implemented by the package -are described. Beside these additional commands, -the full set of standard \REDUCE\ instructions remains -available for performing any other calculation. - -\subsection{Type declaration commands} - -The new \REDUCE\ data type PHYSOP implemented by the package allows the -definition of a new kind of operators (i.e. kernels carrying -an arbitrary -number of arguments). Throughout this manual, the name -``operator'' -will refer, unless explicitly stated otherwise, to this new data type. -This data type is in turn -divided into 5 subtypes. For each of this subtype, a declaration command -has been defined: -\begin{description} -\item[\f{SCALOP A;} ] \index{SCALOP} declares \f{A} to be a scalar -operator. This operator may -carry an arbitrary number of arguments i.e.\ after the -declaration: \f{ SCALOP A; } -all kernels of the form e.g.\ -\f{A(J), A(1,N), A(N,L,M)} -are recognized by the system as being scalar operators. - -\item[\f{VECOP V;} ] \index{VECOP} declares \f{V} to be a vector operator. -As for scalar operators, the vector operators may carry an arbitrary -number of arguments. For example \f{V(3)} can be used to represent -the vector operator $\vec{V}_{3}$. Note that the dimension of space -in which this operator lives is \underline{arbitrary}. -One can however address a specific component of the -vector operator by using a special index declared as \f{PHYSINDEX} (see -below). This index must then be the first in the argument list -of the vector operator. - -\item[\f{TENSOP C(3);} ] \index{TENSOP} -declares \f{C} to be a tensor operator of rank 3. Tensor operators -of any fixed integer rank larger than 1 can be declared. -Again this operator may carry an arbitrary number of arguments -and the space dimension is not fixed. -The tensor -components can be addressed by using special \f{PHYSINDEX} indices -(see below) which have to be placed in front of all other -arguments in the argument list. - - -\item[\f{STATE U;} ] \index{STATE} declares \f{U} to be a state, i.e.\ an -object on -which operators have a certain action. The state U can also carry an -arbitrary number of arguments. - -\item[\f{PHYSINDEX X;} ] \index{PHYSINDEX} declares \f{X} to be a special -index which will be used -to address components of vector and tensor operators. -\end{description} - -It is very important to understand precisely the way how the type -declaration commands work in order to avoid type mismatch errors when -using the PHYSOP package. The following examples should illustrate the -way the program interprets type declarations. -Assume that the declarations listed above have -been typed in by the user, then: -\begin{description} -\item[$\bullet$] \f{A,A(1,N),A(N,M,K)} are SCALAR operators. -\item[$\bullet$] \f{V,V(3),V(N,M)} are VECTOR operators. -\item[$\bullet$] \f{C, C(5),C(Y,Z)} are TENSOR operators of -rank 3. -\item[$\bullet$] \f{U,U(P),U(N,L,M)} are STATES. -\item[BUT:] \f{V(X),V(X,3),V(X,N,M)} are all \underline{scalar} -operators -since the \underline{special index} \f{X} addresses a -specific component -of the vector operator (which is a scalar operator). Accordingly, -\f{C(X,X,X)} is also a \underline{scalar} operator because -the diagonal component $C_{xxx}$ -of the tensor operator \f{C} is meant here -(C has rank 3 so 3 special indices must be used for the components). -\end{description} - -In view of these examples, every time the following text -refers to \underline{scalar} operators, -it should be understood that this means not only operators defined by -the -\f{SCALOP} statement but also components of vector and tensor operators. -Depending on the situation, in some case when dealing only with the -components of vector or tensor operators it may be preferable to use -an operator declared with \f{SCALOP} rather than addressing the -components using several special indices (throughout the -manual, -indices declared with the \f{PHYSINDEX} command are referred to as special -indices). - -Another important feature of the system is that -for each operator declared using the statements described above, the -system generates 2 additional operators of the same type: -the \underline{adjoint} and the \underline{inverse} operator. -These operators are accessible to the user for subsequent calculations -without any new declaration. The syntax is as following: - -If \f{A} has been declared to be an operator (scalar, vector or tensor) -the \underline{adjoint} operator is denoted \f{A!+} and the -\underline{inverse} -operator is denoted \f{A!-1} (an inverse adjoint operator \f{A!+!-1} -is also generated). -The exclamation marks do not appear -when these operators are printed out by \REDUCE\ (except when the switch -\f{NAT} is set to off) -but have to be typed in when these operators are used in an input -expression. -An adjoint (but \underline{no} inverse) state is also -generated for every state defined by the user. -One may consider these generated operators as ''placeholders'' which -means that these operators are considered by default as -being completely independent of the original operator. -Especially if some value is assigned to the original operator, -this value is \underline{not} automatically assigned to the -generated operators. The user must code additional assignement -statements in order to get the corresponding values. - -Exceptions from these rules are (i) that inverse operators are -\underline{always} ordered at the same place as the original operators -and (ii) that the expressions \f{A!-1*A} -and \f{A*A!-1} are replaced\footnote{This may not always occur in -intermediate steps of a calculation due to efficiency reasons.} -by the unit operator \f{UNIT} \index{UNIT}. -This operator is defined -as a scalar operator during the initialization of the PHYSOP package. -It should be used to indicate -the type of an operator expression whenever no other PHYSOP -occur in it. For example, the following sequence: \\ - -\begin{framedverbatim} -SCALOP A; -A:= 5; -\end{framedverbatim} -leads to a type mismatch error and should be replaced by: \\ - -\begin{framedverbatim} -SCALOP A; -A:=5*UNIT; -\end{framedverbatim} -The operator \f{UNIT} is a reserved variable of the system and should -not be used for other purposes. - -All other kernels (including standard \REDUCE\ operators) -occurring in expressions are treated as ordinary scalar variables -without any PHYSOP type (referred to as \underline{scalars} in the -following). -Assignement statements are checked to ensure correct operator -type assignement on both sides leading to an error if a type -mismatch occurs. However an assignement statement of the form -\f{A:= 0} or \f{LET A = 0} is \underline{always} valid regardless of the -type of \f{A}. - -Finally a command \f{CLEARPHYSOP} \index{CLEARPHYSOP} -has been defined to remove -the PHYSOP type from an identifier in order to use it for subsequent -calculations (e.g. as an ordinary \REDUCE\ operator). However it should be -remembered that \underline{no} -substitution rule is cleared by this function. It -is therefore left to the user's responsibility to clear previously all -substitution rules involving the identifier from which the PHYSOP type -is removed. - -Users should be very careful when defining procedures or statements of -the type \f{FOR ALL ... LET ...} that the PHYSOP type of all identifiers -occurring in such expressions is unambigously fixed. The type analysing -procedure is rather restrictive and will print out a ''PHYSOP type -conflict'' error message if such ambiguities occur. - -\subsection{Ordering of operators in an expression} - -The ordering of kernels in an expression is performed according to -the following rules: \\ -1. \underline{Scalars} are always ordered ahead of -PHYSOP \underline{operators} in an expression. -The \REDUCE\ statement \f{KORDER} \index{KORDER} can be used to control the -ordering of scalars but has \underline{no} -effect on the ordering of operators. - -2. The default ordering of \underline{operators} follows the -order in which they have been declared (and \underline{not} -the alphabetical one). -This ordering scheme can be changed using the command \f{OPORDER}. -\index{OPORDER} -Its syntax is similar to the \f{KORDER} statement, i.e.\ coding: -\f{OPORDER A,V,F;} -means that all occurrences of the operator \f{A} are ordered ahead of -those of \f{V} etc. It is also possible to include operators -carrying -indices (both normal and special ones) in the argument list of -\f{OPORDER}. However including objects \underline{not} -defined as operators (i.e. scalars or indices) in the argument list -of the \f{OPORDER} command leads to an error. - -3. Adjoint operators are placed by the declaration commands just -after the original operators on the \f{OPORDER} list. Changing the -place of an operator on this list means \underline{not} that the -adjoint operator is moved accordingly. This adjoint operator can -be moved freely by including it in the argument list of the -\f{OPORDER} command. - -\subsection{Arithmetic operations on operators} - -The following arithmetic operations are possible with -operator expressions: \\ - -1. Multiplication or division of an operator by a scalar. - -2. Addition and subtraction of operators of the \underline{same} type. - -3. Multiplication of operators is only defined between two -\underline{scalar} operators. - -4. The scalar product of two VECTOR operators is implemented with -a new function \f{DOT} \index{DOT}. The system expands the product of -two vector operators into an ordinary product of the components of these -operators by inserting a special index generated by the program. -To give an example, if one codes: \\ - -\begin{framedverbatim} -VECOP V,W; -V DOT W; -\end{framedverbatim} -the system will transform the product into: \\ - -\begin{framedverbatim} -V(IDX1) * W(IDX1) -\end{framedverbatim} -where \f{IDX1} is a \f{PHYSINDEX} generated by the system (called a DUMMY -INDEX in the following) to express the summation over the components. -The identifiers \f{IDXn} (\f{n} is -a nonzero integer) are -reserved variables for this purpose and should not be used for other -applications. The arithmetic operator -\f{DOT} can be used both in infix and prefix form with two arguments. - -5. Operators (but not states) can only be raised to an -\underline{integer} power. The system expands this power -expression into a product of the corresponding number of terms -inserting dummy indices if necessary. The following examples explain -the transformations occurring on power expressions (system output -is indicated with an \f{-->}): \\ - -\begin{framedverbatim} -SCALOP A; A**2; -- --> A*A -VECOP V; V**4; -- --> V(IDX1)*V(IDX1)*V(IDX2)*V(IDX2) -TENSOP C(2); C**2; -- --> C(IDX3,IDX4)*C(IDX3,IDX4) -\end{framedverbatim} -Note in particular the way how the system interprets powers of -tensor operators which is different from the notation used in matrix -algebra. - -6. Quotients of operators are only defined between -\underline{scalar} operator expressions. -The system transforms the quotient of 2 scalar operators into the -product of the first operator times the inverse of the second one. -Example\footnote{This shows how inverse operators are printed out when -the switch \f{NAT} is on}: \\ - -\begin{framedverbatim} -SCALOP A,B; A / B; - -1 - --> (B )*A -\end{framedverbatim} - -7. Combining the last 2 rules explains the way how the system -handles negative powers of operators: \\ - -\noindent -\begin{framedverbatim} -SCALOP B; -B**(-3); - -1 -1 -1 - --> (B )*(B )*(B ) -\end{framedverbatim} - - -The method of inserting dummy indices and expanding powers of -operators has been chosen to facilitate the handling of -complicated operator -expressions and particularly their application on states -(see section 3.4.3). However it may be useful to get rid of these -dummy indices in order to enhance the readability of the -system's final output. -For this purpose the switch \f{CONTRACT} \index{CONTRACT} has to -be turned on (\f{CONTRACT} is normally set to \f{OFF}). -The system in this case contracts over dummy indices reinserting the -\f{DOT} operator and reassembling the expanded powers. However due to -the predefined operator ordering the system may not remove all the -dummy indices introduced previously. - -\subsection{Special functions} - -\subsubsection{Commutation relations} - -If 2 PHYSOPs have been declared noncommutative using the (redefined) -\f{NONCOM} statement, it is possible to introduce in the environment -\underline{elementary} (anti-) commutation relations between them. For -this purpose, -2 \underline{scalar} operators \f{COMM} \index{COMM} and -\f{ANTICOMM} \index{ANTICOMM} are available. -These operators are used in conjunction with \f{LET} statements. -Example: \\ - -\begin{framedverbatim} -SCALOP A,B,C,D; -LET COMM(A,B)=C; -FOR ALL N,M LET ANTICOMM(A(N),B(M))=D; -VECOP U,V,W; PHYSINDEX X,Y,Z; -FOR ALL X,Y LET COMM(V(X),W(Y))=U(Z); -\end{framedverbatim} - -Note that if special indices are used as dummy variables in -\f{FOR ALL ... LET} constructs then these indices should have been -declared previously using the \f{PHYSINDEX} command. - -Every time the system -encounters a product term involving 2 -noncommutative operators which have to be reordered on account of the -given operator ordering, the list of available (anti-) commutators is -checked in the following way: First the system looks for a -\underline{commutation} relation which matches the product term. If it -fails then the defined \underline{anticommutation} relations are -checked. If there is no successful match the product term - \f{A*B} is replaced by: \\ - -\begin{framedverbatim} -A*B; - --> COMM(A,B) + B*A -\end{framedverbatim} -so that the user may introduce the commutation relation later on. - -The user may want to force the system to look for -\underline{anticommutators} only; for this purpose a switch \f{ANTICOM} -\index{ANTICOM} -is defined which has to be turned on ( \f{ANTICOM} is normally set to -\f{OFF}). In this case, the above example is replaced by: \\ - -\begin{framedverbatim} -ON ANTICOM; -A*B; - --> ANTICOMM(A,B) - B*A -\end{framedverbatim} - -Once the operator ordering has been fixed (in the example above \f{B} -has to be ordered ahead of \f{A}), -there is \underline{no way} to prevent the -system from introducing (anti-)commutators every time it encounters -a product whose terms are not in the right order. On the other hand, -simply by changing the \f{OPORDER} statement and reevaluating the -expression one can change the operator ordering -\underline{without} -the need to introduce new commutation relations. -Consider the following example: \\ - -\begin{framedverbatim} -SCALOP A,B,C; NONCOM A,B; OPORDER B,A; -LET COMM(A,B)=C; -A*B; -- --> B*A + C; -OPORDER A,B; - B*A; -- --> A*B - C; -\end{framedverbatim} - -The functions \f{COMM} and \f{ANTICOMM} should only be used to -define -elementary (anti-) commutation relations between single operators. -For the calculation of (anti-) commutators between complex -operator -expressions, the functions \f{COMMUTE} \index{COMMUTE} and -\f{ANTICOMMUTE} \index{ANTICOMMUTE} have been defined. -Example (is included as example 1 in the test file): \\ - -\begin{framedverbatim} -VECOP P,A,K; -PHYSINDEX X,Y; -FOR ALL X,Y LET COMM(P(X),A(Y))=K(X)*A(Y); -COMMUTE(P**2,P DOT A); -\end{framedverbatim} - -\subsubsection{Adjoint expressions} - -As has been already mentioned, for each operator and state defined -using the declaration commands quoted in section 3.1, the system -generates automatically the corresponding adjoint operator. For the -calculation of the adjoint representation of a complicated -operator expression, a function \f{ADJ} \index{ADJ} has been defined. -Example\footnote{This shows how adjoint operators are printed out -when the switch \f{NAT} is on}: \\ - -\begin{framedverbatim} -SCALOP A,B; -ADJ(A*B); - + + - --> (B )*(A ) -\end{framedverbatim} - -\subsubsection{Application of operators on states} - -For this purpose, a function \f{OPAPPLY} \index{OPAPPLY} has been -defined. -It has 2 arguments and is used in the following combinations: \\ - -{\bf (i)} \f{LET OPAPPLY(}{\it operator, state}\f{) =} {\it state}; -This is to define a elementary -action of an operator on a state in analogy to the way -elementary commutation relations are introduced to the system. -Example: \\ - -\begin{framedverbatim} -SCALOP A; STATE U; -FOR ALL N,P LET OPAPPLY((A(N),U(P))= EXP(I*N*P)*U(P); -\end{framedverbatim} - -{\bf (ii)} \f{LET OPAPPLY(}{\it state, state}\f{) =} {\it scalar exp.}; -This form is to define scalar products between states and normalization -conditions. -Example: \\ - -\begin{framedverbatim} -STATE U; -FOR ALL N,M LET OPAPPLY(U(N),U(M)) = IF N=M THEN 1 ELSE 0; -\end{framedverbatim} - -{\bf (iii)} {\it state} \f{:= OPAPPLY(}{\it operator expression, state}); - In this way, the action of an operator expression on a given state -is calculated using elementary relations defined as explained in {\bf -(i)}. The result may be assigned to a different state vector. - -{\bf (iv)} \f{OPAPPLY(}{\it state}\f{, OPAPPLY(}{\it operator expression, -state}\f{))}; This is the way how to calculate matrix elements of -operator -expressions. The system proceeds in the following way: first the -rightmost operator is applied on the right state, which means that the -system tries -to find an elementary relation which match the application of the -operator on the state. If it fails -the system tries to apply the leftmost operator of the expression on the -left state using the adjoint representations. If this fails also, -the system prints out a warning message and stops the evaluation. -Otherwise the next operator occuring in the expression is -taken and so on until the complete expression is applied. Then the -system -looks for a relation expressing the scalar product of the two -resulting states and prints out the final result. An example of such -a calculation is given in the test file. - -The infix version of the \f{OPAPPLY} function is the vertical bar $\mid$ -. It is \underline{right} associative and placed in the precedence -list just above the minus ($-$) operator. -Some of the \REDUCE\ implementation may not work with this character, -the prefix form should then be used instead\footnote{The source code -can also be modified to choose another special character for the -function}. - -\section{Known problems in the current release of PHYSOP} - -\indent {\bf (i)} Some spurious negative powers of operators -may appear -in the result of a calculation using the PHYSOP package. This is a -purely ''cosmetic'' effect which is due to an additional -factorization of the expression in the output printing routines of -\REDUCE. Setting off the \REDUCE\ switch \f{ALLFAC} (\f{ALLFAC} is normally -on) -should make these -terms disappear and print out the correct result (see example 1 -in the test file). - -{\bf (ii)} The current release of the PHYSOP package is not optimized -w.r.t. computation speed. Users should be aware that the evaluation -of complicated expressions involving a lot of commutation relations -requires a significant amount of CPU time \underline{and} memory. -Therefore the use of PHYSOP on small machines is rather limited. A -minimal hardware configuration should include at least 4 MB of -memory and a reasonably fast CPU (type Intel 80386 or equiv.). - -{\bf (iii)} Slightly different ordering of operators (especially with -multiple occurrences of the same operator with different indices) -may appear in some calculations -due to the internal ordering of atoms in the underlying LISP system -(see last example in the test file). This cannot be entirely avoided -by the package but does not affect the correctness of the results. - -\section{Compilation of the packages} -To build a fast loading module of the NONCOM2 package, enter the -following commands after starting the \REDUCE\ system: \\ - -\begin{framedverbatim} - faslout "noncom2"; - in "noncom2.red"; - faslend; -\end{framedverbatim} -To build a fast loading module of the PHYSOP package, enter the -following commands after starting the \REDUCE\ system: \\ - -\begin{framedverbatim} - faslout "physop"; - in "noncom2.red"; - in "physop.red"; - faslend; -\end{framedverbatim} -Input and output file specifications may change according to the -underlying operating system. \\ -On PSL--based systems, a spurious message: \\ - -\begin{framedverbatim} -*** unknown function PHYSOP!*SQ called from compiled code -\end{framedverbatim} -may appear during the compilation of the PHYSOP package. This warning -has no effect on the functionality of the package. - -\section{Final remarks} -The package PHYSOP has been presented by -the author at the IV inter. Conference on Computer Algebra in Physical -Research, Dubna (USSR) 1990 (see M. Warns, {\it -Software Extensions of \REDUCE\ for Operator Calculus in Quantum Theory}, -Proc.\ of the IV inter.\ Conf.\ on Computer Algebra in Physical -Research, Dubna 1990, to appear). It has been developed with the aim in -mind to perform calculations of the type exemplified in the test file -included in the distribution of this package. -However it should -also be useful in some other domains like e.g.\ the calculations of -complicated Feynman diagrams in QCD which could not be performed using -the HEPHYS package. The author is therefore grateful for any -suggestion -to improve or extend the usability of the package. Users should not -hesitate to contact the author for additional help and explanations on -how to use -this package. Some bugs may also -appear which have not been discovered during the tests performed -prior to the release of this version. Please send in this case to the -author a short -input and output listing displaying the encountered problem. - -\section*{Acknowledgements} -The main ideas for the implementation of a new data type in the \REDUCE\ -environnement have been taken from the VECTOR package developed by -Dr.\ David Harper (D. Harper, Comp.\ Phys.\ Comm.\ {\bf 54} (1989) -295). -Useful discussions with Dr.\ Eberhard Schr\"ufer and -Prof.\ John Fitch are also gratefully acknowledged. - -\appendix - -\section{List of error and warning messages} -In the following the error (E) and warning (W) messages specific to the -PHYSOP package are listed. -\begin{description} -\item[\f{cannot declare} {\it x}\f{ as }{\it data type}] (W): - An attempt has been made to declare an -object {\it x} which cannot be used as a PHYSOP operator of the -required type. The declaration command is ignored. - -\item [{\it x} \f{already defined as} {\it data type}] (W): The object -{\it x} has already been declared using a \REDUCE\ type declaration -command and can therefore not be used as a PHYSOP operator. -The declaration command is ignored. - -\item [{\it x} \f{already declared as} {\it data type}] (W): The object -\f{x} has already been declared with a PHYSOP declaration command. -The declaration command is ignored. - -\item[{\it x} \f{is not a PHYSOP}] (E): An invalid argument has been -included in an \f{OPORDER} command. Check the arguments. - -\item[\f{invalid argument(s) to }{\it function}] (E): A -function implemented by the PHYSOP package has been called with an -invalid argument. Check type of arguments. - - -\item[\f{Type conflict in }{\it operation}] (E): A PHYSOP type conflict -has occured during an arithmetic operation. Check the arguments. - -\item [\f{invalid call of }{\it function} \f{with args:} {\it arguments}] -(E): A function -of the PHYSOP package has been declared with invalid argument(s). Check -the argument list. - -\item[\f{type mismatch in} {\it expression}] (E): A type mismatch has -been detected in an expression. Check the corresponding expression. - -\item[\f{type mismatch in} {\it assignement}] (E): A type -mismatch has been detected in an assignment or in a \f{LET} -statement. Check the listed statement. - -\item[\f{PHYSOP type conflict in} {\it expr}] (E): A ambiguity has been -detected during the type analysis of the expression. Check the -expression. - -\item[\f{operators in exponent cannot be handled}] (E): An operator has -occurred in the exponent of an expression. - -\item[\f{cannot raise a state to a power}] (E): states cannot be -exponentiated by the system. - -\item[\f{invalid quotient}] (E): An invalid denominator has occurred in a -quotient. Check the expression. - -\item[\f{physops of different types cannot be commuted}] (E): An invalid -operator has occurred in a call of the \f{COMMUTE}/\f{ANTICOMMUTE} function. - -\item[\f{commutators only implemented between scalar operators}] (E): -An invalid operator has occurred in the call of the -\f{COMMUTE}/\f{ANTICOMMUTE} function. - -\item[\f{evaluation incomplete due to missing elementary relations}] (W): -\\ -The system has not found all -the elementary commutators or application relations necessary to -calculate or reorder the input expression. The result may however be -used for further calculations. -\end{description} - -\section{List of available commands} -\printindex -\end{document} +\documentstyle[11pt,reduce,makeidx]{article} +\makeindex +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +% The following definitions should be commented out by those +% wishing to use MakeIndeX +\def\indexentry#1#2{{\tt #1} \dotfill\ #2\newline} +\renewcommand{\printindex}{\noindent \@input{\jobname.idx}} +%%%%%%% end of definitions %%%%%%%%%%%%%%%%%%%%% + +\title{PHYSOP \\ A Package for Operator Calculus in Quantum Theory} +\author{User's Manual \\ Version 1.5 \\ January 1992} +\date{Mathias Warns \\ +Physikalisches Institut der Universit\"at Bonn \\ +Endenicher Allee 11--13 \\ +D--5300 BONN 1 \\ +Germany \\*[2\parskip] +Tel: (++49) 228 733724 \\ +Fax: (++49) 228 737869 \\ +e--mail: UNP008@DBNRHRZ1.bitnet} + +\begin{document} +\maketitle +\section{Introduction} +The package PHYSOP has been designed to meet the requirements of +theoretical physicists looking for a +computer algebra tool to perform complicated calculations +in quantum theory +with expressions containing operators. These operations +consist mainly in the calculation of commutators between operator +expressions and in the evaluations of operator matrix elements +in some abstract space. Since the capabilities +of the current \REDUCE\ release to deal with complex +expressions containing noncommutative operators are rather restricted, +the first step was to enhance these possibilities in order to +achieve a better usability of \REDUCE\ for these kind of calculations. +This has led to the development of a first package called +NONCOM2 which is described in section 2. For more complicated +expressions involving both scalar quantities and operators +the need for an additional data type has emerged in order to make a +clear separation between the various objects present in the calculation. +The implementation of this new \REDUCE\ data type is realized by the +PHYSOP (for PHYSical OPerator) package described in section 3. + +\section{The NONCOM2 Package} + +The package NONCOM2 redefines some standard \REDUCE\ routines +in order to modify the way noncommutative operators are handled by the +system. In standard \REDUCE\ declaring an operator to be noncommutative +using the \f{NONCOM} statement puts a global flag on the +operator. This flag is checked when the system has to decide +whether or not two operators commute during the manipulation of an +expression. + +The NONCOM2 package redefines the \f{NONCOM} \index{NONCOM} statement in +a way more suitable for calculations in physics. Operators have now to +be declared noncommutative pairwise, i.e. coding: \\ + +\begin{framedverbatim} +NONCOM A,B; +\end{framedverbatim} +declares the operators \f{A} and \f{B} to be noncommutative but allows them +to commute with any other (noncommutative or not) operator present in +the expression. In a similar way if one wants e.g.\ \f{A(X)} and + \f{A(Y)} not to commute, one has now to code: \\ + +\begin{framedverbatim} + NONCOM A,A; +\end{framedverbatim} +Each operator gets a new property list containing the +operators with which it does not commute. +A final example should make +the use of the redefined \f{NONCOM} statement clear: \\ + +\begin{framedverbatim} +NONCOM A,B,C; +\end{framedverbatim} +declares \f{A} to be noncommutative with \f{B} and \f{C}, +\f{B} to be noncommutative +with \f{A} and \f{C} and \f{C} to be noncommutative +with \f{A} and \f{B}. +Note that after these declaration +e.g.\ \f{A(X)} and \f{A(Y)} +are still commuting kernels. + +Finally to keep the compatibility with standard \REDUCE\, declaring a +\underline{single} identifier using the \f{NONCOM} statement has the same +effect as in +standard \REDUCE\, i.e., the identifier is flagged with the \f{NONCOM} tag. + +From the user's point of view there are no other +new commands implemented by the package. Commutation +relations have to be declared in the standard way as described in +the manual i.e.\ using +\f{LET} statements. The package itself consists of several redefined +standard +\REDUCE\ routines to handle the new definition of noncommutativity in +multiplications and pattern matching processes. + +{\bf CAVEAT: } Due to its nature, the package is highly version +dependent. The current version has been designed for the 3.3 and 3.4 +releases +of \REDUCE\ and may not work with previous versions. Some different +(but still correct) results may occur by using this package in +conjunction with +LET statements since part of the pattern matching routines have been +redesigned. The package has been designed to bridge a deficiency of the +current \REDUCE\ version concerning the notion of noncommutativity + and it is the author's hope that it will be made obsolete +by a future release of \REDUCE. + +\section{The PHYSOP package} + +The package PHYSOP implements a new \REDUCE\ data type to perform +calculations with physical operators. The noncommutativity of +operators is +implemented using the NONCOM2 package so this file should be loaded +prior to the use of PHYSOP\footnote{To build a fast +loading version of PHYSOP the NONCOM2 +source code should be read in prior to the PHYSOP +code}. +In the following the new commands implemented by the package +are described. Beside these additional commands, +the full set of standard \REDUCE\ instructions remains +available for performing any other calculation. + +\subsection{Type declaration commands} + +The new \REDUCE\ data type PHYSOP implemented by the package allows the +definition of a new kind of operators (i.e. kernels carrying +an arbitrary +number of arguments). Throughout this manual, the name +``operator'' +will refer, unless explicitly stated otherwise, to this new data type. +This data type is in turn +divided into 5 subtypes. For each of this subtype, a declaration command +has been defined: +\begin{description} +\item[\f{SCALOP A;} ] \index{SCALOP} declares \f{A} to be a scalar +operator. This operator may +carry an arbitrary number of arguments i.e.\ after the +declaration: \f{ SCALOP A; } +all kernels of the form e.g.\ +\f{A(J), A(1,N), A(N,L,M)} +are recognized by the system as being scalar operators. + +\item[\f{VECOP V;} ] \index{VECOP} declares \f{V} to be a vector operator. +As for scalar operators, the vector operators may carry an arbitrary +number of arguments. For example \f{V(3)} can be used to represent +the vector operator $\vec{V}_{3}$. Note that the dimension of space +in which this operator lives is \underline{arbitrary}. +One can however address a specific component of the +vector operator by using a special index declared as \f{PHYSINDEX} (see +below). This index must then be the first in the argument list +of the vector operator. + +\item[\f{TENSOP C(3);} ] \index{TENSOP} +declares \f{C} to be a tensor operator of rank 3. Tensor operators +of any fixed integer rank larger than 1 can be declared. +Again this operator may carry an arbitrary number of arguments +and the space dimension is not fixed. +The tensor +components can be addressed by using special \f{PHYSINDEX} indices +(see below) which have to be placed in front of all other +arguments in the argument list. + + +\item[\f{STATE U;} ] \index{STATE} declares \f{U} to be a state, i.e.\ an +object on +which operators have a certain action. The state U can also carry an +arbitrary number of arguments. + +\item[\f{PHYSINDEX X;} ] \index{PHYSINDEX} declares \f{X} to be a special +index which will be used +to address components of vector and tensor operators. +\end{description} + +It is very important to understand precisely the way how the type +declaration commands work in order to avoid type mismatch errors when +using the PHYSOP package. The following examples should illustrate the +way the program interprets type declarations. +Assume that the declarations listed above have +been typed in by the user, then: +\begin{description} +\item[$\bullet$] \f{A,A(1,N),A(N,M,K)} are SCALAR operators. +\item[$\bullet$] \f{V,V(3),V(N,M)} are VECTOR operators. +\item[$\bullet$] \f{C, C(5),C(Y,Z)} are TENSOR operators of +rank 3. +\item[$\bullet$] \f{U,U(P),U(N,L,M)} are STATES. +\item[BUT:] \f{V(X),V(X,3),V(X,N,M)} are all \underline{scalar} +operators +since the \underline{special index} \f{X} addresses a +specific component +of the vector operator (which is a scalar operator). Accordingly, +\f{C(X,X,X)} is also a \underline{scalar} operator because +the diagonal component $C_{xxx}$ +of the tensor operator \f{C} is meant here +(C has rank 3 so 3 special indices must be used for the components). +\end{description} + +In view of these examples, every time the following text +refers to \underline{scalar} operators, +it should be understood that this means not only operators defined by +the +\f{SCALOP} statement but also components of vector and tensor operators. +Depending on the situation, in some case when dealing only with the +components of vector or tensor operators it may be preferable to use +an operator declared with \f{SCALOP} rather than addressing the +components using several special indices (throughout the +manual, +indices declared with the \f{PHYSINDEX} command are referred to as special +indices). + +Another important feature of the system is that +for each operator declared using the statements described above, the +system generates 2 additional operators of the same type: +the \underline{adjoint} and the \underline{inverse} operator. +These operators are accessible to the user for subsequent calculations +without any new declaration. The syntax is as following: + +If \f{A} has been declared to be an operator (scalar, vector or tensor) +the \underline{adjoint} operator is denoted \f{A!+} and the +\underline{inverse} +operator is denoted \f{A!-1} (an inverse adjoint operator \f{A!+!-1} +is also generated). +The exclamation marks do not appear +when these operators are printed out by \REDUCE\ (except when the switch +\f{NAT} is set to off) +but have to be typed in when these operators are used in an input +expression. +An adjoint (but \underline{no} inverse) state is also +generated for every state defined by the user. +One may consider these generated operators as ''placeholders'' which +means that these operators are considered by default as +being completely independent of the original operator. +Especially if some value is assigned to the original operator, +this value is \underline{not} automatically assigned to the +generated operators. The user must code additional assignement +statements in order to get the corresponding values. + +Exceptions from these rules are (i) that inverse operators are +\underline{always} ordered at the same place as the original operators +and (ii) that the expressions \f{A!-1*A} +and \f{A*A!-1} are replaced\footnote{This may not always occur in +intermediate steps of a calculation due to efficiency reasons.} +by the unit operator \f{UNIT} \index{UNIT}. +This operator is defined +as a scalar operator during the initialization of the PHYSOP package. +It should be used to indicate +the type of an operator expression whenever no other PHYSOP +occur in it. For example, the following sequence: \\ + +\begin{framedverbatim} +SCALOP A; +A:= 5; +\end{framedverbatim} +leads to a type mismatch error and should be replaced by: \\ + +\begin{framedverbatim} +SCALOP A; +A:=5*UNIT; +\end{framedverbatim} +The operator \f{UNIT} is a reserved variable of the system and should +not be used for other purposes. + +All other kernels (including standard \REDUCE\ operators) +occurring in expressions are treated as ordinary scalar variables +without any PHYSOP type (referred to as \underline{scalars} in the +following). +Assignement statements are checked to ensure correct operator +type assignement on both sides leading to an error if a type +mismatch occurs. However an assignement statement of the form +\f{A:= 0} or \f{LET A = 0} is \underline{always} valid regardless of the +type of \f{A}. + +Finally a command \f{CLEARPHYSOP} \index{CLEARPHYSOP} +has been defined to remove +the PHYSOP type from an identifier in order to use it for subsequent +calculations (e.g. as an ordinary \REDUCE\ operator). However it should be +remembered that \underline{no} +substitution rule is cleared by this function. It +is therefore left to the user's responsibility to clear previously all +substitution rules involving the identifier from which the PHYSOP type +is removed. + +Users should be very careful when defining procedures or statements of +the type \f{FOR ALL ... LET ...} that the PHYSOP type of all identifiers +occurring in such expressions is unambigously fixed. The type analysing +procedure is rather restrictive and will print out a ''PHYSOP type +conflict'' error message if such ambiguities occur. + +\subsection{Ordering of operators in an expression} + +The ordering of kernels in an expression is performed according to +the following rules: \\ +1. \underline{Scalars} are always ordered ahead of +PHYSOP \underline{operators} in an expression. +The \REDUCE\ statement \f{KORDER} \index{KORDER} can be used to control the +ordering of scalars but has \underline{no} +effect on the ordering of operators. + +2. The default ordering of \underline{operators} follows the +order in which they have been declared (and \underline{not} +the alphabetical one). +This ordering scheme can be changed using the command \f{OPORDER}. +\index{OPORDER} +Its syntax is similar to the \f{KORDER} statement, i.e.\ coding: +\f{OPORDER A,V,F;} +means that all occurrences of the operator \f{A} are ordered ahead of +those of \f{V} etc. It is also possible to include operators +carrying +indices (both normal and special ones) in the argument list of +\f{OPORDER}. However including objects \underline{not} +defined as operators (i.e. scalars or indices) in the argument list +of the \f{OPORDER} command leads to an error. + +3. Adjoint operators are placed by the declaration commands just +after the original operators on the \f{OPORDER} list. Changing the +place of an operator on this list means \underline{not} that the +adjoint operator is moved accordingly. This adjoint operator can +be moved freely by including it in the argument list of the +\f{OPORDER} command. + +\subsection{Arithmetic operations on operators} + +The following arithmetic operations are possible with +operator expressions: \\ + +1. Multiplication or division of an operator by a scalar. + +2. Addition and subtraction of operators of the \underline{same} type. + +3. Multiplication of operators is only defined between two +\underline{scalar} operators. + +4. The scalar product of two VECTOR operators is implemented with +a new function \f{DOT} \index{DOT}. The system expands the product of +two vector operators into an ordinary product of the components of these +operators by inserting a special index generated by the program. +To give an example, if one codes: \\ + +\begin{framedverbatim} +VECOP V,W; +V DOT W; +\end{framedverbatim} +the system will transform the product into: \\ + +\begin{framedverbatim} +V(IDX1) * W(IDX1) +\end{framedverbatim} +where \f{IDX1} is a \f{PHYSINDEX} generated by the system (called a DUMMY +INDEX in the following) to express the summation over the components. +The identifiers \f{IDXn} (\f{n} is +a nonzero integer) are +reserved variables for this purpose and should not be used for other +applications. The arithmetic operator +\f{DOT} can be used both in infix and prefix form with two arguments. + +5. Operators (but not states) can only be raised to an +\underline{integer} power. The system expands this power +expression into a product of the corresponding number of terms +inserting dummy indices if necessary. The following examples explain +the transformations occurring on power expressions (system output +is indicated with an \f{-->}): \\ + +\begin{framedverbatim} +SCALOP A; A**2; +- --> A*A +VECOP V; V**4; +- --> V(IDX1)*V(IDX1)*V(IDX2)*V(IDX2) +TENSOP C(2); C**2; +- --> C(IDX3,IDX4)*C(IDX3,IDX4) +\end{framedverbatim} +Note in particular the way how the system interprets powers of +tensor operators which is different from the notation used in matrix +algebra. + +6. Quotients of operators are only defined between +\underline{scalar} operator expressions. +The system transforms the quotient of 2 scalar operators into the +product of the first operator times the inverse of the second one. +Example\footnote{This shows how inverse operators are printed out when +the switch \f{NAT} is on}: \\ + +\begin{framedverbatim} +SCALOP A,B; A / B; + -1 + --> (B )*A +\end{framedverbatim} + +7. Combining the last 2 rules explains the way how the system +handles negative powers of operators: \\ + +\noindent +\begin{framedverbatim} +SCALOP B; +B**(-3); + -1 -1 -1 + --> (B )*(B )*(B ) +\end{framedverbatim} + + +The method of inserting dummy indices and expanding powers of +operators has been chosen to facilitate the handling of +complicated operator +expressions and particularly their application on states +(see section 3.4.3). However it may be useful to get rid of these +dummy indices in order to enhance the readability of the +system's final output. +For this purpose the switch \f{CONTRACT} \index{CONTRACT} has to +be turned on (\f{CONTRACT} is normally set to \f{OFF}). +The system in this case contracts over dummy indices reinserting the +\f{DOT} operator and reassembling the expanded powers. However due to +the predefined operator ordering the system may not remove all the +dummy indices introduced previously. + +\subsection{Special functions} + +\subsubsection{Commutation relations} + +If 2 PHYSOPs have been declared noncommutative using the (redefined) +\f{NONCOM} statement, it is possible to introduce in the environment +\underline{elementary} (anti-) commutation relations between them. For +this purpose, +2 \underline{scalar} operators \f{COMM} \index{COMM} and +\f{ANTICOMM} \index{ANTICOMM} are available. +These operators are used in conjunction with \f{LET} statements. +Example: \\ + +\begin{framedverbatim} +SCALOP A,B,C,D; +LET COMM(A,B)=C; +FOR ALL N,M LET ANTICOMM(A(N),B(M))=D; +VECOP U,V,W; PHYSINDEX X,Y,Z; +FOR ALL X,Y LET COMM(V(X),W(Y))=U(Z); +\end{framedverbatim} + +Note that if special indices are used as dummy variables in +\f{FOR ALL ... LET} constructs then these indices should have been +declared previously using the \f{PHYSINDEX} command. + +Every time the system +encounters a product term involving 2 +noncommutative operators which have to be reordered on account of the +given operator ordering, the list of available (anti-) commutators is +checked in the following way: First the system looks for a +\underline{commutation} relation which matches the product term. If it +fails then the defined \underline{anticommutation} relations are +checked. If there is no successful match the product term + \f{A*B} is replaced by: \\ + +\begin{framedverbatim} +A*B; + --> COMM(A,B) + B*A +\end{framedverbatim} +so that the user may introduce the commutation relation later on. + +The user may want to force the system to look for +\underline{anticommutators} only; for this purpose a switch \f{ANTICOM} +\index{ANTICOM} +is defined which has to be turned on ( \f{ANTICOM} is normally set to +\f{OFF}). In this case, the above example is replaced by: \\ + +\begin{framedverbatim} +ON ANTICOM; +A*B; + --> ANTICOMM(A,B) - B*A +\end{framedverbatim} + +Once the operator ordering has been fixed (in the example above \f{B} +has to be ordered ahead of \f{A}), +there is \underline{no way} to prevent the +system from introducing (anti-)commutators every time it encounters +a product whose terms are not in the right order. On the other hand, +simply by changing the \f{OPORDER} statement and reevaluating the +expression one can change the operator ordering +\underline{without} +the need to introduce new commutation relations. +Consider the following example: \\ + +\begin{framedverbatim} +SCALOP A,B,C; NONCOM A,B; OPORDER B,A; +LET COMM(A,B)=C; +A*B; +- --> B*A + C; +OPORDER A,B; + B*A; +- --> A*B - C; +\end{framedverbatim} + +The functions \f{COMM} and \f{ANTICOMM} should only be used to +define +elementary (anti-) commutation relations between single operators. +For the calculation of (anti-) commutators between complex +operator +expressions, the functions \f{COMMUTE} \index{COMMUTE} and +\f{ANTICOMMUTE} \index{ANTICOMMUTE} have been defined. +Example (is included as example 1 in the test file): \\ + +\begin{framedverbatim} +VECOP P,A,K; +PHYSINDEX X,Y; +FOR ALL X,Y LET COMM(P(X),A(Y))=K(X)*A(Y); +COMMUTE(P**2,P DOT A); +\end{framedverbatim} + +\subsubsection{Adjoint expressions} + +As has been already mentioned, for each operator and state defined +using the declaration commands quoted in section 3.1, the system +generates automatically the corresponding adjoint operator. For the +calculation of the adjoint representation of a complicated +operator expression, a function \f{ADJ} \index{ADJ} has been defined. +Example\footnote{This shows how adjoint operators are printed out +when the switch \f{NAT} is on}: \\ + +\begin{framedverbatim} +SCALOP A,B; +ADJ(A*B); + + + + --> (B )*(A ) +\end{framedverbatim} + +\subsubsection{Application of operators on states} + +For this purpose, a function \f{OPAPPLY} \index{OPAPPLY} has been +defined. +It has 2 arguments and is used in the following combinations: \\ + +{\bf (i)} \f{LET OPAPPLY(}{\it operator, state}\f{) =} {\it state}; +This is to define a elementary +action of an operator on a state in analogy to the way +elementary commutation relations are introduced to the system. +Example: \\ + +\begin{framedverbatim} +SCALOP A; STATE U; +FOR ALL N,P LET OPAPPLY((A(N),U(P))= EXP(I*N*P)*U(P); +\end{framedverbatim} + +{\bf (ii)} \f{LET OPAPPLY(}{\it state, state}\f{) =} {\it scalar exp.}; +This form is to define scalar products between states and normalization +conditions. +Example: \\ + +\begin{framedverbatim} +STATE U; +FOR ALL N,M LET OPAPPLY(U(N),U(M)) = IF N=M THEN 1 ELSE 0; +\end{framedverbatim} + +{\bf (iii)} {\it state} \f{:= OPAPPLY(}{\it operator expression, state}); + In this way, the action of an operator expression on a given state +is calculated using elementary relations defined as explained in {\bf +(i)}. The result may be assigned to a different state vector. + +{\bf (iv)} \f{OPAPPLY(}{\it state}\f{, OPAPPLY(}{\it operator expression, +state}\f{))}; This is the way how to calculate matrix elements of +operator +expressions. The system proceeds in the following way: first the +rightmost operator is applied on the right state, which means that the +system tries +to find an elementary relation which match the application of the +operator on the state. If it fails +the system tries to apply the leftmost operator of the expression on the +left state using the adjoint representations. If this fails also, +the system prints out a warning message and stops the evaluation. +Otherwise the next operator occuring in the expression is +taken and so on until the complete expression is applied. Then the +system +looks for a relation expressing the scalar product of the two +resulting states and prints out the final result. An example of such +a calculation is given in the test file. + +The infix version of the \f{OPAPPLY} function is the vertical bar $\mid$ +. It is \underline{right} associative and placed in the precedence +list just above the minus ($-$) operator. +Some of the \REDUCE\ implementation may not work with this character, +the prefix form should then be used instead\footnote{The source code +can also be modified to choose another special character for the +function}. + +\section{Known problems in the current release of PHYSOP} + +\indent {\bf (i)} Some spurious negative powers of operators +may appear +in the result of a calculation using the PHYSOP package. This is a +purely ''cosmetic'' effect which is due to an additional +factorization of the expression in the output printing routines of +\REDUCE. Setting off the \REDUCE\ switch \f{ALLFAC} (\f{ALLFAC} is normally +on) +should make these +terms disappear and print out the correct result (see example 1 +in the test file). + +{\bf (ii)} The current release of the PHYSOP package is not optimized +w.r.t. computation speed. Users should be aware that the evaluation +of complicated expressions involving a lot of commutation relations +requires a significant amount of CPU time \underline{and} memory. +Therefore the use of PHYSOP on small machines is rather limited. A +minimal hardware configuration should include at least 4 MB of +memory and a reasonably fast CPU (type Intel 80386 or equiv.). + +{\bf (iii)} Slightly different ordering of operators (especially with +multiple occurrences of the same operator with different indices) +may appear in some calculations +due to the internal ordering of atoms in the underlying LISP system +(see last example in the test file). This cannot be entirely avoided +by the package but does not affect the correctness of the results. + +\section{Compilation of the packages} +To build a fast loading module of the NONCOM2 package, enter the +following commands after starting the \REDUCE\ system: \\ + +\begin{framedverbatim} + faslout "noncom2"; + in "noncom2.red"; + faslend; +\end{framedverbatim} +To build a fast loading module of the PHYSOP package, enter the +following commands after starting the \REDUCE\ system: \\ + +\begin{framedverbatim} + faslout "physop"; + in "noncom2.red"; + in "physop.red"; + faslend; +\end{framedverbatim} +Input and output file specifications may change according to the +underlying operating system. \\ +On PSL--based systems, a spurious message: \\ + +\begin{framedverbatim} +*** unknown function PHYSOP!*SQ called from compiled code +\end{framedverbatim} +may appear during the compilation of the PHYSOP package. This warning +has no effect on the functionality of the package. + +\section{Final remarks} +The package PHYSOP has been presented by +the author at the IV inter. Conference on Computer Algebra in Physical +Research, Dubna (USSR) 1990 (see M. Warns, {\it +Software Extensions of \REDUCE\ for Operator Calculus in Quantum Theory}, +Proc.\ of the IV inter.\ Conf.\ on Computer Algebra in Physical +Research, Dubna 1990, to appear). It has been developed with the aim in +mind to perform calculations of the type exemplified in the test file +included in the distribution of this package. +However it should +also be useful in some other domains like e.g.\ the calculations of +complicated Feynman diagrams in QCD which could not be performed using +the HEPHYS package. The author is therefore grateful for any +suggestion +to improve or extend the usability of the package. Users should not +hesitate to contact the author for additional help and explanations on +how to use +this package. Some bugs may also +appear which have not been discovered during the tests performed +prior to the release of this version. Please send in this case to the +author a short +input and output listing displaying the encountered problem. + +\section*{Acknowledgements} +The main ideas for the implementation of a new data type in the \REDUCE\ +environnement have been taken from the VECTOR package developed by +Dr.\ David Harper (D. Harper, Comp.\ Phys.\ Comm.\ {\bf 54} (1989) +295). +Useful discussions with Dr.\ Eberhard Schr\"ufer and +Prof.\ John Fitch are also gratefully acknowledged. + +\appendix + +\section{List of error and warning messages} +In the following the error (E) and warning (W) messages specific to the +PHYSOP package are listed. +\begin{description} +\item[\f{cannot declare} {\it x}\f{ as }{\it data type}] (W): + An attempt has been made to declare an +object {\it x} which cannot be used as a PHYSOP operator of the +required type. The declaration command is ignored. + +\item [{\it x} \f{already defined as} {\it data type}] (W): The object +{\it x} has already been declared using a \REDUCE\ type declaration +command and can therefore not be used as a PHYSOP operator. +The declaration command is ignored. + +\item [{\it x} \f{already declared as} {\it data type}] (W): The object +\f{x} has already been declared with a PHYSOP declaration command. +The declaration command is ignored. + +\item[{\it x} \f{is not a PHYSOP}] (E): An invalid argument has been +included in an \f{OPORDER} command. Check the arguments. + +\item[\f{invalid argument(s) to }{\it function}] (E): A +function implemented by the PHYSOP package has been called with an +invalid argument. Check type of arguments. + + +\item[\f{Type conflict in }{\it operation}] (E): A PHYSOP type conflict +has occured during an arithmetic operation. Check the arguments. + +\item [\f{invalid call of }{\it function} \f{with args:} {\it arguments}] +(E): A function +of the PHYSOP package has been declared with invalid argument(s). Check +the argument list. + +\item[\f{type mismatch in} {\it expression}] (E): A type mismatch has +been detected in an expression. Check the corresponding expression. + +\item[\f{type mismatch in} {\it assignement}] (E): A type +mismatch has been detected in an assignment or in a \f{LET} +statement. Check the listed statement. + +\item[\f{PHYSOP type conflict in} {\it expr}] (E): A ambiguity has been +detected during the type analysis of the expression. Check the +expression. + +\item[\f{operators in exponent cannot be handled}] (E): An operator has +occurred in the exponent of an expression. + +\item[\f{cannot raise a state to a power}] (E): states cannot be +exponentiated by the system. + +\item[\f{invalid quotient}] (E): An invalid denominator has occurred in a +quotient. Check the expression. + +\item[\f{physops of different types cannot be commuted}] (E): An invalid +operator has occurred in a call of the \f{COMMUTE}/\f{ANTICOMMUTE} function. + +\item[\f{commutators only implemented between scalar operators}] (E): +An invalid operator has occurred in the call of the +\f{COMMUTE}/\f{ANTICOMMUTE} function. + +\item[\f{evaluation incomplete due to missing elementary relations}] (W): +\\ +The system has not found all +the elementary commutators or application relations necessary to +calculate or reorder the input expression. The result may however be +used for further calculations. +\end{description} + +\section{List of available commands} +\printindex +\end{document} Index: r36/doc/PM.DOC ================================================================== --- r36/doc/PM.DOC +++ r36/doc/PM.DOC @@ -1,284 +1,284 @@ - - - PM - A REDUCE Pattern Matcher - - - Kevin McIsaac - - The University of Western Australia - and - The RAND Corporation - - kevin@wri.com - - -PM is a general pattern matcher similar in style to those found in systems -such as SMP and Mathematica, and is based on the pattern matcher described -in Kevin McIsaac, "Pattern Matching Algebraic Identities", SIGSAM Bulletin, -19 (1985), 4-13. The following is a description of its structure. - -A template is any expression composed of literal elements (e.g. "5", "a" or -"a+1") and specially denoted pattern variables (e.g. ?a or ??b). Atoms -beginning with `?' are called generic variables and match any expression. -Atoms beginning with `??' are called multi-generic variables and match any -expression or any sequence of expressions including the null or empty -sequence. A sequence is an expression of the form `[a1, a2,...]'. When -placed in a function argument list the brackets are removed, i.e. f([a,1]) --> f(a,1) and f(a,[1,2],b) -> f(a,1,2,b). - -A template is said to match an expression if the template is literally -equal to the expression or if by replacing any of the generic or -multi-generic symbols occurring in the template, the template can be made -to be literally equal to the expression. These replacements are called the -bindings for the generic variables. A replacement is an expression of the -form `exp1 -> exp2', which means exp1 is replaced by exp2, or `exp1 --> -exp2', which is the same except exp2 is not simplified until after the -substitution for exp1 is made. If the expression has any of the -properties; associativity, commutativity, or an identity element, they are -used to determine if the expressions match. If an attempt to match the -template to the expression fails the matcher backtracks, unbinding generic -variables, until it reached a place were it can make a different choice. -It then proceeds along the new branch. - -The current matcher proceeds from left to right in a depth first search of -the template expression tree. Rearrangements of the expression are -generated when the match fails and the matcher backtracks. - -The matcher also supports semantic matching. Briefly, if a subtemplate -does not match the corresponding subexpression because they have different -structures then the two are equated and the matcher continues matching the -rest of the expression until all the generic variables in the subexpression -are bound. The equality is then checked. This is controlled by the switch -`semantic'. By default it is on. - -M(exp,temp) - - The template, temp, is matched against the expression, exp. If the - template is literally equal to the expression `T' is returned. If the - template is literally equal to the expression after replacing the - generic variables by their bindings then the set of bindings is returned - as a set of replacements. Otherwise 0 (nil) is returned. - -Examples: - - A "literal" template - m(f(a),f(a)); - T - - Not literally equal - m(f(a),f(b)); - 0 - - Nested operators - m(f(a,h(b)),f(a,h(b))); - T - - a "generic" template - m(f(a,b),f(a,?a)); - {?A->B} - - m(f(a,b),f(?a,?b)); - {?B->B,?A->A} - - The Multi-Generic symbol, ??a, takes "rest" of arguments - m(f(a,b),f(??a)); - {??A->[A,B]} - - but the Generic symbol, ?a, does not - m(f(a,b),f(?a)); - 0 - - Flag h as associative - flag('(h),'assoc); - Associativity is used to "group" terms together - m(h(a,b,d,e),h(?a,d,?b)); - {?B->E,?A->H(A,B)} - - "plus" is a symmetric function - m(a+b+c,c+?a+?b); - {?B->A,?A->B} - - it is also associative - m(a+b+c,b+?a); - {?A->C + A} - - Note the affect of using multi-generic symbol is different - m(a+b+c,b+??c); - {??C->[C,A]} - -temp _= logical-exp - - A template may be qualified by the use of the conditional operator `_=', - such!-that. When a such!-that condition is encountered in a template it - is held until all generic variables appearing in logical-exp are bound. - On the binding of the last generic variable logical-exp is simplified - and if the result is not `T' the condition fails and the pattern matcher - backtracks. When the template has been fully parsed any remaining held - such-that conditions are evaluated and compared to `T'. - -Examples: - - m(f(a,b),f(?a,?b_=(?a=?b))); - 0 - - m(f(a,a),f(?a,?b_=(?a=?b))); - {?B->A,?A->A} - - Note that f(?a,?b_=(?a=?b)) is the same as f(?a,?a) - -S(exp,{temp1->sub1,temp2->sub2,...},rept, depth) - - Substitute the set of replacements into exp, resubstituting a maximum of - 'rept' times and to a maximum depth 'depth'. 'Rept' and 'depth' have the - default values of 1 and infinity respectively. Essentially S is a - breadth first search and replace. - - Each template is matched against exp until a successful match occurs. - Any replacements for generic variables are applied to the rhs of that - replacement and exp is replaced by the rhs. The substitution process is - restarted on the new expression starting with the first replacement. If - none of the templates match exp then the first replacement is tried - against each sub-expression of exp. If a matching template is found - then the sub-expression is replaced and process continues with the next - sub-expression. - - When all sub-expressions have been examined, if a match was found, the - expression is evaluated and the process is restarted on the - sub-expressions of the resulting expression, starting with the first - replacement. When all sub-expressions have been examined and no match - found the sub-expressions are reexamined using the next replacement. - Finally when this has been done for all replacements and no match found - then the process recures on each sub-expression. - - The process is terminated after rept replacements or when the expression - no longer changes. - -Si(exp,{temp1->sub1,temp2->sub2,...}, depth) - - Substitute infinitely many times until expression stops changing. - Short hand notation for S(exp,{temp1->sub1,temp2->sub2,...},Inf, - depth) - -Sd(exp,{temp1->sub1,temp2->sub2,...},rept, depth) - - Depth first version of Substitute. - -Examples: - - s(f(a,b),f(a,?b)->?b^2); - 2 - B - - s(a+b,a+b->a*b); - B*A - - "associativity" is used to group a+b+c in to (a+b) + c - s(a+b+c,a+b->a*b); - B*A + C - -The next three examples use a rule set that defines the factorial function. - Substitute once - s(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)}); - 3*NFAC(2) - - Substitute twice - s(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)},2); - 6*NFAC(1) - - Substitute until expression stops changing - si(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)}); - 6 - - Only substitute at the top level - s(a+b+f(a+b),a+b->a*b,inf,0); - F(B + A) + B*A - - - -temp :- exp - - If during simplification of an expression, temp matches some - sub-expression then that sub-expression is replaced by exp. If there is - a choice of templates to apply the least general is used. - - If a old rule exists with the same template then the old rule is - replaced by the new rule. If exp is `nil' the rule is retracted. - -temp ::- exp - - Same as temp :- exp, but the lhs is not simplified until the replacement - is made - - Examples: - -Define the factorial function of a natural number as a recursive function -and a termination condition. For all other values write it as a Gamma -Function. Note that the order of definition is not important as the rules -are reordered so that the most specific rule is tried first. - - Note the use of `::-' instead of `:-' to stop simplification of - the LHS. Hold stops its arguments from being simplified. - fac(?x_=Natp(?x)) ::- ?x*fac(?x-1); - HOLD(FAC(?X-1)*?X) - - fac(0) :- 1; - 1 - - fac(?x) :- Gamma(?x+1); - GAMMA(?X + 1) - - fac(3); - 6 - - fac(3/2); - GAMMA(5/2) - -Arep({rep1,rep2,..}) - - In future simplifications automatically apply replacements re1, - rep2... until the rules are retracted. In effect it replaces the - operator `->' by `:-' in the set of replacements {rep1, rep2,...}. - -Drep({rep1,rep2,..}) - - Delete the rules rep1, rep2,... - -As we said earlier, the matcher has been constructed along the lines of the -pattern matcher described in McIsaac with the addition of such-that -conditions and `semantic matching' as described in Grief. To make a -template efficient some consideration should be given to the structure of -the template and the position of such-that statements. In general the -template should be constructed to that failure to match is recognize as -early as possible. The multi-generic symbol should be used when ever -appropriate, particularly with symmetric functions. For further details -see McIsaac. - -Examples: - - f(?a,?a,?b) is better that f(?a,?b,?c_=(?a=?b)) - ?a+??b is better than ?a+?b+?c... - The template, f(?a+?b,?a,?b), matched against f(3,2,1) is - matched as f(?e_=(?e=?a+?b),?a,?b) when semantic matching is allowed. - - - Switches - -------- - -TRPM - Produces a trace of the rules applied during a substitution. This is - useful to see how the pattern matcher works, or to understand an - unexpected result. - -In general usage the following switches need not be considered. - -SEMANTIC - Allow semantic matches, e.g. f(?a+?b,?a,?b) will match f(3,2,1) even - though the matcher works from left to right. - -SYM!-ASSOC - Limits the search space of symmetric associative functions when the - template contains multi-generic symbols so that generic symbols will not - the function. For example: m(a+b+c,?a+??b) will return {?a -> a, ??b-> - [b,c]} or {?a -> b, ??b-> [a,c]} or {?a -> c, ??b-> [a,b]} but no {?a -> - a+b, ??b-> c} etc. No sane template should require these types of - matches. However they can be made available by turning the switch off. + + + PM - A REDUCE Pattern Matcher + + + Kevin McIsaac + + The University of Western Australia + and + The RAND Corporation + + kevin@wri.com + + +PM is a general pattern matcher similar in style to those found in systems +such as SMP and Mathematica, and is based on the pattern matcher described +in Kevin McIsaac, "Pattern Matching Algebraic Identities", SIGSAM Bulletin, +19 (1985), 4-13. The following is a description of its structure. + +A template is any expression composed of literal elements (e.g. "5", "a" or +"a+1") and specially denoted pattern variables (e.g. ?a or ??b). Atoms +beginning with `?' are called generic variables and match any expression. +Atoms beginning with `??' are called multi-generic variables and match any +expression or any sequence of expressions including the null or empty +sequence. A sequence is an expression of the form `[a1, a2,...]'. When +placed in a function argument list the brackets are removed, i.e. f([a,1]) +-> f(a,1) and f(a,[1,2],b) -> f(a,1,2,b). + +A template is said to match an expression if the template is literally +equal to the expression or if by replacing any of the generic or +multi-generic symbols occurring in the template, the template can be made +to be literally equal to the expression. These replacements are called the +bindings for the generic variables. A replacement is an expression of the +form `exp1 -> exp2', which means exp1 is replaced by exp2, or `exp1 --> +exp2', which is the same except exp2 is not simplified until after the +substitution for exp1 is made. If the expression has any of the +properties; associativity, commutativity, or an identity element, they are +used to determine if the expressions match. If an attempt to match the +template to the expression fails the matcher backtracks, unbinding generic +variables, until it reached a place were it can make a different choice. +It then proceeds along the new branch. + +The current matcher proceeds from left to right in a depth first search of +the template expression tree. Rearrangements of the expression are +generated when the match fails and the matcher backtracks. + +The matcher also supports semantic matching. Briefly, if a subtemplate +does not match the corresponding subexpression because they have different +structures then the two are equated and the matcher continues matching the +rest of the expression until all the generic variables in the subexpression +are bound. The equality is then checked. This is controlled by the switch +`semantic'. By default it is on. + +M(exp,temp) + + The template, temp, is matched against the expression, exp. If the + template is literally equal to the expression `T' is returned. If the + template is literally equal to the expression after replacing the + generic variables by their bindings then the set of bindings is returned + as a set of replacements. Otherwise 0 (nil) is returned. + +Examples: + + A "literal" template + m(f(a),f(a)); + T + + Not literally equal + m(f(a),f(b)); + 0 + + Nested operators + m(f(a,h(b)),f(a,h(b))); + T + + a "generic" template + m(f(a,b),f(a,?a)); + {?A->B} + + m(f(a,b),f(?a,?b)); + {?B->B,?A->A} + + The Multi-Generic symbol, ??a, takes "rest" of arguments + m(f(a,b),f(??a)); + {??A->[A,B]} + + but the Generic symbol, ?a, does not + m(f(a,b),f(?a)); + 0 + + Flag h as associative + flag('(h),'assoc); + Associativity is used to "group" terms together + m(h(a,b,d,e),h(?a,d,?b)); + {?B->E,?A->H(A,B)} + + "plus" is a symmetric function + m(a+b+c,c+?a+?b); + {?B->A,?A->B} + + it is also associative + m(a+b+c,b+?a); + {?A->C + A} + + Note the affect of using multi-generic symbol is different + m(a+b+c,b+??c); + {??C->[C,A]} + +temp _= logical-exp + + A template may be qualified by the use of the conditional operator `_=', + such!-that. When a such!-that condition is encountered in a template it + is held until all generic variables appearing in logical-exp are bound. + On the binding of the last generic variable logical-exp is simplified + and if the result is not `T' the condition fails and the pattern matcher + backtracks. When the template has been fully parsed any remaining held + such-that conditions are evaluated and compared to `T'. + +Examples: + + m(f(a,b),f(?a,?b_=(?a=?b))); + 0 + + m(f(a,a),f(?a,?b_=(?a=?b))); + {?B->A,?A->A} + + Note that f(?a,?b_=(?a=?b)) is the same as f(?a,?a) + +S(exp,{temp1->sub1,temp2->sub2,...},rept, depth) + + Substitute the set of replacements into exp, resubstituting a maximum of + 'rept' times and to a maximum depth 'depth'. 'Rept' and 'depth' have the + default values of 1 and infinity respectively. Essentially S is a + breadth first search and replace. + + Each template is matched against exp until a successful match occurs. + Any replacements for generic variables are applied to the rhs of that + replacement and exp is replaced by the rhs. The substitution process is + restarted on the new expression starting with the first replacement. If + none of the templates match exp then the first replacement is tried + against each sub-expression of exp. If a matching template is found + then the sub-expression is replaced and process continues with the next + sub-expression. + + When all sub-expressions have been examined, if a match was found, the + expression is evaluated and the process is restarted on the + sub-expressions of the resulting expression, starting with the first + replacement. When all sub-expressions have been examined and no match + found the sub-expressions are reexamined using the next replacement. + Finally when this has been done for all replacements and no match found + then the process recures on each sub-expression. + + The process is terminated after rept replacements or when the expression + no longer changes. + +Si(exp,{temp1->sub1,temp2->sub2,...}, depth) + + Substitute infinitely many times until expression stops changing. + Short hand notation for S(exp,{temp1->sub1,temp2->sub2,...},Inf, + depth) + +Sd(exp,{temp1->sub1,temp2->sub2,...},rept, depth) + + Depth first version of Substitute. + +Examples: + + s(f(a,b),f(a,?b)->?b^2); + 2 + B + + s(a+b,a+b->a*b); + B*A + + "associativity" is used to group a+b+c in to (a+b) + c + s(a+b+c,a+b->a*b); + B*A + C + +The next three examples use a rule set that defines the factorial function. + Substitute once + s(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)}); + 3*NFAC(2) + + Substitute twice + s(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)},2); + 6*NFAC(1) + + Substitute until expression stops changing + si(nfac(3),{nfac(0)->1,nfac(?x)->?x*nfac(?x-1)}); + 6 + + Only substitute at the top level + s(a+b+f(a+b),a+b->a*b,inf,0); + F(B + A) + B*A + + + +temp :- exp + + If during simplification of an expression, temp matches some + sub-expression then that sub-expression is replaced by exp. If there is + a choice of templates to apply the least general is used. + + If a old rule exists with the same template then the old rule is + replaced by the new rule. If exp is `nil' the rule is retracted. + +temp ::- exp + + Same as temp :- exp, but the lhs is not simplified until the replacement + is made + + Examples: + +Define the factorial function of a natural number as a recursive function +and a termination condition. For all other values write it as a Gamma +Function. Note that the order of definition is not important as the rules +are reordered so that the most specific rule is tried first. + + Note the use of `::-' instead of `:-' to stop simplification of + the LHS. Hold stops its arguments from being simplified. + fac(?x_=Natp(?x)) ::- ?x*fac(?x-1); + HOLD(FAC(?X-1)*?X) + + fac(0) :- 1; + 1 + + fac(?x) :- Gamma(?x+1); + GAMMA(?X + 1) + + fac(3); + 6 + + fac(3/2); + GAMMA(5/2) + +Arep({rep1,rep2,..}) + + In future simplifications automatically apply replacements re1, + rep2... until the rules are retracted. In effect it replaces the + operator `->' by `:-' in the set of replacements {rep1, rep2,...}. + +Drep({rep1,rep2,..}) + + Delete the rules rep1, rep2,... + +As we said earlier, the matcher has been constructed along the lines of the +pattern matcher described in McIsaac with the addition of such-that +conditions and `semantic matching' as described in Grief. To make a +template efficient some consideration should be given to the structure of +the template and the position of such-that statements. In general the +template should be constructed to that failure to match is recognize as +early as possible. The multi-generic symbol should be used when ever +appropriate, particularly with symmetric functions. For further details +see McIsaac. + +Examples: + + f(?a,?a,?b) is better that f(?a,?b,?c_=(?a=?b)) + ?a+??b is better than ?a+?b+?c... + The template, f(?a+?b,?a,?b), matched against f(3,2,1) is + matched as f(?e_=(?e=?a+?b),?a,?b) when semantic matching is allowed. + + + Switches + -------- + +TRPM + Produces a trace of the rules applied during a substitution. This is + useful to see how the pattern matcher works, or to understand an + unexpected result. + +In general usage the following switches need not be considered. + +SEMANTIC + Allow semantic matches, e.g. f(?a+?b,?a,?b) will match f(3,2,1) even + though the matcher works from left to right. + +SYM!-ASSOC + Limits the search space of symmetric associative functions when the + template contains multi-generic symbols so that generic symbols will not + the function. For example: m(a+b+c,?a+??b) will return {?a -> a, ??b-> + [b,c]} or {?a -> b, ??b-> [a,c]} or {?a -> c, ??b-> [a,b]} but no {?a -> + a+b, ??b-> c} etc. No sane template should require these types of + matches. However they can be made available by turning the switch off. Index: r36/doc/RANDPOLY.TEX ================================================================== --- r36/doc/RANDPOLY.TEX +++ r36/doc/RANDPOLY.TEX @@ -1,506 +1,506 @@ -\documentstyle[11pt]{article} - -\title{RANDPOLY: A Random Polynomial Generator} - -\author{Francis J. Wright \\ -School of Mathematical Sciences \\ -Queen Mary and Westfield College \\ -University of London \\ -Mile End Road, London E1 4NS, UK. \\ -Email: {\tt F.J.Wright@QMW.ac.uk}} - -\date{14 July 1994} - -\begin{document} -\maketitle - -\begin{abstract} - This package is based on a port of the Maple random polynomial - generator together with some support facilities for the generation - of random numbers and anonymous procedures. -\end{abstract} - - -\section{Introduction} - -The operator {\tt randpoly} is based on a port of the Maple random -polynomial generator. In fact, although by default it generates a -univariate or multivariate polynomial, in its most general form it -generates a sum of products of arbitrary integer powers of the -variables multiplied by arbitrary coefficient expressions, in which -the variable powers and coefficient expressions are the results of -calling user-supplied functions (with no arguments). Moreover, the -``variables'' can be arbitrary expressions, which are composed with -the underlying polynomial-like function. - -The user interface, code structure and algorithms used are essentially -identical to those in the Maple version. The package also provides an -analogue of the Maple {\tt rand} random-number-generator generator, -primarily for use by {\tt randpoly}. There are principally two -reasons for translating these facilities rather than designing -comparable facilites anew: (1) the Maple design seems satisfactory and -has already been ``proven'' within Maple, so there is no good reason -to repeat the design effort; (2) the main use for these facilities is -in testing the performance of other algebraic code, and there is an -advantage in having essentially the same test data generator -implemented in both Maple and REDUCE\@. Moreover, it is interesting -to see the extent to which a facility can be translated without change -between two systems. (This aspect will be described elsewhere.) - -Sections \ref{sec:Basic} and \ref{sec:Advanced} describe respectively -basic and more advanced use of {\tt randpoly}; \S\ref{sec:Subsidiary} -describes subsidiary functions provided to support advanced use of -{\tt randpoly}; \S\ref{sec:Examples} gives examples; an appendix gives -some details of the only non-trivial algorithm, that used to compute -random sparse polynomials. Additional examples of the use of {\tt -randpoly} are given in the test and demonstration file {\tt -randpoly.tst}. - - -\section{Basic use of {\tt randpoly}} -\label{sec:Basic} - -The operator {\tt randpoly} requires at least one argument -corresponding to the polynomial variable or variables, which must be -either a single expression or a list of expressions.% -\footnote{If it is a single expression then the univariate code is -invoked; if it is a list then the multivariate code is invoked, and in -the special case of a list of one element the multivariate code is -invoked to generate a univariate polynomial, but the result should be -indistinguishable from that resulting from specifying a single -expression not in a list.} % -In effect, {\tt randpoly} replaces each input expression by an -internal variable and then substitutes the input expression for the -internal variable in the generated polynomial (and by default expands -the result as usual), although in fact if the input expression is a -REDUCE kernel then it is used directly. The rest of this document -uses the term ``variable'' to refer to a general input expression or -the internal variable used to represent it, and all references to the -polynomial structure, such as its degree, are with respect to these -internal variables. The actual degree of a generated polynomial might -be different from its degree in the internal variables. - -By default, the polynomial generated has degree 5 and contains 6 -terms. Therefore, if it is univariate it is dense whereas if it is -multivariate it is sparse. - - -\subsection{Optional arguments} - -Other arguments can optionally be specified, in any order, after the -first compulsory variable argument. All arguments receive full -algebraic evaluation, subject to the current switch settings etc. The -arguments are processed in the order given, so that if more than one -argument relates to the same property then the last one specified -takes effect. Optional arguments are either keywords or equations -with keywords on the left. - -In general, the polynomial is sparse by default, unless the keyword -{\tt dense} is specified as an optional argument. (The keyword {\tt -sparse} is also accepted, but is the default.) The default degree can -be changed by specifying an optional argument of the form -\begin{center} - {\tt degree = {\it natural number}}. -\end{center} -In the multivariate case this is the total degree, i.e.\ the sum of -the degrees with respect to the individual variables. The keywords -{\tt deg} and {\tt maxdeg} can also be used in place of {\tt degree}. -More complicated monomial degree bounds can be constructed by using -the coefficient function described below to return a monomial or -polynomial coefficient expression. Moreover, {\tt randpoly} respects -internally the REDUCE ``asymptotic'' commands {\tt let}, {\tt weight} -etc.\ described in \S10.4 of the \REDUCE 3.6 manual, which can be used -to exercise additional control over the polynomial generated. - -In the sparse case (only), the default maximum number of terms -generated can be changed by specifying an optional argument of the -form -\begin{center} - {\tt terms = {\it natural number}}. -\end{center} -The actual number of terms generated will be the minimum of the value -of {\tt terms} and the number of terms in a dense polynomial of the -specified degree, number of variables, etc. - - -\section{Advanced use of {\tt randpoly}} -\label{sec:Advanced} - -The default order (or minimum or trailing degree) can be changed by -specifying an optional argument of the form -\begin{center} - {\tt ord = {\it natural number}}. -\end{center} -The keyword is {\tt ord} rather than {\tt order} because {\tt order} -is a reserved command name in REDUCE\@. The keyword {\tt mindeg} can -also be used in place of {\tt ord}. In the multivariate case this is -the total degree, i.e.\ the sum of the degrees with respect to the -individual variables. The order normally defaults to 0. - -However, the input expressions to {\tt randpoly} can also be -equations, in which case the order defaults to 1 rather than 0. Input -equations are converted to the difference of their two sides before -being substituted into the generated polynomial. The purpose of this -facility is to easily generate polynomials with a specified zero -- for -example -\begin{center}\tt - randpoly(x = a); -\end{center} -generates a polynomial that is guaranteed to vanish at $x = a$, but is -otherwise random. - -Order specification and equation input are extensions of the current -Maple version of {\tt randpoly}. - -The operator {\tt randpoly} accepts two further optional arguments in -the form of equations with the keywords {\tt coeffs} and {\tt expons} -on the left. The right sides of each of these equations must evaluate -to objects that can be applied as functions of no variables. These -functions should be normal algebraic procedures (or something -equivalent); the {\tt coeffs} procedure may return any algebraic -expression, but the {\tt expons} procedure must return an integer -(otherwise {\tt randpoly} reports an error). The values returned by -the functions should normally be random, because it is the randomness -of the coefficients and, in the sparse case, of the exponents that -makes the constructed polynomial random. - -A convenient special case is to use the function {\tt rand} on the -right of one or both of these equations; when called with a single -argument {\tt rand} returns an anonymous function of no variables that -generates a random integer. The single argument of {\tt rand} should -normally be an integer range in the form $a~..~b$, where $a$, $b$ are -integers such that $a < b$. The spaces around (or at least before) -the infix operator ``..'' are necessary in some cases in REDUCE and -generally recommended. For example, the {\tt expons} argument might -take the form -\begin{center}\tt - expons = rand(0~..~n) -\end{center} -where {\tt n} will be the maximum degree with respect to each variable -{\em independently}. In the case of {\tt coeffs} the lower limit will -often be the negative of the upper limit to give a balanced -coefficient range, so that the {\tt coeffs} argument might take the -form -\begin{center}\tt - coeffs = rand(-n~..~n) -\end{center} -which will generate random integer coefficients in the range $[-n,n]$. - - -\section{Subsidiary functions: rand, proc, random} -\label{sec:Subsidiary} - -\subsection{Rand: a random-number-generator generator} - -The first argument of {\tt rand} must be either an integer range in -the form $a~..~b$, where $a$, $b$ are integers such that $a < b$, or a -positive integer $n$ which is equivalent to the range $0~..~n-1$. The -operator {\tt rand} constructs a function of no arguments that calls -the REDUCE random number generator function {\tt random} to return a -random integer in the range specified; in the case that the first -argument of {\tt rand} is a single positive integer $n$ the function -constructed just calls {\tt random($n$)}, otherwise the call of {\tt -random} is scaled and shifted. - -As an additional convenience, if {\tt rand} is called with a second -argument that is an identifier then the call of {\tt rand} acts -exactly like a procedure definition with the identifier as the -procedure name. The procedure generated can then be called with an -empty argument list by the algebraic processor. - -[Note that {\tt rand()} with no argument is an error in REDUCE and -does not return directly a random number in a default range as it does -in Maple -- use instead the REDUCE function {\tt random} (see below).] - - -\subsection{Proc: an anonymous procedure generator} - -The operator {\tt proc} provides a generalization of {\tt rand}, and -is primarily intended to be used with expressions involving the {\tt -random} function (see below). Essentially, it provides a mechanism to -prevent functions such as {\tt random} being evaluated when the -arguments to {\tt randpoly} are evaluated, which is too early. {\tt -Proc} accepts a single argument which is converted into the body of an -anonymous procedure, which is returned as the value of {\tt proc}. -(If a named procedure is required then the normal REDUCE {\tt -procedure} statement should be used instead.) Examples are given in -the following sections, and in the file {\tt randpoly.tst}. - - -\subsection{Random: a generalized interface} - -As an additional convenience, this package extends the interface to -the standard REDUCE {\tt random} function so that it will directly -accept either a natural number or an integer range as its argument, -exactly as for the first argument of {\tt rand}. Hence effectively -\begin{center}\tt - rand(X) = proc random(X) -\end{center} -although {\tt rand} is marginally more efficient. However, {\tt proc} -and the generalized {\tt random} interface allow expressions such as -the following anonymous random fraction generator to be easily -constructed: -\begin{center}\tt - proc(random(-99~..~99)/random(1~..~99)) -\end{center} - - -\subsection{Further support for procs} - -{\tt Rand} is a special case of {\tt proc}, and (for either) if the -switch {\tt comp} is {\tt on} (and the compiler is available) then the -generated procedure body is compiled. - -{\tt Rand} with a single argument and {\tt proc} both return as their -values anonymous procedures, which if they are not compiled are Lisp -lambda expressions. However, if compilation is in effect then they -return only an identifier that has no external significance% -\footnote{It is not interned on the oblist.} % -but which can be applied as a function in the same way as a lambda -expression. - -It is primarily intended that such ``proc expressions'' will be used -immediately as input to {\tt randpoly}. The algebraic processor is -not intended to handle lambda expressions. However, they can be -output or assigned to variables in algebraic mode, although the output -form looks a little strange and is probably best not displayed. But -beware that lambda expressions cannot be evaluated by the algebraic -processor (at least, not without declaring some internal Lisp -functions to be algebraic operators). Therefore, for testing purposes -or curious users, this package provides the operators {\tt showproc} -and {\tt evalproc} respectively to display and evaluate ``proc -expressions'' output by {\tt rand} or {\tt proc} (or in fact any -lambda expression), in the case of {\tt showproc} provided they are -not compiled. - - -\section{Examples} -\label{sec:Examples} - -The file {\tt randpoly.tst} gives a set of test and demonstration -examples. - -The following additional examples were taken from the Maple {\tt -randpoly} help file and converted to REDUCE syntax by replacing [~] by -\{~\} and making the other changes shown explicitly: -\begin{verbatim} -randpoly(x); - - 5 4 3 2 - - 54*x - 92*x - 30*x + 73*x - 69*x - 67 - - -randpoly({x, y}, terms = 20); - - 5 4 4 3 2 3 3 -31*x - 17*x *y - 48*x - 15*x *y + 80*x *y + 92*x - - 2 3 2 2 4 3 2 - + 86*x *y + 2*x *y - 44*x + 83*x*y + 85*x*y + 55*x*y - - 5 4 3 2 - - 27*x*y + 33*x - 98*y + 51*y - 2*y + 70*y - 60*y - 10 - - -randpoly({x, sin(x), cos(x)}); - - 4 3 3 -sin(x)*( - 4*cos(x) - 85*cos(x) *x + 50*sin(x) - - 2 - - 20*sin(x) *x + 76*sin(x)*x + 96*sin(x)) - - -% randpoly(z, expons = rand(-5..5)); % Maple -% A generalized random "polynomial"! -% Note that spaces are needed around .. in REDUCE. -on div; off allfac; -randpoly(z, expons = rand(-5 .. 5)); - - 4 3 -3 -4 -5 - - 39*z + 14*z - 77*z - 37*z - 8*z - -off div; on allfac; -% randpoly([x], coeffs = proc() randpoly(y) end); % Maple -randpoly({x}, coeffs = proc randpoly(y)); - - 5 5 5 4 5 3 5 2 5 5 -95*x *y - 53*x *y - 78*x *y + 69*x *y + 58*x *y - 58*x - - 4 5 4 4 4 3 4 2 4 - + 64*x *y + 93*x *y - 21*x *y + 24*x *y - 13*x *y - - 4 3 5 3 4 3 3 3 2 - - 28*x - 57*x *y - 78*x *y - 44*x *y + 37*x *y - - 3 3 2 5 2 4 2 3 2 2 - - 64*x *y - 95*x - 71*x *y - 69*x *y - x *y - 49*x *y - - 2 2 5 4 3 2 - + 77*x *y + 48*x + 38*x*y + 93*x*y - 65*x*y - 83*x*y - - 5 4 3 2 - + 25*x*y + 51*x + 35*y - 18*y - 59*y + 73*y - y + 31 - - -% A more conventional alternative is ... -% procedure r; randpoly(y)$ randpoly({x}, coeffs = r); -% or, in fact, equivalently ... -% randpoly({x}, coeffs = procedure r; randpoly(y)); - -randpoly({x, y}, dense); - - 5 4 4 3 2 3 3 -85*x + 43*x *y + 68*x + 87*x *y - 93*x *y - 20*x - - 2 2 2 2 4 3 2 - - 74*x *y - 29*x *y + 7*x + 10*x*y + 62*x*y - 86*x*y - - 5 4 3 2 - + 15*x*y - 97*x - 53*y + 71*y - 46*y - 28*y + 79*y + 44 -\end{verbatim} - - -\appendix - -\newfont{\SYM}{msbm10 scaled\magstephalf} % AMS "blackboard bold" etc -\newcommand{\N}{\mbox{\SYM N}} %%% {{\bf N}} - -\newcommand{\th}{\mbox{$^{\it th}$}} - -\newtheorem{prop}{Proposition} - -\newenvironment{proof}% - {\par\addvspace\baselineskip\noindent{\bf Proof~}}% - {\hspace*{\fill}$\Box$\par\addvspace\baselineskip} - -\section{Algorithmic background} - -The only part of this package that involves any mathematics that is -not completely trivial is the procedure to generate a sparse set of -monomials of specified maximum and minimum total degrees in a -specified set of variables. This involves some combinatorics, and the -Maple implementation calls some procedures from the Maple -Combinatorial Functions Package {\tt combinat} (of which I have -implemented restricted versions in REDUCE). - -Given the maximum possible number $N$ of terms (in a dense -polynomial), the required number of terms (in the sparse polynomial) -is selected as a random subset of the natural numbers up to $N$, where -each number indexes a term. In the univariate case these indices are -used directly as monomial exponents, but in the multivariate case they -are converted to monomial exponent vectors using a lexicographic -ordering. - - -\subsection{Numbers of polynomial terms} - -By explicitly enumerating cases with 1, 2, etc.\ variables, as -indicated by the inductive proof below, one deduces that: - -\begin{prop} - In $n$ variables, the number of distinct monomials having total - degree precisely $r$ is $^{r+n-1}C_{n-1}$, and the maximum number of - distinct monomials in a polynomial of maximum total degree $d$ is - $^{d+n}C_n$. -\end{prop} - -\begin{proof} - Suppose the first part of the proposition is true, namely that there - are at most - \[ - N_h(n,r) = {}^{r+n-1}C_{n-1} - \] - distinct monomials in an $n$-variable {\em homogeneous\/} - polynomial of total degree $r$. Then there are at most - \[ - N(d,r) = \sum_{r=0}^d {}^{r+n-1}C_{n-1} = {}^{d+n}C_n - \] - distinct monomials in an $n$-variable polynomial of maximum total - degree $d$. - - The sum follows from the fact that - \[ - {}^{r+n}C_n = \frac{(r+n)^{\underline n}}{n!} - \] - where $x^{\underline n} = x(x-1)(x-2)\cdots(x-n+1)$ denotes a - falling factorial, and - \[ - \sum_{a \leq x < b} x^{\underline n} = - \left. \frac{x^{\underline{n+1}}}{n+1} \right|_a^b. - \] - (See, for example, D. H. Greene \& D. E. Knuth, {\it Mathematics - for the Analysis of Algorithms}, Birkh\"auser, Second Edn.\ 1982, - equation (1.37)). Hence the second part of the proposition follows - from the first. - - The proposition holds for 1 variable ($n = 1$), because there is - clearly 1 distinct monomial of each degree precisely $r$ and hence - at most $d+1$ distinct monomials in a polynomial of maximum degree - $d$. - - Suppose that the proposition holds for $n$ variables, which are - represented by the vector $X$. Then a homogeneous polynomial of - degree $r$ in the $n+1$ variables $X$ together with the single - variable $x$ has the form - \[ - x^r P_0(X) + x^{r-1} P_1(X) + \cdots + x^0 P_r(X) - \] - where $P_s(X)$ represents a polynomial of maximum total degree $s$ - in the $n$ variables $X$, which therefore contains at most - $^{s+n}C_n$ distinct monomials. The homogeneous polynomial of - degree $r$ in $n+1$ terms therefore contains at most - \[ - \sum_{s=0}^r {}^{s+n}C_n = {}^{r+n+1}C_{n+1} - \] - distinct monomials. - Hence the proposition holds for $n+1$ variables, and therefore by - induction it holds for all $n$. -\end{proof} - - -\subsection{Mapping indices to exponent vectors} - -The previous proposition is also the basis of the algorithm to map -term indices $m \in \N$ to exponent vectors $v \in \N^n$, where $n$ is -the number of variables. - -Define a norm $\|\cdot\|$ on exponent vectors by $\|v\| = \sum_{i=1}^n -v_i$, which corresponds to the total degree of the monomial. Then, -from the previous proposition, the number of exponent vectors of -length $n$ with norm $\|v\| \leq d$ is $N(n,d) = {}^{d+n}C_n$. The -elements of the $m\th$ exponent vector are constructed recursively by -applying the algorithm to successive tail vectors, so let a subscript -denote the length of the vector to which a symbol refers. - -The aim is to compute the vector of length $n$ with index $m = m_n$. -If this vector has norm $d_n$ then the index and norm must satisfy -\[ - N(n,d_n-1) \leq m_n < N(n,d_n), -\] -which can be used (as explained below) to compute $d_n$ given $n$ and -$m_n$. Since there are $N(n,d_n-1)$ vectors with norm less than -$d_n$, the index of the $(n-1)$-element tail vector must be given by -$m_{n-1} = m_n - N(n,d_n-1)$, which can be used recursively to compute -the norm $d_{n-1}$ of the tail vector. From this, the first element -of the exponent vector is given by $v_1 = d_n - d_{n-1}$. - -The algorithm therefore has a natural recursive structure that -computes the norm of each tail subvector as the recursion stack is -built up, but can only compute the first term of each tail subvector -as the recursion stack is unwound. Hence, it constructs the exponent -vector from right to left, whilst being applied to the elements from -left to right. The recursion is terminated by the observation that -$v_1 = d_1 = m_1$ for an exponent vector of length $n = 1$. - -The main sub-procedure, given the required length $n$ and index $m_n$ -of an exponent vector, must return its norm $d_n$ and the index of its -tail subvector of length $n-1$. Within this procedure, $N(n,d)$ can -be efficiently computed for values of $d$ increasing from 0, for which -$N(n,0) = {}^nC_n = 1$, until $N(n,d) > m$ by using the observation -that -\[ - N(n,d) = {}^{d+n}C_n = \frac{(d+n)(d-1+n)\cdots(1+n)}{d!}. -\] - -\end{document} +\documentstyle[11pt]{article} + +\title{RANDPOLY: A Random Polynomial Generator} + +\author{Francis J. Wright \\ +School of Mathematical Sciences \\ +Queen Mary and Westfield College \\ +University of London \\ +Mile End Road, London E1 4NS, UK. \\ +Email: {\tt F.J.Wright@QMW.ac.uk}} + +\date{14 July 1994} + +\begin{document} +\maketitle + +\begin{abstract} + This package is based on a port of the Maple random polynomial + generator together with some support facilities for the generation + of random numbers and anonymous procedures. +\end{abstract} + + +\section{Introduction} + +The operator {\tt randpoly} is based on a port of the Maple random +polynomial generator. In fact, although by default it generates a +univariate or multivariate polynomial, in its most general form it +generates a sum of products of arbitrary integer powers of the +variables multiplied by arbitrary coefficient expressions, in which +the variable powers and coefficient expressions are the results of +calling user-supplied functions (with no arguments). Moreover, the +``variables'' can be arbitrary expressions, which are composed with +the underlying polynomial-like function. + +The user interface, code structure and algorithms used are essentially +identical to those in the Maple version. The package also provides an +analogue of the Maple {\tt rand} random-number-generator generator, +primarily for use by {\tt randpoly}. There are principally two +reasons for translating these facilities rather than designing +comparable facilites anew: (1) the Maple design seems satisfactory and +has already been ``proven'' within Maple, so there is no good reason +to repeat the design effort; (2) the main use for these facilities is +in testing the performance of other algebraic code, and there is an +advantage in having essentially the same test data generator +implemented in both Maple and REDUCE\@. Moreover, it is interesting +to see the extent to which a facility can be translated without change +between two systems. (This aspect will be described elsewhere.) + +Sections \ref{sec:Basic} and \ref{sec:Advanced} describe respectively +basic and more advanced use of {\tt randpoly}; \S\ref{sec:Subsidiary} +describes subsidiary functions provided to support advanced use of +{\tt randpoly}; \S\ref{sec:Examples} gives examples; an appendix gives +some details of the only non-trivial algorithm, that used to compute +random sparse polynomials. Additional examples of the use of {\tt +randpoly} are given in the test and demonstration file {\tt +randpoly.tst}. + + +\section{Basic use of {\tt randpoly}} +\label{sec:Basic} + +The operator {\tt randpoly} requires at least one argument +corresponding to the polynomial variable or variables, which must be +either a single expression or a list of expressions.% +\footnote{If it is a single expression then the univariate code is +invoked; if it is a list then the multivariate code is invoked, and in +the special case of a list of one element the multivariate code is +invoked to generate a univariate polynomial, but the result should be +indistinguishable from that resulting from specifying a single +expression not in a list.} % +In effect, {\tt randpoly} replaces each input expression by an +internal variable and then substitutes the input expression for the +internal variable in the generated polynomial (and by default expands +the result as usual), although in fact if the input expression is a +REDUCE kernel then it is used directly. The rest of this document +uses the term ``variable'' to refer to a general input expression or +the internal variable used to represent it, and all references to the +polynomial structure, such as its degree, are with respect to these +internal variables. The actual degree of a generated polynomial might +be different from its degree in the internal variables. + +By default, the polynomial generated has degree 5 and contains 6 +terms. Therefore, if it is univariate it is dense whereas if it is +multivariate it is sparse. + + +\subsection{Optional arguments} + +Other arguments can optionally be specified, in any order, after the +first compulsory variable argument. All arguments receive full +algebraic evaluation, subject to the current switch settings etc. The +arguments are processed in the order given, so that if more than one +argument relates to the same property then the last one specified +takes effect. Optional arguments are either keywords or equations +with keywords on the left. + +In general, the polynomial is sparse by default, unless the keyword +{\tt dense} is specified as an optional argument. (The keyword {\tt +sparse} is also accepted, but is the default.) The default degree can +be changed by specifying an optional argument of the form +\begin{center} + {\tt degree = {\it natural number}}. +\end{center} +In the multivariate case this is the total degree, i.e.\ the sum of +the degrees with respect to the individual variables. The keywords +{\tt deg} and {\tt maxdeg} can also be used in place of {\tt degree}. +More complicated monomial degree bounds can be constructed by using +the coefficient function described below to return a monomial or +polynomial coefficient expression. Moreover, {\tt randpoly} respects +internally the REDUCE ``asymptotic'' commands {\tt let}, {\tt weight} +etc.\ described in \S10.4 of the \REDUCE 3.6 manual, which can be used +to exercise additional control over the polynomial generated. + +In the sparse case (only), the default maximum number of terms +generated can be changed by specifying an optional argument of the +form +\begin{center} + {\tt terms = {\it natural number}}. +\end{center} +The actual number of terms generated will be the minimum of the value +of {\tt terms} and the number of terms in a dense polynomial of the +specified degree, number of variables, etc. + + +\section{Advanced use of {\tt randpoly}} +\label{sec:Advanced} + +The default order (or minimum or trailing degree) can be changed by +specifying an optional argument of the form +\begin{center} + {\tt ord = {\it natural number}}. +\end{center} +The keyword is {\tt ord} rather than {\tt order} because {\tt order} +is a reserved command name in REDUCE\@. The keyword {\tt mindeg} can +also be used in place of {\tt ord}. In the multivariate case this is +the total degree, i.e.\ the sum of the degrees with respect to the +individual variables. The order normally defaults to 0. + +However, the input expressions to {\tt randpoly} can also be +equations, in which case the order defaults to 1 rather than 0. Input +equations are converted to the difference of their two sides before +being substituted into the generated polynomial. The purpose of this +facility is to easily generate polynomials with a specified zero -- for +example +\begin{center}\tt + randpoly(x = a); +\end{center} +generates a polynomial that is guaranteed to vanish at $x = a$, but is +otherwise random. + +Order specification and equation input are extensions of the current +Maple version of {\tt randpoly}. + +The operator {\tt randpoly} accepts two further optional arguments in +the form of equations with the keywords {\tt coeffs} and {\tt expons} +on the left. The right sides of each of these equations must evaluate +to objects that can be applied as functions of no variables. These +functions should be normal algebraic procedures (or something +equivalent); the {\tt coeffs} procedure may return any algebraic +expression, but the {\tt expons} procedure must return an integer +(otherwise {\tt randpoly} reports an error). The values returned by +the functions should normally be random, because it is the randomness +of the coefficients and, in the sparse case, of the exponents that +makes the constructed polynomial random. + +A convenient special case is to use the function {\tt rand} on the +right of one or both of these equations; when called with a single +argument {\tt rand} returns an anonymous function of no variables that +generates a random integer. The single argument of {\tt rand} should +normally be an integer range in the form $a~..~b$, where $a$, $b$ are +integers such that $a < b$. The spaces around (or at least before) +the infix operator ``..'' are necessary in some cases in REDUCE and +generally recommended. For example, the {\tt expons} argument might +take the form +\begin{center}\tt + expons = rand(0~..~n) +\end{center} +where {\tt n} will be the maximum degree with respect to each variable +{\em independently}. In the case of {\tt coeffs} the lower limit will +often be the negative of the upper limit to give a balanced +coefficient range, so that the {\tt coeffs} argument might take the +form +\begin{center}\tt + coeffs = rand(-n~..~n) +\end{center} +which will generate random integer coefficients in the range $[-n,n]$. + + +\section{Subsidiary functions: rand, proc, random} +\label{sec:Subsidiary} + +\subsection{Rand: a random-number-generator generator} + +The first argument of {\tt rand} must be either an integer range in +the form $a~..~b$, where $a$, $b$ are integers such that $a < b$, or a +positive integer $n$ which is equivalent to the range $0~..~n-1$. The +operator {\tt rand} constructs a function of no arguments that calls +the REDUCE random number generator function {\tt random} to return a +random integer in the range specified; in the case that the first +argument of {\tt rand} is a single positive integer $n$ the function +constructed just calls {\tt random($n$)}, otherwise the call of {\tt +random} is scaled and shifted. + +As an additional convenience, if {\tt rand} is called with a second +argument that is an identifier then the call of {\tt rand} acts +exactly like a procedure definition with the identifier as the +procedure name. The procedure generated can then be called with an +empty argument list by the algebraic processor. + +[Note that {\tt rand()} with no argument is an error in REDUCE and +does not return directly a random number in a default range as it does +in Maple -- use instead the REDUCE function {\tt random} (see below).] + + +\subsection{Proc: an anonymous procedure generator} + +The operator {\tt proc} provides a generalization of {\tt rand}, and +is primarily intended to be used with expressions involving the {\tt +random} function (see below). Essentially, it provides a mechanism to +prevent functions such as {\tt random} being evaluated when the +arguments to {\tt randpoly} are evaluated, which is too early. {\tt +Proc} accepts a single argument which is converted into the body of an +anonymous procedure, which is returned as the value of {\tt proc}. +(If a named procedure is required then the normal REDUCE {\tt +procedure} statement should be used instead.) Examples are given in +the following sections, and in the file {\tt randpoly.tst}. + + +\subsection{Random: a generalized interface} + +As an additional convenience, this package extends the interface to +the standard REDUCE {\tt random} function so that it will directly +accept either a natural number or an integer range as its argument, +exactly as for the first argument of {\tt rand}. Hence effectively +\begin{center}\tt + rand(X) = proc random(X) +\end{center} +although {\tt rand} is marginally more efficient. However, {\tt proc} +and the generalized {\tt random} interface allow expressions such as +the following anonymous random fraction generator to be easily +constructed: +\begin{center}\tt + proc(random(-99~..~99)/random(1~..~99)) +\end{center} + + +\subsection{Further support for procs} + +{\tt Rand} is a special case of {\tt proc}, and (for either) if the +switch {\tt comp} is {\tt on} (and the compiler is available) then the +generated procedure body is compiled. + +{\tt Rand} with a single argument and {\tt proc} both return as their +values anonymous procedures, which if they are not compiled are Lisp +lambda expressions. However, if compilation is in effect then they +return only an identifier that has no external significance% +\footnote{It is not interned on the oblist.} % +but which can be applied as a function in the same way as a lambda +expression. + +It is primarily intended that such ``proc expressions'' will be used +immediately as input to {\tt randpoly}. The algebraic processor is +not intended to handle lambda expressions. However, they can be +output or assigned to variables in algebraic mode, although the output +form looks a little strange and is probably best not displayed. But +beware that lambda expressions cannot be evaluated by the algebraic +processor (at least, not without declaring some internal Lisp +functions to be algebraic operators). Therefore, for testing purposes +or curious users, this package provides the operators {\tt showproc} +and {\tt evalproc} respectively to display and evaluate ``proc +expressions'' output by {\tt rand} or {\tt proc} (or in fact any +lambda expression), in the case of {\tt showproc} provided they are +not compiled. + + +\section{Examples} +\label{sec:Examples} + +The file {\tt randpoly.tst} gives a set of test and demonstration +examples. + +The following additional examples were taken from the Maple {\tt +randpoly} help file and converted to REDUCE syntax by replacing [~] by +\{~\} and making the other changes shown explicitly: +\begin{verbatim} +randpoly(x); + + 5 4 3 2 + - 54*x - 92*x - 30*x + 73*x - 69*x - 67 + + +randpoly({x, y}, terms = 20); + + 5 4 4 3 2 3 3 +31*x - 17*x *y - 48*x - 15*x *y + 80*x *y + 92*x + + 2 3 2 2 4 3 2 + + 86*x *y + 2*x *y - 44*x + 83*x*y + 85*x*y + 55*x*y + + 5 4 3 2 + - 27*x*y + 33*x - 98*y + 51*y - 2*y + 70*y - 60*y - 10 + + +randpoly({x, sin(x), cos(x)}); + + 4 3 3 +sin(x)*( - 4*cos(x) - 85*cos(x) *x + 50*sin(x) + + 2 + - 20*sin(x) *x + 76*sin(x)*x + 96*sin(x)) + + +% randpoly(z, expons = rand(-5..5)); % Maple +% A generalized random "polynomial"! +% Note that spaces are needed around .. in REDUCE. +on div; off allfac; +randpoly(z, expons = rand(-5 .. 5)); + + 4 3 -3 -4 -5 + - 39*z + 14*z - 77*z - 37*z - 8*z + +off div; on allfac; +% randpoly([x], coeffs = proc() randpoly(y) end); % Maple +randpoly({x}, coeffs = proc randpoly(y)); + + 5 5 5 4 5 3 5 2 5 5 +95*x *y - 53*x *y - 78*x *y + 69*x *y + 58*x *y - 58*x + + 4 5 4 4 4 3 4 2 4 + + 64*x *y + 93*x *y - 21*x *y + 24*x *y - 13*x *y + + 4 3 5 3 4 3 3 3 2 + - 28*x - 57*x *y - 78*x *y - 44*x *y + 37*x *y + + 3 3 2 5 2 4 2 3 2 2 + - 64*x *y - 95*x - 71*x *y - 69*x *y - x *y - 49*x *y + + 2 2 5 4 3 2 + + 77*x *y + 48*x + 38*x*y + 93*x*y - 65*x*y - 83*x*y + + 5 4 3 2 + + 25*x*y + 51*x + 35*y - 18*y - 59*y + 73*y - y + 31 + + +% A more conventional alternative is ... +% procedure r; randpoly(y)$ randpoly({x}, coeffs = r); +% or, in fact, equivalently ... +% randpoly({x}, coeffs = procedure r; randpoly(y)); + +randpoly({x, y}, dense); + + 5 4 4 3 2 3 3 +85*x + 43*x *y + 68*x + 87*x *y - 93*x *y - 20*x + + 2 2 2 2 4 3 2 + - 74*x *y - 29*x *y + 7*x + 10*x*y + 62*x*y - 86*x*y + + 5 4 3 2 + + 15*x*y - 97*x - 53*y + 71*y - 46*y - 28*y + 79*y + 44 +\end{verbatim} + + +\appendix + +\newfont{\SYM}{msbm10 scaled\magstephalf} % AMS "blackboard bold" etc +\newcommand{\N}{\mbox{\SYM N}} %%% {{\bf N}} + +\newcommand{\th}{\mbox{$^{\it th}$}} + +\newtheorem{prop}{Proposition} + +\newenvironment{proof}% + {\par\addvspace\baselineskip\noindent{\bf Proof~}}% + {\hspace*{\fill}$\Box$\par\addvspace\baselineskip} + +\section{Algorithmic background} + +The only part of this package that involves any mathematics that is +not completely trivial is the procedure to generate a sparse set of +monomials of specified maximum and minimum total degrees in a +specified set of variables. This involves some combinatorics, and the +Maple implementation calls some procedures from the Maple +Combinatorial Functions Package {\tt combinat} (of which I have +implemented restricted versions in REDUCE). + +Given the maximum possible number $N$ of terms (in a dense +polynomial), the required number of terms (in the sparse polynomial) +is selected as a random subset of the natural numbers up to $N$, where +each number indexes a term. In the univariate case these indices are +used directly as monomial exponents, but in the multivariate case they +are converted to monomial exponent vectors using a lexicographic +ordering. + + +\subsection{Numbers of polynomial terms} + +By explicitly enumerating cases with 1, 2, etc.\ variables, as +indicated by the inductive proof below, one deduces that: + +\begin{prop} + In $n$ variables, the number of distinct monomials having total + degree precisely $r$ is $^{r+n-1}C_{n-1}$, and the maximum number of + distinct monomials in a polynomial of maximum total degree $d$ is + $^{d+n}C_n$. +\end{prop} + +\begin{proof} + Suppose the first part of the proposition is true, namely that there + are at most + \[ + N_h(n,r) = {}^{r+n-1}C_{n-1} + \] + distinct monomials in an $n$-variable {\em homogeneous\/} + polynomial of total degree $r$. Then there are at most + \[ + N(d,r) = \sum_{r=0}^d {}^{r+n-1}C_{n-1} = {}^{d+n}C_n + \] + distinct monomials in an $n$-variable polynomial of maximum total + degree $d$. + + The sum follows from the fact that + \[ + {}^{r+n}C_n = \frac{(r+n)^{\underline n}}{n!} + \] + where $x^{\underline n} = x(x-1)(x-2)\cdots(x-n+1)$ denotes a + falling factorial, and + \[ + \sum_{a \leq x < b} x^{\underline n} = + \left. \frac{x^{\underline{n+1}}}{n+1} \right|_a^b. + \] + (See, for example, D. H. Greene \& D. E. Knuth, {\it Mathematics + for the Analysis of Algorithms}, Birkh\"auser, Second Edn.\ 1982, + equation (1.37)). Hence the second part of the proposition follows + from the first. + + The proposition holds for 1 variable ($n = 1$), because there is + clearly 1 distinct monomial of each degree precisely $r$ and hence + at most $d+1$ distinct monomials in a polynomial of maximum degree + $d$. + + Suppose that the proposition holds for $n$ variables, which are + represented by the vector $X$. Then a homogeneous polynomial of + degree $r$ in the $n+1$ variables $X$ together with the single + variable $x$ has the form + \[ + x^r P_0(X) + x^{r-1} P_1(X) + \cdots + x^0 P_r(X) + \] + where $P_s(X)$ represents a polynomial of maximum total degree $s$ + in the $n$ variables $X$, which therefore contains at most + $^{s+n}C_n$ distinct monomials. The homogeneous polynomial of + degree $r$ in $n+1$ terms therefore contains at most + \[ + \sum_{s=0}^r {}^{s+n}C_n = {}^{r+n+1}C_{n+1} + \] + distinct monomials. + Hence the proposition holds for $n+1$ variables, and therefore by + induction it holds for all $n$. +\end{proof} + + +\subsection{Mapping indices to exponent vectors} + +The previous proposition is also the basis of the algorithm to map +term indices $m \in \N$ to exponent vectors $v \in \N^n$, where $n$ is +the number of variables. + +Define a norm $\|\cdot\|$ on exponent vectors by $\|v\| = \sum_{i=1}^n +v_i$, which corresponds to the total degree of the monomial. Then, +from the previous proposition, the number of exponent vectors of +length $n$ with norm $\|v\| \leq d$ is $N(n,d) = {}^{d+n}C_n$. The +elements of the $m\th$ exponent vector are constructed recursively by +applying the algorithm to successive tail vectors, so let a subscript +denote the length of the vector to which a symbol refers. + +The aim is to compute the vector of length $n$ with index $m = m_n$. +If this vector has norm $d_n$ then the index and norm must satisfy +\[ + N(n,d_n-1) \leq m_n < N(n,d_n), +\] +which can be used (as explained below) to compute $d_n$ given $n$ and +$m_n$. Since there are $N(n,d_n-1)$ vectors with norm less than +$d_n$, the index of the $(n-1)$-element tail vector must be given by +$m_{n-1} = m_n - N(n,d_n-1)$, which can be used recursively to compute +the norm $d_{n-1}$ of the tail vector. From this, the first element +of the exponent vector is given by $v_1 = d_n - d_{n-1}$. + +The algorithm therefore has a natural recursive structure that +computes the norm of each tail subvector as the recursion stack is +built up, but can only compute the first term of each tail subvector +as the recursion stack is unwound. Hence, it constructs the exponent +vector from right to left, whilst being applied to the elements from +left to right. The recursion is terminated by the observation that +$v_1 = d_1 = m_1$ for an exponent vector of length $n = 1$. + +The main sub-procedure, given the required length $n$ and index $m_n$ +of an exponent vector, must return its norm $d_n$ and the index of its +tail subvector of length $n-1$. Within this procedure, $N(n,d)$ can +be efficiently computed for values of $d$ increasing from 0, for which +$N(n,0) = {}^nC_n = 1$, until $N(n,d) > m$ by using the observation +that +\[ + N(n,d) = {}^{d+n}C_n = \frac{(d+n)(d-1+n)\cdots(1+n)}{d!}. +\] + +\end{document} Index: r36/doc/REACTEQN.DOC ================================================================== --- r36/doc/REACTEQN.DOC +++ r36/doc/REACTEQN.DOC @@ -1,196 +1,196 @@ - - REDUCE Support for Reaction Equation Systems - - Herbert Melenk - - Konrad-Zuse-Zentrum Berlin - - January 1991 - - - -The REDUCE package REACTEQN allows one to transform chemical reaction -systems into ordinary differential equation systems (ode) -corresponding to the laws of pure mass action. - -A single reaction equation is an expression of the form - - + + ... -> + + ... - or - + + ... <> + + ... - -where the are arbitrary names of species (REDUCE symbols) -and the are positive integer numbers. The number 1 -can be omitted. The connector -> describes a one way reaction, -while <> describes a forward and backward reaction. - -A reaction system is a list of reaction equations, each of them -optionally followed by one or two expressions for the rate -constants. A rate constant can a number, a symbol or an -arbitrary REDUCE expression. If a rate constant is missing, -an automatic constant of the form RATE(n) (where n is an -integer counter) is generated. For double reactions the -first constant is used for the forward direction, the second -one for the backward direction. - -The names of the species are collected in a list bound to -the REDUCE variable SPECIES. This list is automatically filled -during the processing of a reaction system. The species enter -in an order corresponding to their appearance in the reaction -system and the resulting ode's will be ordered in the same manner. -If a list of species is preassigned to the variable -SPECIES either explicitly or from previous operations, the -given order will be maintained and will dominate the formatting -process. So the ordering of the result can be easily influenced -by the user. - -Syntax: - reac2ode { [, [,]] - [, [, [,]]] - .... - }; - - where two rates are applicable only for <> reactions. - - Result is a system of explicit ordinary differential - equations with polynomial righthand sides. As side - effect the following variables are set: - - lists: - - rates: list of the rates in the system - - species: list of the species in the system - - matrices: - - inputmat: matrix of the input coefficients - - outputmat: matrix of the output coefficients - -In the matrices the row number corresponds to the input reaction -number, while the column number corresponds to the species index. - -Note: if the rates are numerical values, it will be in most cases - appropriate to select a REDUCE evaluation mode for floating - point numbers. That is - REDUCE 3.3: on float,numval; - REDUCE 3.4: on rounded; - -Inputmat and outputmat can be used for linear algebra type -investigations of the reaction system. The classical reaction -matrix is the difference of these matrices; however, the two -matrices contain more information than their differences because -the appearance of a species on both sides is not reflected by -the reaction matrix. - -EXAMPLES: - -% Example taken from Feinberg (Chemical Engineering): - - species := {A1,A2,A3,A4,A5}; - - reac2ode { A1 + A4 <> 2A1, rho, beta, - A1 + A2 <> A3, gamma, epsilon, - A3 <> A2 + A5, theta, mue}; - - - 2 -{DF(A1,T)=RHO*A1*A4 - BETA*A1 - GAMMA*A1*A2 + EPSILON*A3, - - DF(A2,T)= - GAMMA*A1*A2 + EPSILON*A3 + THETA*A3 - MUE*A2*A5, - - DF(A3,T)=GAMMA*A1*A2 - EPSILON*A3 - THETA*A3 + MUE*A2*A5, - - 2 - DF(A4,T)= - RHO*A1*A4 + BETA*A1 , - - DF(A5,T)=THETA*A3 - MUE*A2*A5} - -% the corresponding matrices: - - inputmat; - -[1 0 0 1 0] -[ ] -[1 1 0 0 0] -[ ] -[0 0 1 0 0] - - - outputmat; - -[2 0 0 0 0] -[ ] -[0 0 1 0 0] -[ ] -[0 1 0 0 1] - - -% computation of the classical reaction matrix as difference -% of output and input matrix: - - reactmat := outputmat-inputmat; - - [1 0 0 -1 0] - [ ] -REACTMAT := [-1 -1 1 0 0] - [ ] - [0 1 -1 0 1] - -% Example with automatic generation of rate constants -% and automatic extraction of species - - species := {}; - reac2ode { A1 + A4 <> 2A1, - A1 + A2 <> A3, - a3 <> A2 + A5}; - -new species: A1 -new species: A4 -new species: A3 -new species: A2 -new species: A5 - - - 2 -{DF(A1,T)= - A1 *RATE(2) + A1*A4*RATE(1) - A1*A2*RATE(3) + - - A3*RATE(4), - - 2 - DF(A4,T)=A1 *RATE(2) - A1*A4*RATE(1), - - DF(A2,T)= - A1*A2*RATE(3) - A2*A5*RATE(6) + A3*RATE(5) + A3*RATE(4), - - DF(A3,T)=A1*A2*RATE(3) + A2*A5*RATE(6) - A3*RATE(5) - A3*RATE(4), - - DF(A5,T)= - A2*A5*RATE(6) + A3*RATE(5)} - - -% Example with rates computed from numerical expressions - - species := {}; - reac2ode { A1 + A4 <> 2A1, 17.3* 22.4^1.5, - 0.04* 22.4^1.5 }; - -new species: A1 -new species: A4 - - 2 -{DF(A1,T)= - 4.24065*A1 + 1834.08*A1*A4, - - 2 - DF(A4,T)=4.24065*A1 - 1834.08*A1*A4} - -Herbert Melenk -Konrad-Zuse-Zentrum fuer Informationstechnik -Heilbronner Str 10 -D 1000 Berlin 31 -Germany - -Phone: (49) 30 89604 195 -FAX: (49) 30 89604 125 -e-mail: melenk@sc.zib-berlin.dbp.de - melenk@sc.zib-berlin.de (internet) - + + REDUCE Support for Reaction Equation Systems + + Herbert Melenk + + Konrad-Zuse-Zentrum Berlin + + January 1991 + + + +The REDUCE package REACTEQN allows one to transform chemical reaction +systems into ordinary differential equation systems (ode) +corresponding to the laws of pure mass action. + +A single reaction equation is an expression of the form + + + + ... -> + + ... + or + + + ... <> + + ... + +where the are arbitrary names of species (REDUCE symbols) +and the are positive integer numbers. The number 1 +can be omitted. The connector -> describes a one way reaction, +while <> describes a forward and backward reaction. + +A reaction system is a list of reaction equations, each of them +optionally followed by one or two expressions for the rate +constants. A rate constant can a number, a symbol or an +arbitrary REDUCE expression. If a rate constant is missing, +an automatic constant of the form RATE(n) (where n is an +integer counter) is generated. For double reactions the +first constant is used for the forward direction, the second +one for the backward direction. + +The names of the species are collected in a list bound to +the REDUCE variable SPECIES. This list is automatically filled +during the processing of a reaction system. The species enter +in an order corresponding to their appearance in the reaction +system and the resulting ode's will be ordered in the same manner. +If a list of species is preassigned to the variable +SPECIES either explicitly or from previous operations, the +given order will be maintained and will dominate the formatting +process. So the ordering of the result can be easily influenced +by the user. + +Syntax: + reac2ode { [, [,]] + [, [, [,]]] + .... + }; + + where two rates are applicable only for <> reactions. + + Result is a system of explicit ordinary differential + equations with polynomial righthand sides. As side + effect the following variables are set: + + lists: + + rates: list of the rates in the system + + species: list of the species in the system + + matrices: + + inputmat: matrix of the input coefficients + + outputmat: matrix of the output coefficients + +In the matrices the row number corresponds to the input reaction +number, while the column number corresponds to the species index. + +Note: if the rates are numerical values, it will be in most cases + appropriate to select a REDUCE evaluation mode for floating + point numbers. That is + REDUCE 3.3: on float,numval; + REDUCE 3.4: on rounded; + +Inputmat and outputmat can be used for linear algebra type +investigations of the reaction system. The classical reaction +matrix is the difference of these matrices; however, the two +matrices contain more information than their differences because +the appearance of a species on both sides is not reflected by +the reaction matrix. + +EXAMPLES: + +% Example taken from Feinberg (Chemical Engineering): + + species := {A1,A2,A3,A4,A5}; + + reac2ode { A1 + A4 <> 2A1, rho, beta, + A1 + A2 <> A3, gamma, epsilon, + A3 <> A2 + A5, theta, mue}; + + + 2 +{DF(A1,T)=RHO*A1*A4 - BETA*A1 - GAMMA*A1*A2 + EPSILON*A3, + + DF(A2,T)= - GAMMA*A1*A2 + EPSILON*A3 + THETA*A3 - MUE*A2*A5, + + DF(A3,T)=GAMMA*A1*A2 - EPSILON*A3 - THETA*A3 + MUE*A2*A5, + + 2 + DF(A4,T)= - RHO*A1*A4 + BETA*A1 , + + DF(A5,T)=THETA*A3 - MUE*A2*A5} + +% the corresponding matrices: + + inputmat; + +[1 0 0 1 0] +[ ] +[1 1 0 0 0] +[ ] +[0 0 1 0 0] + + + outputmat; + +[2 0 0 0 0] +[ ] +[0 0 1 0 0] +[ ] +[0 1 0 0 1] + + +% computation of the classical reaction matrix as difference +% of output and input matrix: + + reactmat := outputmat-inputmat; + + [1 0 0 -1 0] + [ ] +REACTMAT := [-1 -1 1 0 0] + [ ] + [0 1 -1 0 1] + +% Example with automatic generation of rate constants +% and automatic extraction of species + + species := {}; + reac2ode { A1 + A4 <> 2A1, + A1 + A2 <> A3, + a3 <> A2 + A5}; + +new species: A1 +new species: A4 +new species: A3 +new species: A2 +new species: A5 + + + 2 +{DF(A1,T)= - A1 *RATE(2) + A1*A4*RATE(1) - A1*A2*RATE(3) + + + A3*RATE(4), + + 2 + DF(A4,T)=A1 *RATE(2) - A1*A4*RATE(1), + + DF(A2,T)= - A1*A2*RATE(3) - A2*A5*RATE(6) + A3*RATE(5) + A3*RATE(4), + + DF(A3,T)=A1*A2*RATE(3) + A2*A5*RATE(6) - A3*RATE(5) - A3*RATE(4), + + DF(A5,T)= - A2*A5*RATE(6) + A3*RATE(5)} + + +% Example with rates computed from numerical expressions + + species := {}; + reac2ode { A1 + A4 <> 2A1, 17.3* 22.4^1.5, + 0.04* 22.4^1.5 }; + +new species: A1 +new species: A4 + + 2 +{DF(A1,T)= - 4.24065*A1 + 1834.08*A1*A4, + + 2 + DF(A4,T)=4.24065*A1 - 1834.08*A1*A4} + +Herbert Melenk +Konrad-Zuse-Zentrum fuer Informationstechnik +Heilbronner Str 10 +D 1000 Berlin 31 +Germany + +Phone: (49) 30 89604 195 +FAX: (49) 30 89604 125 +e-mail: melenk@sc.zib-berlin.dbp.de + melenk@sc.zib-berlin.de (internet) + Index: r36/doc/REDUCE.STY ================================================================== --- r36/doc/REDUCE.STY +++ r36/doc/REDUCE.STY @@ -1,466 +1,466 @@ -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -% The REDUCE Style option File --- LaTeX version. % -%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% -% -% The document should start with: -% \documentstyle[11pt,reduce,makeidx]{...} -% -% This style adds the following commands: -% \COMPATNOTE{...} For compatibility notes. -% \f{...} Sets function name is \tt. -% \k{...} Sets BNF keyword bold. -% \REDUCE REDUCE when needed as a word. -% \RLISP RLISP when needed as a word. -% \s{...} Sets BNF sentential form \em in <...> -% \meta An alternative for BNF italics in <...> -% \ttindex{...} Puts index entry in \tt font. -% -% -% -% Basic religion about REDUCE documentation. No paragraph indentation, -% bigger skip between lines, ragged bottom, and not as much vertical -% space. -%% RmS: setup of size dependent parameters. 11pt is assumed, so let's force it. - -\typeout{Document style option `reduce' -- released 5 Nov 1991.} - -% **************************************** -% * FONTS * -% **************************************** -% - -\lineskip 1pt % \lineskip is 1pt for all font sizes. -\normallineskip 1pt -\def\baselinestretch{1} - -% Each size-changing command \SIZE executes the command -% \@setsize\SIZE{BASELINESKIP}\FONTSIZE\@FONTSIZE -% where: -% BASELINESKIP = Normal value of \baselineskip for that size. (Actual -% value will be \baselinestretch * BASELINESKIP.) -% -% \FONTSIZE = Name of font-size command. The currently available -% (preloaded) font sizes are: \vpt (5pt), \vipt (6pt), -% \viipt (etc.), \viiipt, \ixpt, \xpt, \xipt, \xiipt, -% \xivpt, \xviipt, \xxpt, \xxvpt. -% \@FONTSIZE = The same as the font-size command except with an -% '@' in front---e.g., if \FONTSIZE = \xivpt then -% \@FONTSIZE = \@xivpt. -% -% For reasons of efficiency that needn't concern the designer, -% the document style defines \@normalsize instead of \normalsize. This -% is done only for \normalsize, not for any other size-changing -% commands. - -\def\@normalsize{\@setsize\normalsize{13.6pt}\xipt\@xipt -\abovedisplayskip .5\baselineskip -\belowdisplayskip \abovedisplayskip -\abovedisplayshortskip \z@ plus3\p@ -\belowdisplayshortskip 6.5\p@ plus3.5\p@ minus3\p@ -\let\@listi\@listI} % Setting of \@listi added 9 Jun 87 - -\def\small{\@setsize\small{12pt}\xpt\@xpt -\abovedisplayskip .5\baselineskip -\belowdisplayskip \abovedisplayskip -\abovedisplayshortskip \z@ plus3\p@ -\belowdisplayshortskip 6\p@ plus3\p@ minus3\p@ -\def\@listi{\leftmargin\leftmargini %% Added 22 Dec 87 -\topsep \z@\parsep 3\p@ plus2\p@ minus\p@ -\itemsep .5\baselineskip}} - -\def\footnotesize{\@setsize\footnotesize{11pt}\ixpt\@ixpt -\abovedisplayskip .5\baselineskip -\belowdisplayskip \abovedisplayskip -\abovedisplayshortskip \z@ plus\p@ -\belowdisplayshortskip 4\p@ plus2\p@ minus2\p@ -\def\@listi{\leftmargin\leftmargini %% Added 22 Dec 87 -\topsep \z@ \parsep 2\p@ plus\p@ minus\p@ -\itemsep .5\baselineskip}} - -\def\scriptsize{\@setsize\scriptsize{9.5pt}\viiipt\@viiipt} -\def\tiny{\@setsize\tiny{7pt}\vipt\@vipt} -\def\large{\@setsize\large{14pt}\xiipt\@xiipt} -\def\Large{\@setsize\Large{18pt}\xivpt\@xivpt} -\def\LARGE{\@setsize\LARGE{22pt}\xviipt\@xviipt} -\def\huge{\@setsize\huge{25pt}\xxpt\@xxpt} -\def\Huge{\@setsize\Huge{30pt}\xxvpt\@xxvpt} - -\normalsize % Choose the normalsize font. - - -% **************************************** -% * PAGE LAYOUT * -% **************************************** -% -% All margin dimensions measured from a point one inch from top and side -% of page. - -% SIDE MARGINS: -\if@twoside % Values for two-sided printing: - \oddsidemargin 36pt % Left margin on odd-numbered pages. - \evensidemargin 74pt % Left margin on even-numbered pages. - \marginparwidth 100pt % Width of marginal notes. -\else % Values for one-sided printing: - \oddsidemargin 54pt % Note that \oddsidemargin = \evensidemargin - \evensidemargin 54pt - \marginparwidth 83pt -\fi -\marginparsep 10pt % Horizontal space between outer margin and - % marginal note - - -% VERTICAL SPACING: - % Top of page: -\topmargin 27pt % Nominal distance from top of page to top - % of box containing running head. -\headheight 12pt % Height of box containing running head. -\headsep 25pt % Space between running head and text. -% \topskip = 10pt % '\baselineskip' for first line of page. - % Bottom of page: -\footskip 30pt % Distance from baseline of box containing - % foot to baseline of last line of text. - -% DIMENSION OF TEXT: -% 24 Jun 86: changed to explicitly compute \textheight to avoid -% roundoff. The value of the multiplier was calculated as the floor of -% the old \textheight minus \topskip, divided by \baselineskip for -% \normalsize. The old value of \textheight was 530.4pt. -% \textheight is the height of text (including footnotes and figures, -% excluding running head and foot). - -\textheight = 38\baselineskip -\advance\textheight by \topskip -\textwidth 360pt % Width of text line. - % For two-column mode: -\columnsep 10pt % Space between columns -\columnseprule 0pt % Width of rule between columns. - -% A \raggedbottom command causes 'ragged bottom' pages: pages set to -% natural height instead of being stretched to exactly \textheight. - -% FOOTNOTES: - -\footnotesep 7.7pt % Height of strut placed at the beginning of every - % footnote = height of normal \footnotesize strut, - % so no extra space between footnotes. - -\skip\footins 10pt plus 4pt minus 2pt % Space between last line of text - % and top of first footnote. - -% FLOATS: (a float is something like a figure or table) -% -% FOR FLOATS ON A TEXT PAGE: -% -% ONE-COLUMN MODE OR SINGLE-COLUMN FLOATS IN TWO-COLUMN MODE: -\floatsep 12pt plus 2pt minus 2pt % Space between adjacent floats - % moved to top or bottom of - % text page. -\textfloatsep 20pt plus 2pt minus 4pt % Space between main text and - % floats at top or bottom of - % page. -\intextsep 12pt plus 2pt minus 2pt % Space between in-text figures - % and text. -\@maxsep 20pt % The maximum of \floatsep, - % \textfloatsep and \intextsep - % (minus the stretch and - % shrink). -% TWO-COLUMN FLOATS IN TWO-COLUMN MODE: -\dblfloatsep 12pt plus 2pt minus 2pt % Same as \floatsep for - % double-column figures in - % two-column mode. -\dbltextfloatsep 20pt plus 2pt minus 4pt % \textfloatsep for - % double-column floats. -\@dblmaxsep 20pt % The maximum of \dblfloatsep - % and \dbltexfloatsep. - -% FOR FLOATS ON A SEPARATE FLOAT PAGE OR COLUMN: -% ONE-COLUMN MODE OR SINGLE-COLUMN FLOATS IN TWO-COLUMN MODE: -\@fptop 0pt plus 1fil % Stretch at top of float page/column. (Must - % be 0pt plus ...) -\@fpsep 8pt plus 2fil % Space between floats on float page/column. -\@fpbot 0pt plus 1fil % Stretch at bottom of float page/column. (Must - % be 0pt plus ... ) - -% DOUBLE-COLUMN FLOATS IN TWO-COLUMN MODE. -\@dblfptop 0pt plus 1fil % Stretch at top of float page. (Must be 0pt - % plus ...) -\@dblfpsep 8pt plus 2fil % Space between floats on float page. -\@dblfpbot 0pt plus 1fil % Stretch at bottom of float page. (Must be - % 0pt plus ... ) -% MARGINAL NOTES: -% -\marginparpush 5pt % Minimum vertical separation between two - % marginal notes. - - -% **************************************** -% * PARAGRAPHING * -% **************************************** -% -\parskip 6pt plus 1pt %% RmS % Extra vertical space between - % paragraphs. -\parindent 0pt %% RmS % Width of paragraph indentation. -\topsep 0pt %% RmS % Extra vertical space, in addition - % to \parskip, added above and below - % list and paragraphing environments. -\partopsep 0pt %% RmS % Extra vertical space, in addition - % to \parskip and \topsep, added when - % user leaves blank line before - % environment. -\itemsep \topsep %% RmS % Extra vertical space, in addition - % to \parskip, added between list - % items. -% See \@listI for values of \topsep and \itemsep - -% The following page-breaking penalties are defined - -\@lowpenalty 51 % Produced by \nopagebreak[1] or \nolinebreak[1] -\@medpenalty 151 % Produced by \nopagebreak[2] or \nolinebreak[2] -\@highpenalty 301 % Produced by \nopagebreak[3] or \nolinebreak[3] - -\@beginparpenalty -\@lowpenalty % Before a list or paragraph - % environment. -\@endparpenalty -\@lowpenalty % After a list or paragraph - % environment. -\@itempenalty -\@lowpenalty % Between list items. - -% \clubpenalty % 'Club line' at bottom of page. -% \widowpenalty % 'Widow line' at top of page. -% \displaywidowpenalty % Math display widow line. -% \predisplaypenalty % Breaking before a math display. -% \postdisplaypenalty % Breaking after a math display. -% \interlinepenalty % Breaking at a line within a paragraph. -% \brokenpenalty % Breaking after a hyphenated line. - - -% **************************************** -% * SECTIONS * -% **************************************** -% - -% \@startsection {NAME}{LEVEL}{INDENT}{BEFORESKIP}{AFTERSKIP}{STYLE} -% optional * [ALTHEADING]{HEADING} -% Generic command to start a section. -% NAME : e.g., 'subsection' -% LEVEL : a number, denoting depth of section -- i.e., -% section=1, subsection = 2, etc. A section number will -% be printed if and only if LEVEL < or = the value of -% the secnumdepth counter. -% INDENT : Indentation of heading from left margin -% BEFORESKIP : Absolute value = skip to leave above the heading. -% If negative, then paragraph indent of text following -% heading is suppressed. -% AFTERSKIP : if positive, then skip to leave below heading, -% else - skip to leave to right of run-in heading. -% STYLE : commands to set style -% If '*' missing, then increments the counter. If it is present, then -% there should be no [ALTHEADING] argument. A sectioning command -% is normally defined to \@startsection + its first six arguments. - -\def\section{\@startsection {section}{1}{\z@}{-3.5ex plus-1ex minus - -.2ex}{2.3ex plus.2ex}{\reset@font\Large\bf}} -\def\subsection{\@startsection{subsection}{2}{\z@}{-3.25ex plus-1ex - minus-.2ex}{1.5ex plus.2ex}{\reset@font\large\bf}} -\def\subsubsection{\@startsection{subsubsection}{3}{\z@}{-3.25ex plus - -1ex minus-.2ex}{1.5ex plus.2ex}{\reset@font\normalsize\bf}} -\def\paragraph{\@startsection - {paragraph}{4}{\z@}{3.25ex plus1ex minus.2ex}{-1em}{\reset@font - \normalsize\bf}} -\def\subparagraph{\@startsection - {subparagraph}{4}{\parindent}{3.25ex plus1ex minus - .2ex}{-1em}{\reset@font\normalsize\bf}} - - -% Default initializations of \...mark commands. (See below for their -% use in defining page styles. -% - -% \def\sectionmark#1{} % Preloaded definitions -% \def\subsectionmark#1{} -% \def\subsubsectionmark#1{} -% \def\paragraphmark#1{} -% \def\subparagraphmark#1{} - -% The value of the counter secnumdepth gives the depth of the -% highest-level sectioning command that is to produce section numbers. -% - -\setcounter{secnumdepth}{3} - -% APPENDIX -% -% The \appendix command must do the following: -% -- reset the section and subsection counters to zero -% -- redefine the section counter to produce appendix numbers -% -- redefine the \section command if appendix titles and headings -% are to look different from section titles and headings. - -\def\appendix{\par - \setcounter{section}{0} - \setcounter{subsection}{0} - \def\thesection{\Alph{section}}} - - -% **************************************** -% * LISTS * -% **************************************** -% - -% The following commands are used to set the default values for the list -% environment's parameters. See the LaTeX manual for an explanation of -% the meanings of the parameters. Defaults for the list environment are -% set as follows. First, \rightmargin, \listparindent and \itemindent -% are set to 0pt. Then, for a Kth level list, the command \@listK is -% called, where 'K' denotes 'i', 'ii', ... , 'vi'. (I.e., \@listiii is -% called for a third-level list.) By convention, \@listK should set -% \leftmargin to \leftmarginK. -% - -\leftmargini 2.5em -\leftmarginii 2.2em % > \labelsep + width of '(m)' -\leftmarginiii 1.87em % > \labelsep + width of 'vii.' -\leftmarginiv 1.7em % > \labelsep + width of 'M.' -\leftmarginv 1em -\leftmarginvi 1em - -\leftmargin\leftmargini -\labelsep .5em -\labelwidth\leftmargini\advance\labelwidth-\labelsep -%\parsep 4.5pt plus 2pt minus 1pt %(Removed 9 Jun 87) - -% \@listI defines top level and \@listi values of -% \leftmargin, \topsep, \parsep, and \itemsep -% (Added 9 Jun 87) -\def\@listI{\leftmargin\leftmargini \parsep 4.5\p@ plus2\p@ minus\p@ -\topsep \z@ \itemsep \topsep} - -\let\@listi\@listI -\@listi - -\def\@listii{\leftmargin\leftmarginii - \labelwidth\leftmarginii\advance\labelwidth-\labelsep - \topsep \z@ \itemsep \topsep - \parsep 2\p@ plus\p@ minus\p@} - -\def\@listiii{\leftmargin\leftmarginiii - \labelwidth\leftmarginiii\advance\labelwidth-\labelsep - \topsep \z@ \itemsep \topsep - \parsep \z@ \partopsep\z@} - -\def\@listiv{\leftmargin\leftmarginiv - \labelwidth\leftmarginiv\advance\labelwidth-\labelsep} - - - - - -%% RmS: which at the same time makes the vertical space in lists (verbatim...) -%% too large if not other precautions are taken. -\setlength{\parindent}{0pt} -\setlength{\parskip}{6pt} -\raggedbottom - - -% Various boxes. -\newlength{\reduceboxwidth} -\setlength{\reduceboxwidth}{4in} - -\newlength{\redboxwidth} -\setlength{\redboxwidth}{3.5in} - -\newlength{\rboxwidth} -\setlength{\rboxwidth}{2.6in} - -% These are here in case the name changes or we someday want a special -% font. -\newcommand{\REDUCE}{REDUCE} -\newcommand{\RLISP}{RLISP} - -% This is useful for putting function names in \tt format in the index. -\newcommand{\ttindex}[1]{\index{#1@{\tt #1}}} - -% Use this when you are speaking about problems across systems. -\newcommand{\COMPATNOTE}{{\em Compatibility Note:\ }} - -\pagestyle{headings} - -%% For BNF notation. - -% \s{...} is a sentential form in descriptions. Enclosed \em text in <...> -\newcommand{\s}[1] {$<${\em #1}$>$} - -% \meta{...} is an alternative sentential form in descriptions using \it. -\newcommand{\meta}[1]{\mbox{$\langle$\it#1\/$\rangle$}} - -% \k{...} is a keyword. Just do in bold for the moment. -\newcommand{\k}[1] {{\bf #1}} - -% \f is a function name. Just do this as tt. -\newcommand{\f}[1] {{\tt #1}} - -% An example macro for numbering and indenting examples. -\newcounter{examplectr} -\newcommand{\example}{\refstepcounter{examplectr} -\noindent{\bf Example \theexamplectr}} - -% The following are currently only used in the GENTRAN document. However, -% there's no objection to using them elsewhere. - -\begingroup - \catcode `|=0 - \catcode `[= 1 - \catcode`]=2 - \catcode `\{=12 - \catcode `\}=12 - \catcode`\\=12 - |gdef|@xframedverbatim#1\end{framedverbatim}[#1|end[framedverbatim]] - |gdef|@sxframedverbatim#1\end{framedverbatim*}[#1|end[framedverbatim*]] -|endgroup - -\newdimen\@mcdheight - -\def\@sframedverbatim{\obeyspaces\@framedverbatim} - -\def\@mcdrule{\@mcdheight=\baselineskip\advance\@mcdheight by-2pt -\setbox0=\hbox{\vrule height\@mcdheight depth 2pt width 1pt}% -\ht0=\@mcdheight\dp0=0pt\wd0=1pt\box0} - -\def\@mcdendrule{\@mcdheight=\baselineskip% -\setbox0=\hbox{\vrule height\@mcdheight depth 2pt width 1pt}% -\ht0=\@mcdheight\dp0=0pt\wd0=1pt\box0} - -\def\@framedverbatim{\trivlist \item[] -\parskip \z@ -\hrule \@height \p@ \@depth \z@ \@width\textwidth -\everypar{\global \@minipagefalse \global \@newlistfalse \if@inlabel -\global \@inlabelfalse \hskip -\parindent \box \@labels \penalty \z@ \fi -\hbox to6\p@{\rlap{\@mcdrule}\hskip\textwidth\llap{\@mcdrule}\hss}}% -\if@minipage\else\vskip\parskip\fi -\leftskip\@totalleftmargin\rightskip\z@ -\parindent\z@\parfillskip\@flushglue\parskip\z@ -\@tempswafalse \def\par{\if@tempswa\hbox{}\fi\@tempswatrue\@@par -\penalty\interlinepenalty}% % fix \samepage bug -\obeylines \tt \catcode``=13 \@noligs \let\do\@makeother \dospecials} - -\def\framedverbatim{\@framedverbatim \frenchspacing\@vobeyspaces - \@xframedverbatim} - -\def\endframedverbatim{\nointerlineskip -{\everypar{}\baselineskip 4\p@\vbox to4\p@{\par\noindent\hbox - to6pt{\rlap{\@mcdendrule}\hskip\textwidth\llap{\@mcdendrule}\hss}}% -\vskip\p@\hrule \@height \p@ \@depth \z@ \@width\textwidth}\endtrivlist} - -\@namedef{framedverbatim*}{\@framedverbatim\@sxframedverbatim} - -\expandafter\let\csname endframedverbatim*\endcsname =\endtrivlist - -% Will print out a heading in bold, and then indent the following text. -\def\indented{\list{}{ - \itemindent\listparindent - \rightmargin\leftmargin}\item[]} -\let\endindented=\endlist -\newenvironment{describe}[1]{\par{\bf #1}\begin{indented}}{\end{indented}} - -\@ifundefined{reset@font}{\let\reset@font\@empty}{} - -\endinput +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +% The REDUCE Style option File --- LaTeX version. % +%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% +% +% The document should start with: +% \documentstyle[11pt,reduce,makeidx]{...} +% +% This style adds the following commands: +% \COMPATNOTE{...} For compatibility notes. +% \f{...} Sets function name is \tt. +% \k{...} Sets BNF keyword bold. +% \REDUCE REDUCE when needed as a word. +% \RLISP RLISP when needed as a word. +% \s{...} Sets BNF sentential form \em in <...> +% \meta An alternative for BNF italics in <...> +% \ttindex{...} Puts index entry in \tt font. +% +% +% +% Basic religion about REDUCE documentation. No paragraph indentation, +% bigger skip between lines, ragged bottom, and not as much vertical +% space. +%% RmS: setup of size dependent parameters. 11pt is assumed, so let's force it. + +\typeout{Document style option `reduce' -- released 5 Nov 1991.} + +% **************************************** +% * FONTS * +% **************************************** +% + +\lineskip 1pt % \lineskip is 1pt for all font sizes. +\normallineskip 1pt +\def\baselinestretch{1} + +% Each size-changing command \SIZE executes the command +% \@setsize\SIZE{BASELINESKIP}\FONTSIZE\@FONTSIZE +% where: +% BASELINESKIP = Normal value of \baselineskip for that size. (Actual +% value will be \baselinestretch * BASELINESKIP.) +% +% \FONTSIZE = Name of font-size command. The currently available +% (preloaded) font sizes are: \vpt (5pt), \vipt (6pt), +% \viipt (etc.), \viiipt, \ixpt, \xpt, \xipt, \xiipt, +% \xivpt, \xviipt, \xxpt, \xxvpt. +% \@FONTSIZE = The same as the font-size command except with an +% '@' in front---e.g., if \FONTSIZE = \xivpt then +% \@FONTSIZE = \@xivpt. +% +% For reasons of efficiency that needn't concern the designer, +% the document style defines \@normalsize instead of \normalsize. This +% is done only for \normalsize, not for any other size-changing +% commands. + +\def\@normalsize{\@setsize\normalsize{13.6pt}\xipt\@xipt +\abovedisplayskip .5\baselineskip +\belowdisplayskip \abovedisplayskip +\abovedisplayshortskip \z@ plus3\p@ +\belowdisplayshortskip 6.5\p@ plus3.5\p@ minus3\p@ +\let\@listi\@listI} % Setting of \@listi added 9 Jun 87 + +\def\small{\@setsize\small{12pt}\xpt\@xpt +\abovedisplayskip .5\baselineskip +\belowdisplayskip \abovedisplayskip +\abovedisplayshortskip \z@ plus3\p@ +\belowdisplayshortskip 6\p@ plus3\p@ minus3\p@ +\def\@listi{\leftmargin\leftmargini %% Added 22 Dec 87 +\topsep \z@\parsep 3\p@ plus2\p@ minus\p@ +\itemsep .5\baselineskip}} + +\def\footnotesize{\@setsize\footnotesize{11pt}\ixpt\@ixpt +\abovedisplayskip .5\baselineskip +\belowdisplayskip \abovedisplayskip +\abovedisplayshortskip \z@ plus\p@ +\belowdisplayshortskip 4\p@ plus2\p@ minus2\p@ +\def\@listi{\leftmargin\leftmargini %% Added 22 Dec 87 +\topsep \z@ \parsep 2\p@ plus\p@ minus\p@ +\itemsep .5\baselineskip}} + +\def\scriptsize{\@setsize\scriptsize{9.5pt}\viiipt\@viiipt} +\def\tiny{\@setsize\tiny{7pt}\vipt\@vipt} +\def\large{\@setsize\large{14pt}\xiipt\@xiipt} +\def\Large{\@setsize\Large{18pt}\xivpt\@xivpt} +\def\LARGE{\@setsize\LARGE{22pt}\xviipt\@xviipt} +\def\huge{\@setsize\huge{25pt}\xxpt\@xxpt} +\def\Huge{\@setsize\Huge{30pt}\xxvpt\@xxvpt} + +\normalsize % Choose the normalsize font. + + +% **************************************** +% * PAGE LAYOUT * +% **************************************** +% +% All margin dimensions measured from a point one inch from top and side +% of page. + +% SIDE MARGINS: +\if@twoside % Values for two-sided printing: + \oddsidemargin 36pt % Left margin on odd-numbered pages. + \evensidemargin 74pt % Left margin on even-numbered pages. + \marginparwidth 100pt % Width of marginal notes. +\else % Values for one-sided printing: + \oddsidemargin 54pt % Note that \oddsidemargin = \evensidemargin + \evensidemargin 54pt + \marginparwidth 83pt +\fi +\marginparsep 10pt % Horizontal space between outer margin and + % marginal note + + +% VERTICAL SPACING: + % Top of page: +\topmargin 27pt % Nominal distance from top of page to top + % of box containing running head. +\headheight 12pt % Height of box containing running head. +\headsep 25pt % Space between running head and text. +% \topskip = 10pt % '\baselineskip' for first line of page. + % Bottom of page: +\footskip 30pt % Distance from baseline of box containing + % foot to baseline of last line of text. + +% DIMENSION OF TEXT: +% 24 Jun 86: changed to explicitly compute \textheight to avoid +% roundoff. The value of the multiplier was calculated as the floor of +% the old \textheight minus \topskip, divided by \baselineskip for +% \normalsize. The old value of \textheight was 530.4pt. +% \textheight is the height of text (including footnotes and figures, +% excluding running head and foot). + +\textheight = 38\baselineskip +\advance\textheight by \topskip +\textwidth 360pt % Width of text line. + % For two-column mode: +\columnsep 10pt % Space between columns +\columnseprule 0pt % Width of rule between columns. + +% A \raggedbottom command causes 'ragged bottom' pages: pages set to +% natural height instead of being stretched to exactly \textheight. + +% FOOTNOTES: + +\footnotesep 7.7pt % Height of strut placed at the beginning of every + % footnote = height of normal \footnotesize strut, + % so no extra space between footnotes. + +\skip\footins 10pt plus 4pt minus 2pt % Space between last line of text + % and top of first footnote. + +% FLOATS: (a float is something like a figure or table) +% +% FOR FLOATS ON A TEXT PAGE: +% +% ONE-COLUMN MODE OR SINGLE-COLUMN FLOATS IN TWO-COLUMN MODE: +\floatsep 12pt plus 2pt minus 2pt % Space between adjacent floats + % moved to top or bottom of + % text page. +\textfloatsep 20pt plus 2pt minus 4pt % Space between main text and + % floats at top or bottom of + % page. +\intextsep 12pt plus 2pt minus 2pt % Space between in-text figures + % and text. +\@maxsep 20pt % The maximum of \floatsep, + % \textfloatsep and \intextsep + % (minus the stretch and + % shrink). +% TWO-COLUMN FLOATS IN TWO-COLUMN MODE: +\dblfloatsep 12pt plus 2pt minus 2pt % Same as \floatsep for + % double-column figures in + % two-column mode. +\dbltextfloatsep 20pt plus 2pt minus 4pt % \textfloatsep for + % double-column floats. +\@dblmaxsep 20pt % The maximum of \dblfloatsep + % and \dbltexfloatsep. + +% FOR FLOATS ON A SEPARATE FLOAT PAGE OR COLUMN: +% ONE-COLUMN MODE OR SINGLE-COLUMN FLOATS IN TWO-COLUMN MODE: +\@fptop 0pt plus 1fil % Stretch at top of float page/column. (Must + % be 0pt plus ...) +\@fpsep 8pt plus 2fil % Space between floats on float page/column. +\@fpbot 0pt plus 1fil % Stretch at bottom of float page/column. (Must + % be 0pt plus ... ) + +% DOUBLE-COLUMN FLOATS IN TWO-COLUMN MODE. +\@dblfptop 0pt plus 1fil % Stretch at top of float page. (Must be 0pt + % plus ...) +\@dblfpsep 8pt plus 2fil % Space between floats on float page. +\@dblfpbot 0pt plus 1fil % Stretch at bottom of float page. (Must be + % 0pt plus ... ) +% MARGINAL NOTES: +% +\marginparpush 5pt % Minimum vertical separation between two + % marginal notes. + + +% **************************************** +% * PARAGRAPHING * +% **************************************** +% +\parskip 6pt plus 1pt %% RmS % Extra vertical space between + % paragraphs. +\parindent 0pt %% RmS % Width of paragraph indentation. +\topsep 0pt %% RmS % Extra vertical space, in addition + % to \parskip, added above and below + % list and paragraphing environments. +\partopsep 0pt %% RmS % Extra vertical space, in addition + % to \parskip and \topsep, added when + % user leaves blank line before + % environment. +\itemsep \topsep %% RmS % Extra vertical space, in addition + % to \parskip, added between list + % items. +% See \@listI for values of \topsep and \itemsep + +% The following page-breaking penalties are defined + +\@lowpenalty 51 % Produced by \nopagebreak[1] or \nolinebreak[1] +\@medpenalty 151 % Produced by \nopagebreak[2] or \nolinebreak[2] +\@highpenalty 301 % Produced by \nopagebreak[3] or \nolinebreak[3] + +\@beginparpenalty -\@lowpenalty % Before a list or paragraph + % environment. +\@endparpenalty -\@lowpenalty % After a list or paragraph + % environment. +\@itempenalty -\@lowpenalty % Between list items. + +% \clubpenalty % 'Club line' at bottom of page. +% \widowpenalty % 'Widow line' at top of page. +% \displaywidowpenalty % Math display widow line. +% \predisplaypenalty % Breaking before a math display. +% \postdisplaypenalty % Breaking after a math display. +% \interlinepenalty % Breaking at a line within a paragraph. +% \brokenpenalty % Breaking after a hyphenated line. + + +% **************************************** +% * SECTIONS * +% **************************************** +% + +% \@startsection {NAME}{LEVEL}{INDENT}{BEFORESKIP}{AFTERSKIP}{STYLE} +% optional * [ALTHEADING]{HEADING} +% Generic command to start a section. +% NAME : e.g., 'subsection' +% LEVEL : a number, denoting depth of section -- i.e., +% section=1, subsection = 2, etc. A section number will +% be printed if and only if LEVEL < or = the value of +% the secnumdepth counter. +% INDENT : Indentation of heading from left margin +% BEFORESKIP : Absolute value = skip to leave above the heading. +% If negative, then paragraph indent of text following +% heading is suppressed. +% AFTERSKIP : if positive, then skip to leave below heading, +% else - skip to leave to right of run-in heading. +% STYLE : commands to set style +% If '*' missing, then increments the counter. If it is present, then +% there should be no [ALTHEADING] argument. A sectioning command +% is normally defined to \@startsection + its first six arguments. + +\def\section{\@startsection {section}{1}{\z@}{-3.5ex plus-1ex minus + -.2ex}{2.3ex plus.2ex}{\reset@font\Large\bf}} +\def\subsection{\@startsection{subsection}{2}{\z@}{-3.25ex plus-1ex + minus-.2ex}{1.5ex plus.2ex}{\reset@font\large\bf}} +\def\subsubsection{\@startsection{subsubsection}{3}{\z@}{-3.25ex plus + -1ex minus-.2ex}{1.5ex plus.2ex}{\reset@font\normalsize\bf}} +\def\paragraph{\@startsection + {paragraph}{4}{\z@}{3.25ex plus1ex minus.2ex}{-1em}{\reset@font + \normalsize\bf}} +\def\subparagraph{\@startsection + {subparagraph}{4}{\parindent}{3.25ex plus1ex minus + .2ex}{-1em}{\reset@font\normalsize\bf}} + + +% Default initializations of \...mark commands. (See below for their +% use in defining page styles. +% + +% \def\sectionmark#1{} % Preloaded definitions +% \def\subsectionmark#1{} +% \def\subsubsectionmark#1{} +% \def\paragraphmark#1{} +% \def\subparagraphmark#1{} + +% The value of the counter secnumdepth gives the depth of the +% highest-level sectioning command that is to produce section numbers. +% + +\setcounter{secnumdepth}{3} + +% APPENDIX +% +% The \appendix command must do the following: +% -- reset the section and subsection counters to zero +% -- redefine the section counter to produce appendix numbers +% -- redefine the \section command if appendix titles and headings +% are to look different from section titles and headings. + +\def\appendix{\par + \setcounter{section}{0} + \setcounter{subsection}{0} + \def\thesection{\Alph{section}}} + + +% **************************************** +% * LISTS * +% **************************************** +% + +% The following commands are used to set the default values for the list +% environment's parameters. See the LaTeX manual for an explanation of +% the meanings of the parameters. Defaults for the list environment are +% set as follows. First, \rightmargin, \listparindent and \itemindent +% are set to 0pt. Then, for a Kth level list, the command \@listK is +% called, where 'K' denotes 'i', 'ii', ... , 'vi'. (I.e., \@listiii is +% called for a third-level list.) By convention, \@listK should set +% \leftmargin to \leftmarginK. +% + +\leftmargini 2.5em +\leftmarginii 2.2em % > \labelsep + width of '(m)' +\leftmarginiii 1.87em % > \labelsep + width of 'vii.' +\leftmarginiv 1.7em % > \labelsep + width of 'M.' +\leftmarginv 1em +\leftmarginvi 1em + +\leftmargin\leftmargini +\labelsep .5em +\labelwidth\leftmargini\advance\labelwidth-\labelsep +%\parsep 4.5pt plus 2pt minus 1pt %(Removed 9 Jun 87) + +% \@listI defines top level and \@listi values of +% \leftmargin, \topsep, \parsep, and \itemsep +% (Added 9 Jun 87) +\def\@listI{\leftmargin\leftmargini \parsep 4.5\p@ plus2\p@ minus\p@ +\topsep \z@ \itemsep \topsep} + +\let\@listi\@listI +\@listi + +\def\@listii{\leftmargin\leftmarginii + \labelwidth\leftmarginii\advance\labelwidth-\labelsep + \topsep \z@ \itemsep \topsep + \parsep 2\p@ plus\p@ minus\p@} + +\def\@listiii{\leftmargin\leftmarginiii + \labelwidth\leftmarginiii\advance\labelwidth-\labelsep + \topsep \z@ \itemsep \topsep + \parsep \z@ \partopsep\z@} + +\def\@listiv{\leftmargin\leftmarginiv + \labelwidth\leftmarginiv\advance\labelwidth-\labelsep} + + + + + +%% RmS: which at the same time makes the vertical space in lists (verbatim...) +%% too large if not other precautions are taken. +\setlength{\parindent}{0pt} +\setlength{\parskip}{6pt} +\raggedbottom + + +% Various boxes. +\newlength{\reduceboxwidth} +\setlength{\reduceboxwidth}{4in} + +\newlength{\redboxwidth} +\setlength{\redboxwidth}{3.5in} + +\newlength{\rboxwidth} +\setlength{\rboxwidth}{2.6in} + +% These are here in case the name changes or we someday want a special +% font. +\newcommand{\REDUCE}{REDUCE} +\newcommand{\RLISP}{RLISP} + +% This is useful for putting function names in \tt format in the index. +\newcommand{\ttindex}[1]{\index{#1@{\tt #1}}} + +% Use this when you are speaking about problems across systems. +\newcommand{\COMPATNOTE}{{\em Compatibility Note:\ }} + +\pagestyle{headings} + +%% For BNF notation. + +% \s{...} is a sentential form in descriptions. Enclosed \em text in <...> +\newcommand{\s}[1] {$<${\em #1}$>$} + +% \meta{...} is an alternative sentential form in descriptions using \it. +\newcommand{\meta}[1]{\mbox{$\langle$\it#1\/$\rangle$}} + +% \k{...} is a keyword. Just do in bold for the moment. +\newcommand{\k}[1] {{\bf #1}} + +% \f is a function name. Just do this as tt. +\newcommand{\f}[1] {{\tt #1}} + +% An example macro for numbering and indenting examples. +\newcounter{examplectr} +\newcommand{\example}{\refstepcounter{examplectr} +\noindent{\bf Example \theexamplectr}} + +% The following are currently only used in the GENTRAN document. However, +% there's no objection to using them elsewhere. + +\begingroup + \catcode `|=0 + \catcode `[= 1 + \catcode`]=2 + \catcode `\{=12 + \catcode `\}=12 + \catcode`\\=12 + |gdef|@xframedverbatim#1\end{framedverbatim}[#1|end[framedverbatim]] + |gdef|@sxframedverbatim#1\end{framedverbatim*}[#1|end[framedverbatim*]] +|endgroup + +\newdimen\@mcdheight + +\def\@sframedverbatim{\obeyspaces\@framedverbatim} + +\def\@mcdrule{\@mcdheight=\baselineskip\advance\@mcdheight by-2pt +\setbox0=\hbox{\vrule height\@mcdheight depth 2pt width 1pt}% +\ht0=\@mcdheight\dp0=0pt\wd0=1pt\box0} + +\def\@mcdendrule{\@mcdheight=\baselineskip% +\setbox0=\hbox{\vrule height\@mcdheight depth 2pt width 1pt}% +\ht0=\@mcdheight\dp0=0pt\wd0=1pt\box0} + +\def\@framedverbatim{\trivlist \item[] +\parskip \z@ +\hrule \@height \p@ \@depth \z@ \@width\textwidth +\everypar{\global \@minipagefalse \global \@newlistfalse \if@inlabel +\global \@inlabelfalse \hskip -\parindent \box \@labels \penalty \z@ \fi +\hbox to6\p@{\rlap{\@mcdrule}\hskip\textwidth\llap{\@mcdrule}\hss}}% +\if@minipage\else\vskip\parskip\fi +\leftskip\@totalleftmargin\rightskip\z@ +\parindent\z@\parfillskip\@flushglue\parskip\z@ +\@tempswafalse \def\par{\if@tempswa\hbox{}\fi\@tempswatrue\@@par +\penalty\interlinepenalty}% % fix \samepage bug +\obeylines \tt \catcode``=13 \@noligs \let\do\@makeother \dospecials} + +\def\framedverbatim{\@framedverbatim \frenchspacing\@vobeyspaces + \@xframedverbatim} + +\def\endframedverbatim{\nointerlineskip +{\everypar{}\baselineskip 4\p@\vbox to4\p@{\par\noindent\hbox + to6pt{\rlap{\@mcdendrule}\hskip\textwidth\llap{\@mcdendrule}\hss}}% +\vskip\p@\hrule \@height \p@ \@depth \z@ \@width\textwidth}\endtrivlist} + +\@namedef{framedverbatim*}{\@framedverbatim\@sxframedverbatim} + +\expandafter\let\csname endframedverbatim*\endcsname =\endtrivlist + +% Will print out a heading in bold, and then indent the following text. +\def\indented{\list{}{ + \itemindent\listparindent + \rightmargin\leftmargin}\item[]} +\let\endindented=\endlist +\newenvironment{describe}[1]{\par{\bf #1}\begin{indented}}{\end{indented}} + +\@ifundefined{reset@font}{\let\reset@font\@empty}{} + +\endinput Index: r36/doc/REDUCE.TEX ================================================================== --- r36/doc/REDUCE.TEX +++ r36/doc/REDUCE.TEX @@ -1,8118 +1,8118 @@ -% The REDUCE User's Manual --- LaTeX version. -% To create this manual, the following steps are recommended: -% latex reduce -% latex reduce -% latex reduce -% makeindex reduce -% latex reduce - -\documentstyle[11pt,makeidx]{book} - -\setlength{\parindent}{0pt} - -\setlength{\parskip}{6pt} - -\setlength{\hfuzz}{5pt} % don't complain about tiny overfull boxes -\setlength{\vfuzz}{1pt} - -\renewcommand{\sloppy}{\tolerance=9999\relax%} - \setlength{\emergencystretch}{0.2\hsize}} - -\tolerance=1000 - -\raggedbottom - -\newlength{\reduceboxwidth} -\setlength{\reduceboxwidth}{4in} - -\newlength{\redboxwidth} -\setlength{\redboxwidth}{3.5in} - -\newlength{\rboxwidth} -\setlength{\rboxwidth}{2.6in} - -\newcommand{\REDUCE}{REDUCE} -\newcommand{\RLISP}{RLISP} -\newcommand{\underscore}{\_} -\newcommand{\ttindex}[1]{{\renewcommand{\_}{\protect\underscore}% - \index{#1@{\tt #1}}}} -\newcommand{\COMPATNOTE}{{\em Compatibility Note:\ }} -% \meta{...} is an alternative sentential form in descriptions using \it. -\newcommand{\meta}[1]{\mbox{$\langle$\it#1\/$\rangle$}} - -% Close up default vertical spacings: -\setlength{\topsep}{0.5\baselineskip} % above and below environments -\setlength{\itemsep}{\topsep} -\setlength{\abovedisplayskip}{\topsep} % for "long" equations -\setlength{\belowdisplayskip}{\topsep} - -\newcommand{\key}[1]{\fbox{\sf #1}} - -\pagestyle{headings} - -\makeindex - -\begin{document} -\pagestyle{empty} -\begin{titlepage} -\vspace*{\fill} -\begin{center} - -{\Huge\bf {\REDUCE}} \\ [0.2cm] -{\LARGE\bf User's Manual\vspace{0.4cm} \\ - Version 3.6} - -\vspace{0.5in}\large\bf - -Anthony C.\ Hearn \\ -RAND \\ -Santa Monica, CA 90407-2138 - -\vspace{0.1in} - -\bf Email: reduce@rand.org - -\vspace{0.5in} - -\large\bf July 1995 - -\vspace*{2.5in} - -\bf RAND Publication CP78 (Rev. 7/95) -\end{center} -\end{titlepage} - -\newpage -\vspace*{3.0in} -\noindent Copyright \copyright 1995 RAND. All rights reserved. \\ -\mbox{}\\ -% -\noindent Registered system holders may reproduce all or any part of this -publication for internal purposes, provided that the source of the -material is clearly acknowledged, and the copyright notice is retained. - -\pagestyle{headings} -\setcounter{page}{0} -\tableofcontents - -\chapter*{Abstract} - -\addcontentsline{toc}{chapter}{Abstract} - -This document provides the user with a description of the algebraic -programming system {\REDUCE}. The capabilities of this system include: -\begin{enumerate} -\item expansion and ordering of polynomials and rational functions, -\item substitutions and pattern matching in a wide variety of forms, -\item automatic and user controlled simplification of expressions, -\item calculations with symbolic matrices, -\item arbitrary precision integer and real arithmetic, -\item facilities for defining new functions and extending program syntax, -\item analytic differentiation and integration, -\item factorization of polynomials, -\item facilities for the solution of a variety of algebraic equations, -\item facilities for the output of expressions in a variety of formats, -\item facilities for generating numerical programs from symbolic input, -\item Dirac matrix calculations of interest to high energy physicists. -\end{enumerate} - -\chapter*{Acknowledgment} - -The production of this version of the manual has been the result of the -contributions of a large number of individuals who have taken the time and -effort to suggest improvements to previous versions, and to draft new -sections. Particular thanks are due to Gerry Rayna, who provided a draft -rewrite of most of the first half of the manual. Other people who have -made significant contributions have included John Fitch, Martin Griss, -Stan Kameny, Jed Marti, Herbert Melenk, Don Morrison, Arthur Norman, -Eberhard Schr\"ufer and Larry Seward. Finally, Richard Hitt produced a {\TeX} -version of the {\REDUCE} 3.3 manual, which has been a useful guide for the -production of the {\LaTeX} version of this manual. - -\chapter{Introductory Information} - -\index{Introduction}{\REDUCE} is a system for carrying out algebraic -operations accurately, no matter how complicated the expressions become. -It can manipulate polynomials in a variety of forms, both expanding and -factoring them, and extract various parts of them as required. {\REDUCE} can -also do differentiation and integration, but we shall only show trivial -examples of this in this introduction. Other topics not -considered include the use of arrays, the definition of procedures and -operators, the specific routines for high energy physics calculations, the -use of files to eliminate repetitious typing and for saving results, and -the editing of the input text. - -Also not considered in any detail in this introduction are the many options -that are available for varying computational procedures, output forms, -number systems used, and so on. - -{\REDUCE} is designed to be an interactive system, so that the user can input -an algebraic expression and see its value before moving on to the next -calculation. For those systems that do not support interactive use, or -for those calculations, especially long ones, for which a standard script -can be defined, {\REDUCE} can also be used in batch mode. In this case, -a sequence of commands can be given to {\REDUCE} and results obtained -without any user interaction during the computation. - -In this introduction, we shall limit ourselves to the interactive use of -{\REDUCE}, since this illustrates most completely the capabilities of the -system. When {\REDUCE} is called, it begins by printing a banner message -like: -\begin{verbatim} - REDUCE 3.6, 15-Jul-95 ... -\end{verbatim} -where the version number and the system release date will change from time -to time. It then prompts the user for input by: -\begin{verbatim} - 1: -\end{verbatim} -You can now type a {\REDUCE} statement, terminated by a semicolon to indicate -the end of the expression, for example: -\begin{verbatim} - (x+y+z)^2; -\end{verbatim} -This expression would normally be followed by another character (a -\key{Return} on an ASCII keyboard) to ``wake up'' the system, which would -then input the expression, evaluate it, and return the result: -\begin{verbatim} - 2 2 2 - X + 2*X*Y + 2*X*Z + Y + 2*Y*Z + Z -\end{verbatim} -Let us review this simple example to learn a little more about the way that -{\REDUCE} works. First, we note that {\REDUCE} deals with variables, and -constants like other computer languages, but that in evaluating the former, -a variable can stand for itself. Expression evaluation normally follows -the rules of high school algebra, so the only surprise in the above example -might be that the expression was expanded. {\REDUCE} normally expands -expressions where possible, collecting like terms and ordering the -variables in a specific manner. However, expansion, ordering of variables, -format of output and so on is under control of the user, and various -declarations are available to manipulate these. - -Another characteristic of the above example is the use of lower case on -input and upper case on output. In fact, input may be in either mode, but -output is usually in lower case. To make the difference between input and -output more distinct in this manual, all expressions intended for input -will be shown in lower case and output in upper case. However, for -stylistic reasons, we represent all single identifiers in the text in -upper case. - -Finally, the numerical prompt can be used to reference the result in a -later computation. - -As a further illustration of the system features, the user should try: -\begin{verbatim} - for i:= 1:40 product i; -\end{verbatim} -The result in this case is the value of 40!, -\begin{verbatim} - 815915283247897734345611269596115894272000000000 -\end{verbatim} -You can also get the same result by saying -\begin{verbatim} - factorial 40; -\end{verbatim} -Since we want exact results in algebraic calculations, it is essential that -integer arithmetic be performed to arbitrary precision, as in the above -example. Furthermore, the {\tt FOR} statement in the above is illustrative of a -whole range of combining forms that {\REDUCE} supports for the convenience of -the user. - -Among the many options in {\REDUCE} is the use of other number systems, such -as multiple precision floating point with any specified number of digits --- -of use if roundoff in, say, the $100^{th}$ digit is all that can be tolerated. - -In many cases, it is necessary to use the results of one calculation in -succeeding calculations. One way to do this is via an assignment for a -variable, such as -\begin{verbatim} - u := (x+y+z)^2; -\end{verbatim} -If we now use {\tt U} in later calculations, the value of the right-hand -side of the above will be used. - -The results of a given calculation are also saved in the variable -{\tt WS}\ttindex{WS} (for WorkSpace), so this can be used in the next -calculation for further processing. - -For example, the expression -\begin{verbatim} - df(ws,x); -\end{verbatim} -following the previous evaluation will calculate the derivative of -{\tt (x+y+z)\verb|^|2} with respect to {\tt X}. Alternatively, -\begin{verbatim} - int(ws,y); -\end{verbatim} -would calculate the integral of the same expression with respect to y. - -{\REDUCE} is also capable of handling symbolic matrices. For example, -\begin{verbatim} - matrix m(2,2); -\end{verbatim} -declares m to be a two by two matrix, and -\begin{verbatim} - m := mat((a,b),(c,d)); -\end{verbatim} -gives its elements values. Expressions that include {\tt M} and make -algebraic sense may now be evaluated, such as {\tt 1/m} to give the -inverse, {\tt 2*m - u*m\verb|^|2} to give us another matrix and {\tt det(m)} -to give us the determinant of {\tt M}. - -{\REDUCE} has a wide range of substitution capabilities. The system knows -about elementary functions, but does not automatically invoke many of their -well-known properties. For example, products of trigonometrical functions -are not converted automatically into multiple angle expressions, but if the -user wants this, he can say, for example: -\begin{verbatim} - (sin(a+b)+cos(a+b))*(sin(a-b)-cos(a-b)) - where cos(~x)*cos(~y) = (cos(x+y)+cos(x-y))/2, - cos(~x)*sin(~y) = (sin(x+y)-sin(x-y))/2, - sin(~x)*sin(~y) = (cos(x-y)-cos(x+y))/2; -\end{verbatim} -where the tilde in front of the variables {\tt X} and {\tt Y} indicates -that the rules apply for all values of those variables. -The result of this calculation is -\begin{verbatim} - -(COS(2*A) + SIN(2*B)) -\end{verbatim} -Another very commonly used capability of the system, and an illustration -of one of the many output modes of {\REDUCE}, is the ability to output -results in a FORTRAN compatible form. Such results can then be used in a -FORTRAN based numerical calculation. This is particularly useful as a way -of generating algebraic formulas to be used as the basis of extensive -numerical calculations. - -For example, the statements -\begin{verbatim} - on fort; - df(log(x)*(sin(x)+cos(x))/sqrt(x),x,2); -\end{verbatim} -will result in the output -\begin{verbatim} - ANS=(-4.*LOG(X)*COS(X)*X**2-4.*LOG(X)*COS(X)*X+3.* - . LOG(X)*COS(X)-4.*LOG(X)*SIN(X)*X**2+4.*LOG(X)* - . SIN(X)*X+3.*LOG(X)*SIN(X)+8.*COS(X)*X-8.*COS(X)-8. - . *SIN(X)*X-8.*SIN(X))/(4.*SQRT(X)*X**2) -\end{verbatim} -These algebraic manipulations illustrate the algebraic mode of {\REDUCE}. -{\REDUCE} is based on Standard Lisp. A symbolic mode is also available for -executing Lisp statements. These statements follow the syntax of Lisp, -e.g. -\begin{verbatim} - symbolic car '(a); -\end{verbatim} -Communication between the two modes is possible. - -With this simple introduction, you are now in a position to study the -material in the full {\REDUCE} manual in order to learn just how extensive -the range of facilities really is. If further tutorial material is -desired, the seven {\REDUCE} Interactive Lessons by David R. Stoutemyer are -recommended. These are normally distributed with the system. - -\chapter{Structure of Programs} - -A {\REDUCE} program\index{Program structure} consists of a set of -functional commands which are evaluated sequentially by the computer. -These commands are built up from declarations, statements and expressions. -Such entities are composed of sequences of numbers, variables, operators, -strings, reserved words and delimiters (such as commas and parentheses), -which in turn are sequences of basic characters. - -\section{The {\REDUCE} Standard Character Set} - -\index{Character set}The basic characters which are used to build -{\REDUCE} symbols are the following: -\begin{enumerate} -\item The 26 letters {\tt a} through {\tt z} -\item The 10 decimal digits {\tt 0} through {\tt 9} -\item The special characters \_\_ ! " \$ \% ' ( ) * + , - . / : ; $<$ $>$ - = \{ \} $<$blank$>$ -\end{enumerate} -With the exception of strings and characters preceded by an -exclamation mark\index{Exclamation mark}, the case -of characters is ignored: depending of the underlying LISP -they will all be converted internally into lower case or -upper case: {\tt ALPHA}, {\tt Alpha} and {\tt alpha} -represent the same symbol. Most implementations allow you to switch -this conversion off. The operating instructions for a particular -implementation should be consulted on this point. For portability, we -shall limit ourselves to the standard character set in this exposition. - -\section{Numbers} - -\index{Number}There are several different types of numbers available in -\REDUCE. Integers consist of a signed or unsigned sequence of decimal -digits written without a decimal point, for example: -\begin{verbatim} - -2, 5396, +32 -\end{verbatim} -In principle, there is no practical limit on the number of digits -permitted as exact arithmetic is used in most implementations. (You should -however check the specific instructions for your particular system -implementation to make sure that this is true.) For example, if you ask -for the value of $2^{2000}$ you get it -displayed as a number of 603 decimal digits, taking up nine lines of -output on an interactive display. It should be borne in mind of course -that computations with such long numbers can be quite slow. - -Numbers that aren't integers are usually represented as the quotient of -two integers, in lowest terms: that is, as rational numbers. - -In essentially all versions of {\REDUCE} it is also possible (but not always -desirable!) to ask {\REDUCE} to work with floating point approximations to -numbers again, to any precision. Such numbers are called {\em real}. -\index{Real} They can be input in two ways: -\begin{enumerate} -\item as a signed or unsigned sequence of any number of decimal digits - with an embedded or trailing decimal point. -\item as in 1. followed by a decimal exponent which is written as the - letter {\tt E} followed by a signed or unsigned integer. -\end{enumerate} -e.g. {\tt 32. +32.0 0.32E2} and {\tt 320.E-1} are all representations of -32. - -The declaration {\tt SCIENTIFIC\_NOTATION}\ttindex{SCIENTIFIC\_NOTATION} -controls the output format of floating point numbers. At -the default settings, any number with five or less digits before the -decimal point is printed in a fixed-point notation, e.g., {\tt 12345.6}. -Numbers with more than five digits are printed in scientific notation, -e.g., {\tt 1.234567E+5}. Similarly, by default, any number with eleven or -more zeros after the decimal point is printed in scientific notation. To -change these defaults, {\tt SCIENTIFIC\_NOTATION} can be used in one of two -ways. {\tt SCIENTIFIC\_NOTATION} {\em m};, where {\em m\/} is a positive -integer, sets the printing format so that a number with more than {\em m\/} -digits before the decimal point, or {\em m\/} or more zeros after the -decimal point, is printed in scientific notation. {\tt SCIENTIFIC\_NOTATION} -\{{\em m,n}\}, with {\em m\/} and {\em n\/} both positive integers, sets the -format so that a number with more than {\em m\/} digits before the decimal -point, or {\em n\/} or more zeros after the decimal point is printed in -scientific notation. - -{\it CAUTION:} The unsigned part of any number\index{Number} may {\em not\/} -begin with a decimal point, as this causes confusion with the {\tt CONS} (.) -operator, i.e., NOT ALLOWED: {\tt .5 -.23 +.12}; -use {\tt 0.5 -0.23 +0.12} instead. - -\section{Identifiers} - -Identifiers\index{Identifier} in {\REDUCE} consist of one or more -alphanumeric characters (i.e. alphabetic letters or decimal -digits) the first of which must be alphabetic. The maximum number of -characters allowed is implementation dependent, although twenty-four is -permitted in most implementations. In addition, the underscore character -(\_) is considered a letter if it is {\it within} an identifier. For example, -\begin{verbatim} - a az p1 q23p a_very_long_variable -\end{verbatim} -are all identifiers, whereas -\begin{verbatim} - _a -\end{verbatim} -is not. - -A sequence of alphanumeric characters in which the first is a digit is -interpreted as a product. For example, {\tt 2ab3c} is interpreted as -{\tt 2*ab3c}. There is one exception to this: If the first letter after a -digit is {\tt E}, the system will try to interpret that part of the -sequence as a real number\index{Real}, which may fail in some cases. For -example, {\tt 2E12} is the real number $2.0*10^{12}$, {\tt 2e3c} is -2000.0*C, and {\tt 2ebc} gives an error. - -Special characters, such as $-$, *, and blank, may be used in identifiers -too, even as the first character, but each must be preceded by an -exclamation mark in input. For example: -\begin{verbatim} - light!-years d!*!*n good! morning - !$sign !5goldrings -\end{verbatim} -{\it CAUTION:} Many system identifiers have such special characters in their -names (especially * and =). If the user accidentally picks the name of one -of them for his own purposes it may have catastrophic consequences for his -{\REDUCE} run. Users are therefore advised to avoid such names. - -Identifiers are used as variables, labels and to name arrays, operators -and procedures. - -\subsection*{Restrictions} - -The reserved words listed in another section may not be used as -identifiers. No spaces may appear within an identifier, and an identifier -may not extend over a line of text. (Hyphenation of an identifier, by -using a reserved character as a hyphen before an end-of-line character is -possible in some versions of {\REDUCE}). - -\section{Variables} - -Every variable\index{Variable} is named by an identifier, and is given a -specific type. The type is of no concern to the ordinary user. Most -variables are allowed to have the default type, called {\em scalar}. -These can receive, as values, the representation of any ordinary algebraic -expression. In the absence of such a value, they stand for themselves. - -\subsection*{Reserved Variables} - -Several variables\index{Reserved variable} in {\REDUCE} have particular -properties which should not be changed by the user. These variables -include: - -\begin{list}{}{\renewcommand{\makelabel}[1]{{\tt#1}\hspace{\fill}}% - \settowidth{\labelwidth}{\tt INFINITY}% - \setlength{\labelsep}{1em}% - \settowidth{\leftmargin}{\tt INFINITY\hspace*{\labelsep}}} -\item[E] Intended to represent the base of -\ttindex{E} -the natural logarithms. {\tt log(e)}, if it occurs in an expression, is -automatically replaced by 1. If {\tt ROUNDED}\ttindex{ROUNDED} is -on, {\tt E} is replaced by the value of E to the current degree of -floating point precision\index{Numerical precision}. - -\item[I] Intended to represent the square -\ttindex{I} -root of $-1$. {\tt i\verb|^|2} is replaced by $-1$, and appropriately for higher -powers of {\tt I}. This applies only to the symbol {\tt I} used on the top -level, not as a formal parameter in a procedure, a local variable, nor in -the context {\tt for i:= ...} - -\item[INFINITY] Intended to represent $\infty$ -\ttindex{INFINITY} -in limit and power series calculations for example. Note however that the -current system does {\em not\/} do proper arithmetic on $\infty$. For example, -{\tt infinity + infinity} is {\tt 2*infinity}. - -\item[NIL] In {\REDUCE} (algebraic mode only) -taken as a synonym for zero. Therefore {\tt NIL} cannot be used as a -variable. - -\item[PI] Intended to represent the circular -\ttindex{PI} -constant. With {\tt ROUNDED} on, it is replaced by the value of $\pi$ to -the current degree of floating point precision. - -\item[T] Should not be used as a formal -\ttindex{T} -parameter or local variable in procedures, since conflict arises with the -symbolic mode meaning of T as {\em true}. -\end{list} - -Other reserved variables, such as {\tt LOW\_POW}, described in other sections, -are listed in Appendix A. - -Using these reserved variables\index{Reserved variable} inappropriately -will lead to errors. - -There are also internal variables used by {\REDUCE} that have similar -restrictions. These usually have an asterisk in their names, so it is -unlikely a casual user would use one. An example of such a variable is -{\tt K!*} used in the asymptotic command package. - -Certain words are reserved in {\REDUCE}. They may only be used in the manner -intended. A list of these is given in the section ``Reserved Identifiers''. -There are, of course, an impossibly large number of such names to keep in -mind. The reader may therefore want to make himself a copy of the list, -deleting the names he doesn't think he is likely to use by mistake. - -\section{Strings} - -Strings\index{String} are used in {\tt WRITE} statements, in other -output statements (such as error messages), and to name files. A string -consists of any number of characters enclosed in double quotes. For example: -\begin{verbatim} - "A String". -\end{verbatim} -Lower case characters within a string are not converted to upper case. - -The string {\tt ""} represents the empty string. A double quote may be -included in a string by preceding it by another double quote. Thus -{\tt "a""b"} is the string {\tt a"b}, and {\tt """"} is the string {\tt "}. - -\section{Comments} - -Text can be included in program\index{Program} listings for the -convenience of human readers, in such a way that {\REDUCE} pays no -attention to it. There are two ways to do this: - -\begin{enumerate} -\item Everything from the word {\tt COMMENT}\ttindex{COMMENT} to the next -statement terminator, normally ; or \$, is ignored. Such comments -can be placed anywhere a blank could properly appear. (Note that {\tt END} -and $>>$ are {\em not\/} treated as {\tt COMMENT} delimiters!) - -\item Everything from the symbol {\tt \%}\index{Percent sign} to the end -of the line on which it appears is ignored. Such comments can be placed -as the last part of any line. Statement terminators have no special -meaning in such comments. Remember to put a semicolon before the {\tt \%} -if the earlier part of the line is intended to be so terminated. Remember -also to begin each line of a multi-line {\tt \%} comment with a {\tt \%} -sign. -\end{enumerate} - -\section{Operators} -\label{sec-operators} - -Operators\index{Operator} in {\REDUCE} are specified by name and type. -There are two types, infix\index{Infix operator} and prefix. -\index{Prefix operator} Operators can be purely abstract, just symbols -with no properties; they can have values assigned (using {\tt :=} or -simple {\tt LET} declarations) for specific arguments; they can have -properties declared for some collection of arguments (using more general -{\tt LET} declarations); or they can be fully defined (usually by a -procedure declaration). - -Infix operators\index{Infix operator} have a definite precedence with -respect to one another, and normally occur between their arguments. -For example: -\begin{quote} -\begin{tabbing} -{\tt a + b - c} \hspace{1.5in} \= (spaces optional) \\ -{\tt x (spaces required where shown) -\end{tabbing} -\end{quote} -Spaces can be freely inserted between operators and variables or operators -and operators. They are required only where operator names are spelled out -with letters (such as the {\tt AND} in the example) and must be unambiguously -separated from another such or from a variable (like {\tt Y}). Wherever one -space can be used, so can any larger number. - -Prefix operators occur to the left of their arguments, which are written as -a list enclosed in parentheses and separated by commas, as with normal -mathematical functions, e.g., -\begin{verbatim} - cos(u) - df(x^2,x) - q(v+w) -\end{verbatim} -Unmatched parentheses, incorrect groupings of infix operators -\index{Infix operator} and the like, naturally lead to syntax errors. The -parentheses can be omitted (replaced by a space following the -operator\index{Operator} name) if the operator is unary and the argument -is a single symbol or begins with a prefix operator name: - -\begin{quote} -\begin{tabbing} -{\tt cos y} \hspace{1.75in} \= means cos(y) \\ -{\tt cos (-y)} \> -- parentheses necessary \\ -{\tt log cos y} \> means log(cos(y)) \\ -{\tt log cos (a+b)} \> means log(cos(a+b)) -\end{tabbing} -\end{quote} -but -\begin{quote} -\begin{tabbing} -{\tt cos a*b} \hspace{1.6in} \= means (cos a)*b \\ -{\tt cos -y} \> is erroneous (treated as a variable \\ -\> ``cos'' minus the variable y) -\end{tabbing} -\end{quote} -A unary prefix operator\index{Prefix operator} has a precedence -\index{Operator precedence} higher than any infix operator, including -unary infix operators. \index{Infix operator} -In other words, {\REDUCE} will always interpret {\tt cos~y + 3} as -{\tt (cos~y) + 3} rather than as {\tt cos(y + 3)}. - -Infix operators may also be used in a prefix format on input, e.g., -{\tt +(a,b,c)}. On output, however, such expressions will always be -printed in infix form (i.e., {\tt a + b + c} for this example). - -A number of prefix operators are built into the system with predefined -properties. Users may also add new operators and define their rules for -simplification. The built in operators are described in another section. - -\subsection*{Built-In Infix Operators} - -The following infix operators\index{Infix operator} are built into the -system. They are all defined internally as procedures. -\begin{verbatim} -::= where|:=|or|and|member|memq|=|neq|eq| - >=|>|<=|<|+|-|*|/|^|**|. -\end{verbatim} -These operators may be further divided into the following subclasses: -\begin{verbatim} - ::= := - ::= or|and|member|memq - ::= =|neq|eq|>=|>|<=|< - ::= where - ::= +|-|*|/|^|** - ::= . -\end{verbatim} -{\tt MEMQ} and {\tt EQ} are not used in the algebraic mode of -{\REDUCE}. They are explained in the section on symbolic mode. -{\tt WHERE} is described in the section on substitutions. - -In previous versions of {\REDUCE}, {\em not} was also defined as an infix -operator. In the present version it is a regular prefix operator, and -interchangeable with {\em null}. - -For compatibility with the intermediate language used by {\REDUCE}, each -special character infix operator\index{Infix operator} has an alternative -alphanumeric identifier associated with it. These identifiers may be used -interchangeably with the corresponding special character names on input. -This correspondence is as follows: -\begin{quote} -\begin{tabbing} -{\tt := setq} \hspace{0.5in} \= (the assignment operator) \\ -{\tt = equal} \\ -{\tt >= geq} \\ -{\tt > greaterp} \\ -{\tt <= leq} \\ -{\tt < lessp} \\ -{\tt + plus} \\ -{\tt - difference} \> (if unary, {\tt minus}) \\ -{\tt * times} \\ -{\tt / quotient} \> (if unary, {\tt recip}) \\ -{\tt \verb|^| or ** expt} \> (raising to a power) \\ -{\tt . cons} -\end{tabbing} -\end{quote} -Note: {\tt NEQ} is used to mean {\em not equal}. There is no special -symbol provided for it. - -The above operators\index{Operator} are binary, except {\tt NOT} which is -unary and {\tt +} and {\tt *} which are nary (i.e., taking an arbitrary -number of arguments). In addition, {\tt -} and {\tt /} may be used as -unary operators, e.g., /2 means the same as 1/2. Any other operator is -parsed as a binary operator using a left association rule. Thus {\tt -a/b/c} is interpreted as {\tt (a/b)/c}. There are two exceptions to this -rule: {\tt :=} and {\tt .} are right associative. Example: {\tt a:=b:=c} -is interpreted as {\tt a:=(b:=c)}. Unlike ALGOL and PASCAL, {\tt \verb|^|} is -left associative. In other words, {\tt a\verb|^|b\verb|^|c} is interpreted as -{\tt (a\verb|^|b)\verb|^|c}. - -The operators\index{Operator} {\tt $<$}, {\tt $<$=}, {\tt $>$}, {\tt $>$=} -can only be used for making comparisons between numbers. No meaning is -currently assigned to this kind of comparison between general expressions. - -Parentheses may be used to specify the order of combination. If -parentheses are omitted then this order is by the ordering of the -precedence list\index{Operator precedence} defined by the right-hand side -of the {\tt }\index{Infix operator} table -at the beginning of this section, -from lowest to highest. In other words, {\tt WHERE} has the lowest -precedence, and {\tt .} (the dot operator) the highest. - -\chapter{Expressions} - -{\REDUCE} expressions\index{Expression} may be of several types and consist -of sequences of numbers, variables, operators, left and right parentheses -and commas. The most common types are as follows: - -\section{Scalar Expressions} - -\index{Scalar}Using the arithmetic operations {\tt + - * / \verb|^|} -(power) and parentheses, scalar expressions are composed from numbers, -ordinary ``scalar'' variables (identifiers), array names with subscripts, -operator or procedure names with arguments and statement expressions. - -{\it Examples:} -\begin{verbatim} - x - x^3 - 2*y/(2*z^2 - df(x,z)) - (p^2 + m^2)^(1/2)*log (y/m) - a(5) + b(i,q) -\end{verbatim} -The symbol ** may be used as an alternative to the caret symbol (\verb+^+) -for forming powers, particularly in those systems that do not support a -caret symbol. - -Statement expressions, usually in parentheses, can also form part of -a scalar\index{Scalar} expression, as in the example -\begin{verbatim} - w + (c:=x+y) + z . -\end{verbatim} -When the algebraic value of an expression is needed, {\REDUCE} determines it, -starting with the algebraic values of the parts, roughly as follows: - -Variables and operator symbols with an argument list have the algebraic -values they were last assigned, or if never assigned stand for themselves. -However, array elements have the algebraic values they were last assigned, -or, if never assigned, are taken to be 0. - -Procedures are evaluated with the values of their actual parameters. - -In evaluating expressions, the standard rules of algebra are applied. -Unfortunately, this algebraic evaluation of an expression is not as -unambiguous as is numerical evaluation. This process is generally referred -to as ``simplification''\index{Simplification} in the sense that the -evaluation usually but not always produces a simplified form for the -expression. - -There are many options available to the user for carrying out such -simplification\index{Simplification}. If the user doesn't specify any -method, the default method is used. The default evaluation of an -expression involves expansion of the expression and collection of like -terms, ordering of the terms, evaluation of derivatives and other -functions and substitution for any expressions which have values assigned -or declared (see assignments and {\tt LET} statements). In many cases, -this is all that the user needs. - -The declarations by which the user can exercise some control over the way -in which the evaluation is performed are explained in other sections. For -example, if a real (floating point) number is encountered during -evaluation, the system will normally convert it into a ratio of two -integers. If the user wants to use real arithmetic, he can effect this by -the command {\tt on rounded;}.\ttindex{ROUNDED} Other modes for -coefficient arithmetic are described elsewhere. - -If an illegal action occurs during evaluation (such as division by zero) -or functions are called with the wrong number of arguments, and so on, an -appropriate error message is generated. -% A list of such error messages is given in an appendix. - -\section{Integer Expressions} - -\index{Integer}These are expressions which, because of the values of the -constants and variables in them, evaluate to whole numbers. - -{\it Examples:} -\begin{verbatim} - 2, 37 * 999, (x + 3)^2 - x^2 - 6*x -\end{verbatim} -are obviously integer expressions. -\begin{verbatim} - j + k - 2 * j^2 -\end{verbatim} -is an integer expression when {\tt J} and {\tt K} have values that are -integers, or if not integers are such that ``the variables and fractions -cancel out'', as in -\begin{verbatim} - k - 7/3 - j + 2/3 + 2*j^2. -\end{verbatim} - -\section{Boolean Expressions} -\label{sec-boolean} -A boolean expression\index{Boolean} returns a truth value. In the -algebraic mode of {\REDUCE}, boolean expressions have the syntactical form: -\begin{verbatim} - -\end{verbatim} -or -\begin{verbatim} - () -\end{verbatim} -or -\begin{verbatim} - - . -\end{verbatim} -Parentheses can also be used to control the precedence of expressions. - -In addition to the logical and relational operators defined earlier as -infix operators, the following boolean operators are also defined:\\ -\mbox{}\\ -\ttindex{EVENP}\ttindex{FIXP}\ttindex{FREEOF}\ttindex{NUMBERP} -\ttindex{ORDP}\ttindex{PRIMEP} -{\renewcommand{\arraystretch}{2} -\begin{tabular}{lp{\redboxwidth}} -{\tt EVENP(U)} & determines if the number {\tt U} is even or not; \\ - -{\tt FIXP(U)} & determines if the expression {\tt U} is integer or not; \\ - -{\tt FREEOF(U,V)} & determines if the expression -{\tt U} does not contain the kernel {\tt V} anywhere in its -structure; \\ - -{\tt NUMBERP(U)} & determines if {\tt U} is a number or not; \\ - -{\tt ORDP(U,V)} & determines if {\tt U} is ordered -ahead of {\tt V} by some canonical ordering (based on the expression structure -and an internal ordering of identifiers); \\ - -{\tt PRIMEP(U)} & true if {\tt U} is a prime object. \\ -\end{tabular}} - -{\it Examples:} -\begin{verbatim} - j<1 - x>0 or x=-2 - numberp x - fixp x and evenp x - numberp x and x neq 0 -\end{verbatim} -Boolean expressions can only appear directly within {\tt IF}, {\tt FOR}, -{\tt WHILE}, and {\tt UNTIL} statements, as described in other sections. -Such expressions cannot be used in place of ordinary algebraic expressions, -or assigned to a variable. - -NB: For those familiar with symbolic mode, the meaning of some of -these operators is different in that mode. For example, {\tt NUMBERP} is -true only for integers and reals in symbolic mode. - -When two or more boolean expressions are combined with {\tt AND}, they are -evaluated one by one until a {\em false\/} expression is found. The rest are -not evaluated. Thus -\begin{verbatim} - numberp x and numberp y and x>y -\end{verbatim} -does not attempt to make the {\tt x>y} comparison unless {\tt X} and {\tt Y} -are both verified to be numbers. - -Similarly, evaluation of a sequence of boolean expressions connected by -{\tt OR} stops as soon as a {\em true\/} expression is found. - -NB: In a boolean expression, and in a place where a boolean expression is -expected, the algebraic value 0 is interpreted as {\em false}, while all -other algebraic values are converted to {\em true}. So in algebraic mode -a procedure can be written for direct usage in boolean expressions, -returning say 1 or 0 as its value as in - -\begin{verbatim} - procedure polynomialp(u,x); - if den(u)=1 and deg(u,x)>=1 then 1 else 0; -\end{verbatim} - -One can then use this in a boolean construct, such as -\begin{verbatim} - if polynomialp(q,z) and not polynomialp(q,y) then ... -\end{verbatim} - -In addition, any procedure that does not have a defined return value -(for example, a block without a {\tt RETURN} statement in it) -has the boolean value {\em false}. - -\section{Equations} - -Equations\index{Equation} are a particular type of expression with the syntax - -\begin{verbatim} - = . -\end{verbatim} - -In addition to their role as boolean expressions, they can also be used as -arguments to several operators (e.g., {\tt SOLVE}), and can be -returned as values. - -Under normal circumstances, the right-hand-side of the equation is evaluated -but not the left-hand-side. If both sides are to be evaluated, the switch -{\tt EVALLHSEQP}\ttindex{EVALLHSEQP} should be turned on. - -To facilitate the handling of equations, two selectors, {\tt LHS} -\ttindex{LHS} and {\tt RHS},\ttindex{RHS} which return the left- and -right-hand sides of a equation\index{Equation} respectively, are provided. -For example, -\begin{verbatim} - lhs(a+b=c) -> a+b -and - rhs(a+b=c) -> c. -\end{verbatim} - -\section{Proper Statements as Expressions} - -Several kinds of proper statements\index{Proper statement} deliver -an algebraic or numerical result of some kind, which can in turn be used as -an expression or part of an expression. For example, an assignment -statement itself has a value, namely the value assigned. So -\begin{verbatim} - 2 * (x := a+b) -\end{verbatim} -is equal to {\tt 2*(a+b)}, as well as having the ``side-effect''\index{Side -effect} of assigning the value {\tt a+b} to {\tt X}. In context, -\begin{verbatim} - y := 2 * (x := a+b); -\end{verbatim} -sets {\tt X} to {\tt a+b} and {\tt Y} to {\tt 2*(a+b)}. - -The sections on the various proper statement\index{Proper statement} types -indicate which of these statements are also useful as expressions. - -\chapter{Lists} - -A list\index{List} is an object consisting of a sequence of other objects -(including lists themselves), separated by commas and surrounded by -braces. Examples of lists are: -\begin{verbatim} - {a,b,c} - - {1,a-b,c=d} - - {{a},{{b,c},d},e}. -\end{verbatim} -The empty list is represented as -\begin{verbatim} - {}. -\end{verbatim} - -\section{Operations on Lists}\index{List operation} - -Several operators in the system return their results as lists, and a user -can create new lists using braces and commas. To facilitate the use of -such lists, a number of operators are also available for manipulating -them. {\tt PART(,n)}\ttindex{PART} for example will return the -$n^{th}$ element of a list. {\tt LENGTH}\ttindex{LENGTH} will return the -length of a list. Several operators are also defined uniquely for lists. -For those familiar with them, these operators in fact mirror the -operations defined for Lisp lists. These operators are as follows: - -\subsection{FIRST} - -This operator\ttindex{FIRST} returns the first member of a list. An error -occurs if the argument is not a list, or the list is empty. - -\subsection{SECOND} - -{\tt SECOND}\ttindex{SECOND} returns the second member of a list. An error -occurs if the argument is not a list or has no second element. - -\subsection{THIRD} - -This operator\ttindex{THIRD} returns the third member of a list. An error -occurs if the argument is not a list or has no third element. - -\subsection{REST} - -{\tt REST}\ttindex{REST} returns its argument with the first element -removed. An error occurs if the argument is not a list, or is empty. - -\subsection{$.$ (Cons) Operator} - -This operator\ttindex{. (CONS)} adds (``conses'') an expression to the -front of a list. For example: -\begin{verbatim} - a . {b,c} -> {a,b,c}. -\end{verbatim} - -\subsection{APPEND} - -This operator\ttindex{APPEND} appends its first argument to its second to -form a new list. -{\it Examples:} -\begin{verbatim} - append({a,b},{c,d}) -> {a,b,c,d} - append({{a,b}},{c,d}) -> {{a,b},c,d}. -\end{verbatim} - -\subsection{REVERSE} - -The operator {\tt REVERSE}\ttindex{REVERSE} returns its argument with the -elements in the reverse order. It only applies to the top level list, not -any lower level lists that may occur. Examples are:\index{List operation} -\begin{verbatim} - reverse({a,b,c}) -> {c,b,a} - reverse({{a,b,c},d}) -> {d,{a,b,c}}. -\end{verbatim} - -\subsection{List Arguments of Other Operators} - -If an operator other than those specifically defined for lists is given a -single argument that is a list, then the result of this operation will be -a list in which that operator is applied to each element of the list. For -example, the result of evaluating {\tt log\{a,b,c\}} is the expression -{\tt \{LOG(A),LOG(B),LOG(C)\}}. - -There are two ways to inhibit this operator distribution. Firstly, the -switch {\tt LISTARGS},\ttindex{LISTARGS} if on, will globally inhibit -such distribution. Secondly, one can inhibit this distribution for a -specific operator by the declaration {\tt LISTARGP}.\ttindex{LISTARGP} For -example, with the declaration {\tt listargp log}, {\tt log\{a,b,c\}} would -evaluate to {\tt LOG(\{A,B,C\})}. - -If an operator has more than one argument, no such distribution occurs. - -\chapter{Statements} - -A statement\index{Statement} is any combination of reserved words and -expressions, and has the syntax \index{Proper statement} -\begin{verbatim} - ::= | -\end{verbatim} -A {\REDUCE} program consists of a series of commands which are statements -followed by a terminator:\index{Terminator}\index{Semicolon} -\index{Dollar sign} -\begin{verbatim} - ::= ;|$ -\end{verbatim} -The division of the program into lines is arbitrary. Several statements -can be on one line, or one statement can be freely broken onto several -lines. If the program is run interactively, statements ending with ; or \$ -are not processed until an end-of-line character is encountered. This -character can vary from system to system, but is normally the \key{Return} -key on an ASCII terminal. Specific systems may also use additional keys -as statement terminators. - -If a statement is a proper statement\index{Proper statement}, the -appropriate action takes place. - -Depending on the nature of the proper statement some result or response may -or may not be printed out, and the response may or may not depend on the -terminator used. - -If a statement is an expression, it is evaluated. If the terminator is a -semicolon, the result is printed. If the terminator is a dollar sign, the -result is not printed. Because it is not usually possible to know in -advance how large an expression will be, no explicit format statements are -offered to the user. However, a variety of output declarations are -available so that the output can be produced in different forms. These -output declarations are explained in Section~\ref{sec-output}. - -The following sub-sections describe the types of proper statements -\index{Proper statement} in {\REDUCE}. - -\section{Assignment Statements} - -These statements\index{Assignment} have the syntax -\begin{verbatim} - ::= := -\end{verbatim} -The {\tt } on the left side is normally the name of a variable, an -operator symbol with its list of arguments filled in, or an array name with -the proper number of integer subscript values within the array bounds. For -example: -\begin{quote} -\begin{tabbing} -{\tt a1 := b + c} \\ -{\tt h(l,m) := x-2*y} \hspace{1in} \= (where {\tt h} is an operator) \\ -{\tt k(3,5) := x-2*y} \> (where {\tt k} is a 2-dim. array) -\end{tabbing} -\end{quote} -More general assignments\index{Assignment} such as {\tt a+b := c} are also -allowed. The effect of these is explained in Section~\ref{sec-gensubs}. - -An assignment statement causes the expression on the right-hand-side to be -evaluated. If the left-hand-side is a variable, the value of the -right-hand-side is assigned to that unevaluated variable. If the -left-hand-side is an operator or array expression, the arguments of that -operator or array are evaluated, but no other simplification done. The -evaluated right-hand-side is then assigned to the resulting expression. -For example, if {\tt A} is a single-dimensional array, {\tt a(1+1) := b} -assigns the value {\tt B} to the array element {\tt a(2)}. - -If a semicolon is used as the terminator when an assignment -\index{Assignment} is issued as a command (i.e. not as a part of a group -statement or procedure or other similar construct), the left-hand side -symbol of the assignment statement is printed out, followed by a -``{\tt :=}'', followed by the value of the expression on the right. - -It is also possible to write a multiple assignment statement: -\index{Multiple assignment statement} -\begin{verbatim} - := ... := := -\end{verbatim} -In this form, each {\tt } but the last is set to the value of -the last {\tt }. If a semicolon is used as a terminator, each -expression except the last is printed followed by a ``{\tt :=}'' ending -with the value of the last expression. - - -\subsection{Set Statement} - -In some cases, it is desirable to perform an assignment in which {\em both\/} -the left- and right-hand sides of an assignment\index{Assignment} are -evaluated. In this case, the {\tt SET}\ttindex{SET} statement can be used -with the syntax: - -\begin{verbatim} - SET(,); -\end{verbatim} -For example, the statements -\begin{verbatim} - j := 23; - set(mkid(a,j),x); -\end{verbatim} -assigns the value {\tt X} to {\tt A23}. - -\section{Group Statements} - -The group statement\index{Group statement} is a construct used where -{\REDUCE} expects a single statement, but a series of actions needs to be -performed. It is formed by enclosing one or more statements (of any kind) -between the symbols {\tt $<<$} and {\tt $>>$}, separated by semicolons or -dollar signs -- it doesn't matter which. The statements are executed one -after another. - -Examples will be given in the sections on {\tt IF}\ttindex{IF} and other -types of statements in which the {\tt $<<$} \ldots {\tt $>>$} construct is -useful. - -If the last statement in the enclosed group has a value, then that is also -the value of the group statement. Care must be taken not to have a -semicolon or dollar sign after the last grouped statement, if the value of -the group is relevant: such an extra terminator causes the group to have -the value NIL or zero. - -\section{Conditional Statements} - -The conditional statement\index{Conditional statement} has the following -syntax: - -\begin{verbatim} - ::= - IF THEN [ELSE ] -\end{verbatim} - -The boolean expression is evaluated. If this is {\em true}, the first -{\tt } is executed. If it is {\em false}, the second is. - -{\it Examples:} -\begin{verbatim} - if x=5 then a:=b+c else d:=e+f - - if x=5 and numberp y - then <> - else <> -\end{verbatim} -Note the use of the group statement\index{Group statement}. -\\ -Conditional statements associate to the right; i.e.,\ttindex{IF} -\begin{verbatim} - IF THEN ELSE IF THEN ELSE -\end{verbatim} -is equivalent to: -\begin{verbatim} - IF THEN ELSE (IF THEN ELSE ) -\end{verbatim} -In addition, the construction -\begin{verbatim} - IF THEN IF THEN ELSE -\end{verbatim} -parses as -\begin{verbatim} - IF THEN (IF THEN ELSE ). -\end{verbatim} -If the value of the conditional statement\index{Conditional -statement} is of primary interest, it is often called a conditional -expression instead. Its value is the value of whichever statement was -executed. (If the executed statement has no value, the conditional -expression has no value or the value 0, depending on how it is used.) - -{\it Examples:} -\begin{verbatim} - a:=if x<5 then 123 else 456; - b:=u + v^(if numberp z then 10*z else 1) + w; -\end{verbatim} -If the value is of no concern, the {\tt ELSE} clause may be omitted if no -action is required in the {\em false\/} case. -\begin{verbatim} - if x=5 then a:=b+c; -\end{verbatim} -Note: As explained in Section~\ref{sec-boolean},a -if a scalar or numerical expression is used in place of -the boolean expression -- for example, a variable is written there -- the -{\em true\/} alternative is followed unless the expression has the value 0. - -\section{FOR Statements} - -The {\tt FOR} statement is used to define a variety of program -loops\index{Loop}. Its general syntax is as follows:\ttindex{UNTIL} -\ttindex{DO}\ttindex{PRODUCT}\ttindex{SUM}\ttindex{COLLECT}\ttindex{JOIN} -\begin{small} -\[ \mbox{\tt FOR} \left\{ \begin{array}{@{}ccc@{}} - \mbox{\tt \meta{var} := \meta{number} } \left\{ \begin{array}{@{}c@{}} - \mbox{\tt STEP \meta{number} UNTIL} \\ - \mbox{\tt :} - \end{array} - \right\} \mbox{\tt \meta{number}} \\[3mm] - \multicolumn{1}{c}{\mbox{\tt EACH \meta{var} - \(\left\{ - \begin{tabular}{@{}c@{}} - IN \\ ON - \end{tabular} - \right\}\) - \meta{list}}} - \end{array} - \right\} \mbox{\tt \meta{action} \meta{exprn}} \] -\end{small}% -% -where -\begin{center} -\tt \meta{action} ::= do|product|sum|collect|join. -\end{center} -The assignment\index{Assignment} form of the {\tt FOR} statement defines an -iteration over the indicated numerical range. If expressions that do not -evaluate to numbers are used in the designated places, an error will -result. - -The {\tt FOR EACH}\ttindex{FOR EACH} form of the {\tt FOR} statement is -designed to iterate down a list. Again, an error will occur if a list is -not used. - -The action {\tt DO}\ttindex{DO} means that {\tt } is simply -evaluated and no value kept; the statement returning 0 in this case (or no -value at the top level). {\tt COLLECT} means that the results of -evaluating {\tt } each time are linked together to make a list, -and {\tt JOIN} means that the values of {\tt } are themselves -lists that are joined to make one list (similar to {\tt CONC} in Lisp). -Finally, {\tt PRODUCT}\ttindex{PRODUCT} and {\tt SUM}\ttindex{SUM} -form the respective combined value out of the values of {\tt }. - -In all cases, {\tt } is evaluated algebraically within the -scope of the current value of {\tt }. If {\tt } is -{\tt DO}\ttindex{DO}, then nothing else happens. In other cases, {\tt -} is a binary operator that causes a result to be built up and -returned by {\tt FOR}. In those cases, the loop\index{Loop} is -initialized to a default value ({\tt 0} for {\tt SUM},\ttindex{SUM} {\tt -1} for {\tt PRODUCT},\ttindex{PRODUCT} and an empty list for the other -actions). The test for the end condition is made before any action is -taken. As in Pascal, if the variable is out of range in the assignment -case, or the {\tt } is empty in the {\tt FOR EACH}\ttindex{FOR EACH} -case, {\tt } is not evaluated at all. - -{\it Examples:} -\begin{enumerate} -\item If {\tt A}, {\tt B} have been declared to be arrays, the following -stores $5^{2}$ through $10^{2}$ in {\tt A(5)} through {\tt A(10)}, and at -the same time stores the cubes in the {\tt B} array: -\begin{verbatim} - for i := 5 step 1 until 10 do <> -\end{verbatim} -\item As a convenience, the common construction -\begin{verbatim} - STEP 1 UNTIL -\end{verbatim} -may be abbreviated to a colon. Thus, instead of the above we could write: -\begin{verbatim} - for i := 5:10 do <> -\end{verbatim} -\item The following sets {\tt C} to the sum of the squares of 1,3,5,7,9; -and {\tt D} to the expression {\tt x*(x+1)*(x+2)*(x+3)*(x+4):} -\begin{verbatim} - c := for j:=1 step 2 until 9 sum j^2; - d := for k:=0 step 1 until 4 product (x+k); -\end{verbatim} -\item The following forms a list of the squares of the elements of the list -{\tt \{a,b,c\}:}\ttindex{FOR EACH} -\begin{verbatim} - for each x in {a,b,c} collect x^2; -\end{verbatim} -\item The following forms a list of the listed squares of the elements of the -list {\tt \{a,b,c\}} -(i.e., {\tt \{\{A\verb|^|2\},\{B\verb|^|2\},\{C\verb|^|2\}\}):} -\begin{verbatim} - for each x in {a,b,c} collect {x^2}; -\end{verbatim} -\item The following also forms a list of the squares of the elements of -the list {\tt \{a,b,c\},} since the {\tt JOIN} operation joins the -individual lists into one list:\ttindex{FOR EACH} -\begin{verbatim} - for each x in {a,b,c} join {x^2}; -\end{verbatim} -\end{enumerate} -The control variable used in the {\tt FOR} statement is actually a new -variable, not related to the variable of the same name outside the {\tt -FOR} statement. In other words, executing a statement {\tt for i:=} \ldots -doesn't change the system's assumption that $i^{2} = -1$. -Furthermore, in algebraic mode, the value of the control variable is -substituted in {\tt } only if it occurs explicitly in that -expression. It will not replace a variable of the same name in the value -of that expression. For example: -\begin{verbatim} - b := a; for a := 1:2 do write b; -\end{verbatim} -prints {\tt A} twice, not 1 followed by 2. - -\section{WHILE \ldots DO} - -The\ttindex{WHILE} {\tt FOR \ldots DO}\ttindex{DO} feature allows easy -coding of a repeated operation in which the number of repetitions is known -in advance. If the criterion for repetition is more complicated, {\tt -WHILE \ldots DO} can often be used. Its syntax is: -\begin{verbatim} - WHILE DO -\end{verbatim} -The {\tt WHILE \ldots DO} controls the single statement following {\tt DO}. -If several statements are to be repeated, as is almost always the case, -they must be grouped using the $<<$ \ldots $>>$ or {\tt BEGIN \ldots END} -as in the example below. - -The {\tt WHILE} condition is tested each time {\em before\/} the action -following the {\tt DO} is attempted. If the condition is false to begin -with, the action is not performed at all. Make sure that what is to be -tested has an appropriate value initially. - -{\it Example:} - -Suppose we want to add up a series of terms, generated one by one, until -we reach a term which is less than 1/1000 in value. For our simple -example, let us suppose the first term equals 1 and each term is obtained -from the one before by taking one third of it and adding one third its -square. We would write: -\begin{verbatim} - ex:=0; term:=1; - while num(term - 1/1000) >= 0 do - <>; - ex; -\end{verbatim} -As long as {\tt TERM} is greater than or equal to ({\tt >=}) 1/1000 it will -be added to {\tt EX} and the next {\tt TERM} calculated. As soon as {\tt -TERM} becomes less than 1/1000 the {\tt WHILE} test fails and the {\tt -TERM} will not be added. - - -\section{REPEAT \ldots UNTIL} - -\ttindex{REPEAT} {\tt REPEAT \ldots UNTIL} is very similar in purpose to -{\tt WHILE \ldots DO}. Its syntax is: -\begin{verbatim} - REPEAT UNTIL -\end{verbatim} -(PASCAL users note: Only a single statement -- usually a group statement --- is allowed between the {\tt REPEAT} and the {\tt UNTIL.)} - -There are two essential differences: -\begin{enumerate} -\item The test is performed {\em after\/} the controlled statement (or group of -statements) is executed, so the controlled statement is always executed at -least once. - -\item The test is a test for when to stop rather than when to continue, so its -``polarity'' is the opposite of that in {\tt WHILE \ldots DO.} -\end{enumerate} - -As an example, we rewrite the example from the {\tt WHILE \ldots DO} section: -\begin{samepage} -\begin{verbatim} - ex:=0; term:=1; - repeat <> - until num(term - 1/1000) < 0; - ex; -\end{verbatim} -\end{samepage} -In this case, the answer will be the same as before, because in neither -case is a term added to {\tt EX} which is less than 1/1000. - -\section{Compound Statements} - -\index{Compound statement}Often the desired process can best (or only) be -described as a series of steps to be carried out one after the other. In -many cases, this can be achieved by use of the group statement\index{Group -statement}. However, each step often provides some intermediate -result, until at the end we have the final result wanted. Alternatively, -iterations on the steps are needed that are not possible with constructs -such as {\tt WHILE}\ttindex{WHILE} or {\tt REPEAT}\ttindex{REPEAT} -statements. In such cases the steps of the process must be -enclosed between the words {\tt BEGIN} and {\tt END}\ttindex{BEGIN \ldots -END} forming what is technically called a {\em block\/}\index{Block} or -{\em compound\/} statement. Such a compound statement can in fact be used -wherever a group statement appears. The converse is not true: {\tt BEGIN -\ldots END} can be used in ways that {\tt $<<$} \ldots {\tt $>>$} cannot. - -If intermediate results must be formed, local variables must be provided -in which to store them. {\em Local\/} means that their values are deleted as -soon as the block's operations are complete, and there is no conflict with -variables outside the block that happen to have the same name. Local -variables are created by a {\tt SCALAR}\ttindex{SCALAR} declaration -immediately after the {\tt BEGIN}: -\begin{verbatim} - scalar a,b,c,z; -\end{verbatim} -If more convenient, several {\tt SCALAR} declarations can be given one after -another: -\begin{verbatim} - scalar a,b,c; - scalar z; -\end{verbatim} -In place of {\tt SCALAR} one can also use the declarations -{\tt INTEGER}\ttindex{INTEGER} or {\tt REAL}\ttindex{REAL}. In the present -version of {\REDUCE} variables declared {\tt INTEGER} are expected to have -only integer values, and are initialized to 0. {\tt REAL} -variables on the other hand are currently treated as algebraic mode {\tt -SCALAR}s. - -{\it CAUTION:} {\tt INTEGER}, {\tt REAL} and {\tt SCALAR} declarations can -only be given immediately after a {\tt BEGIN}. An error will result if -they are used after other statements in a block (including {\tt ARRAY} and -{\tt OPERATOR} declarations, which are global in scope), or outside the -top-most block (e.g., at the top level). All variables declared {\tt -SCALAR} are automatically initialized to zero in algebraic mode ({\tt NIL} -in symbolic mode). - -Any symbols not declared as local variables in a block refer to the -variables of the same name in the current calling environment. In -particular, if they are not so declared at a higher level (e.g., in a -surrounding block or as parameters in a calling procedure), their values can -be permanently changed. - -Following the {\tt SCALAR}\ttindex{SCALAR} declaration(s), if any, write the -statements to be executed, one after the other, separated by delimiters -(e.g., {\tt ;} or {\tt \$}) (it doesn't matter which). However, from a -stylistic point of view, {\tt ;} is preferred. - -The last statement in the body, just before {\tt END}, need not have a -terminator (since the {\tt BEGIN \ldots END} are in a sense brackets -confining the block statements). The last statement must also be the -command {\tt RETURN}\ttindex{RETURN} followed by the variable or -expression whose value is to be the value returned by the procedure. If -the {\tt RETURN} is omitted (or nothing is written after the word -{\tt RETURN}) the procedure will have no value or the value zero, depending -on how it is used (and {\tt NIL} in symbolic mode). Remember to put a -terminator after the {\tt END}. - -{\it Example:} - -Given a previously assigned integer value for {\tt N}, the following block -will compute the Legendre polynomial of degree {\tt N} in the variable -{\tt X}: -\begin{verbatim} - begin scalar seed,deriv,top,fact; - seed:=1/(y^2 - 2*x*y +1)^(1/2); - deriv:=df(seed,y,n); - top:=sub(y=0,deriv); - fact:=for i:=1:n product i; - return top/fact - end; -\end{verbatim} - -\subsection{Compound Statements with GO TO} - -It is possible to have more complicated structures inside the {\tt BEGIN -\ldots END}\ttindex{BEGIN \ldots END} brackets than indicated in the -previous example. That the individual lines of the program need not be -assignment\index{Assignment} statements, but could be almost any other -kind of statement or command, needs no explanation. For example, -conditional statements, and {\tt WHILE}\ttindex{WHILE} and {\tt REPEAT} -\ttindex{REPEAT} constructions, have an obvious role in defining more -intricate blocks. - -If these structured constructs don't suffice, it is possible to use labels -\index{Label} and {\tt GO} {\tt TO}s\ttindex{GO TO} within a compound -statement,\index{Compound statement} and also to use {\tt RETURN} -\ttindex{RETURN} in places within the block other than just before the -{\tt END}. The following subsections discuss these matters in detail. -For many readers the following example, presenting one possible definition -of a process to calculate the factorial of {\tt N} for preassigned {\tt N} -will suffice: - -{\it Example:} -\begin{verbatim} - begin scalar m; - m:=1; - l: if n=0 then return m; - m:=m*n; - n:=n-1; - go to l - end; -\end{verbatim} - -\subsection{Labels and GO TO Statements} - -\index{Label}\ttindex{GO TO}Within a {\tt BEGIN \ldots END} compound -statement it is possible to label statements, and transfer to them out of -sequence using {\tt GO} {\tt TO} statements. Only statements on the top -level inside compound statements can be labeled, not ones inside -subsidiary constructions like {\tt $<<$} \ldots {\tt $>>$}, {\tt IF} \ldots -{\tt THEN} \ldots , {\tt WHILE} \ldots {\tt DO} \ldots , etc. - -Labels and {\tt GO TO} statements have the syntax: -\begin{verbatim} - ::= GO TO THEN ELSE IF THEN ELSE +\end{verbatim} +is equivalent to: +\begin{verbatim} + IF THEN ELSE (IF THEN ELSE ) +\end{verbatim} +In addition, the construction +\begin{verbatim} + IF THEN IF THEN ELSE +\end{verbatim} +parses as +\begin{verbatim} + IF THEN (IF THEN ELSE ). +\end{verbatim} +If the value of the conditional statement\index{Conditional +statement} is of primary interest, it is often called a conditional +expression instead. Its value is the value of whichever statement was +executed. (If the executed statement has no value, the conditional +expression has no value or the value 0, depending on how it is used.) + +{\it Examples:} +\begin{verbatim} + a:=if x<5 then 123 else 456; + b:=u + v^(if numberp z then 10*z else 1) + w; +\end{verbatim} +If the value is of no concern, the {\tt ELSE} clause may be omitted if no +action is required in the {\em false\/} case. +\begin{verbatim} + if x=5 then a:=b+c; +\end{verbatim} +Note: As explained in Section~\ref{sec-boolean},a +if a scalar or numerical expression is used in place of +the boolean expression -- for example, a variable is written there -- the +{\em true\/} alternative is followed unless the expression has the value 0. + +\section{FOR Statements} + +The {\tt FOR} statement is used to define a variety of program +loops\index{Loop}. Its general syntax is as follows:\ttindex{UNTIL} +\ttindex{DO}\ttindex{PRODUCT}\ttindex{SUM}\ttindex{COLLECT}\ttindex{JOIN} +\begin{small} +\[ \mbox{\tt FOR} \left\{ \begin{array}{@{}ccc@{}} + \mbox{\tt \meta{var} := \meta{number} } \left\{ \begin{array}{@{}c@{}} + \mbox{\tt STEP \meta{number} UNTIL} \\ + \mbox{\tt :} + \end{array} + \right\} \mbox{\tt \meta{number}} \\[3mm] + \multicolumn{1}{c}{\mbox{\tt EACH \meta{var} + \(\left\{ + \begin{tabular}{@{}c@{}} + IN \\ ON + \end{tabular} + \right\}\) + \meta{list}}} + \end{array} + \right\} \mbox{\tt \meta{action} \meta{exprn}} \] +\end{small}% +% +where +\begin{center} +\tt \meta{action} ::= do|product|sum|collect|join. +\end{center} +The assignment\index{Assignment} form of the {\tt FOR} statement defines an +iteration over the indicated numerical range. If expressions that do not +evaluate to numbers are used in the designated places, an error will +result. + +The {\tt FOR EACH}\ttindex{FOR EACH} form of the {\tt FOR} statement is +designed to iterate down a list. Again, an error will occur if a list is +not used. + +The action {\tt DO}\ttindex{DO} means that {\tt } is simply +evaluated and no value kept; the statement returning 0 in this case (or no +value at the top level). {\tt COLLECT} means that the results of +evaluating {\tt } each time are linked together to make a list, +and {\tt JOIN} means that the values of {\tt } are themselves +lists that are joined to make one list (similar to {\tt CONC} in Lisp). +Finally, {\tt PRODUCT}\ttindex{PRODUCT} and {\tt SUM}\ttindex{SUM} +form the respective combined value out of the values of {\tt }. + +In all cases, {\tt } is evaluated algebraically within the +scope of the current value of {\tt }. If {\tt } is +{\tt DO}\ttindex{DO}, then nothing else happens. In other cases, {\tt +} is a binary operator that causes a result to be built up and +returned by {\tt FOR}. In those cases, the loop\index{Loop} is +initialized to a default value ({\tt 0} for {\tt SUM},\ttindex{SUM} {\tt +1} for {\tt PRODUCT},\ttindex{PRODUCT} and an empty list for the other +actions). The test for the end condition is made before any action is +taken. As in Pascal, if the variable is out of range in the assignment +case, or the {\tt } is empty in the {\tt FOR EACH}\ttindex{FOR EACH} +case, {\tt } is not evaluated at all. + +{\it Examples:} +\begin{enumerate} +\item If {\tt A}, {\tt B} have been declared to be arrays, the following +stores $5^{2}$ through $10^{2}$ in {\tt A(5)} through {\tt A(10)}, and at +the same time stores the cubes in the {\tt B} array: +\begin{verbatim} + for i := 5 step 1 until 10 do <> +\end{verbatim} +\item As a convenience, the common construction +\begin{verbatim} + STEP 1 UNTIL +\end{verbatim} +may be abbreviated to a colon. Thus, instead of the above we could write: +\begin{verbatim} + for i := 5:10 do <> +\end{verbatim} +\item The following sets {\tt C} to the sum of the squares of 1,3,5,7,9; +and {\tt D} to the expression {\tt x*(x+1)*(x+2)*(x+3)*(x+4):} +\begin{verbatim} + c := for j:=1 step 2 until 9 sum j^2; + d := for k:=0 step 1 until 4 product (x+k); +\end{verbatim} +\item The following forms a list of the squares of the elements of the list +{\tt \{a,b,c\}:}\ttindex{FOR EACH} +\begin{verbatim} + for each x in {a,b,c} collect x^2; +\end{verbatim} +\item The following forms a list of the listed squares of the elements of the +list {\tt \{a,b,c\}} +(i.e., {\tt \{\{A\verb|^|2\},\{B\verb|^|2\},\{C\verb|^|2\}\}):} +\begin{verbatim} + for each x in {a,b,c} collect {x^2}; +\end{verbatim} +\item The following also forms a list of the squares of the elements of +the list {\tt \{a,b,c\},} since the {\tt JOIN} operation joins the +individual lists into one list:\ttindex{FOR EACH} +\begin{verbatim} + for each x in {a,b,c} join {x^2}; +\end{verbatim} +\end{enumerate} +The control variable used in the {\tt FOR} statement is actually a new +variable, not related to the variable of the same name outside the {\tt +FOR} statement. In other words, executing a statement {\tt for i:=} \ldots +doesn't change the system's assumption that $i^{2} = -1$. +Furthermore, in algebraic mode, the value of the control variable is +substituted in {\tt } only if it occurs explicitly in that +expression. It will not replace a variable of the same name in the value +of that expression. For example: +\begin{verbatim} + b := a; for a := 1:2 do write b; +\end{verbatim} +prints {\tt A} twice, not 1 followed by 2. + +\section{WHILE \ldots DO} + +The\ttindex{WHILE} {\tt FOR \ldots DO}\ttindex{DO} feature allows easy +coding of a repeated operation in which the number of repetitions is known +in advance. If the criterion for repetition is more complicated, {\tt +WHILE \ldots DO} can often be used. Its syntax is: +\begin{verbatim} + WHILE DO +\end{verbatim} +The {\tt WHILE \ldots DO} controls the single statement following {\tt DO}. +If several statements are to be repeated, as is almost always the case, +they must be grouped using the $<<$ \ldots $>>$ or {\tt BEGIN \ldots END} +as in the example below. + +The {\tt WHILE} condition is tested each time {\em before\/} the action +following the {\tt DO} is attempted. If the condition is false to begin +with, the action is not performed at all. Make sure that what is to be +tested has an appropriate value initially. + +{\it Example:} + +Suppose we want to add up a series of terms, generated one by one, until +we reach a term which is less than 1/1000 in value. For our simple +example, let us suppose the first term equals 1 and each term is obtained +from the one before by taking one third of it and adding one third its +square. We would write: +\begin{verbatim} + ex:=0; term:=1; + while num(term - 1/1000) >= 0 do + <>; + ex; +\end{verbatim} +As long as {\tt TERM} is greater than or equal to ({\tt >=}) 1/1000 it will +be added to {\tt EX} and the next {\tt TERM} calculated. As soon as {\tt +TERM} becomes less than 1/1000 the {\tt WHILE} test fails and the {\tt +TERM} will not be added. + + +\section{REPEAT \ldots UNTIL} + +\ttindex{REPEAT} {\tt REPEAT \ldots UNTIL} is very similar in purpose to +{\tt WHILE \ldots DO}. Its syntax is: +\begin{verbatim} + REPEAT UNTIL +\end{verbatim} +(PASCAL users note: Only a single statement -- usually a group statement +-- is allowed between the {\tt REPEAT} and the {\tt UNTIL.)} + +There are two essential differences: +\begin{enumerate} +\item The test is performed {\em after\/} the controlled statement (or group of +statements) is executed, so the controlled statement is always executed at +least once. + +\item The test is a test for when to stop rather than when to continue, so its +``polarity'' is the opposite of that in {\tt WHILE \ldots DO.} +\end{enumerate} + +As an example, we rewrite the example from the {\tt WHILE \ldots DO} section: +\begin{samepage} +\begin{verbatim} + ex:=0; term:=1; + repeat <> + until num(term - 1/1000) < 0; + ex; +\end{verbatim} +\end{samepage} +In this case, the answer will be the same as before, because in neither +case is a term added to {\tt EX} which is less than 1/1000. + +\section{Compound Statements} + +\index{Compound statement}Often the desired process can best (or only) be +described as a series of steps to be carried out one after the other. In +many cases, this can be achieved by use of the group statement\index{Group +statement}. However, each step often provides some intermediate +result, until at the end we have the final result wanted. Alternatively, +iterations on the steps are needed that are not possible with constructs +such as {\tt WHILE}\ttindex{WHILE} or {\tt REPEAT}\ttindex{REPEAT} +statements. In such cases the steps of the process must be +enclosed between the words {\tt BEGIN} and {\tt END}\ttindex{BEGIN \ldots +END} forming what is technically called a {\em block\/}\index{Block} or +{\em compound\/} statement. Such a compound statement can in fact be used +wherever a group statement appears. The converse is not true: {\tt BEGIN +\ldots END} can be used in ways that {\tt $<<$} \ldots {\tt $>>$} cannot. + +If intermediate results must be formed, local variables must be provided +in which to store them. {\em Local\/} means that their values are deleted as +soon as the block's operations are complete, and there is no conflict with +variables outside the block that happen to have the same name. Local +variables are created by a {\tt SCALAR}\ttindex{SCALAR} declaration +immediately after the {\tt BEGIN}: +\begin{verbatim} + scalar a,b,c,z; +\end{verbatim} +If more convenient, several {\tt SCALAR} declarations can be given one after +another: +\begin{verbatim} + scalar a,b,c; + scalar z; +\end{verbatim} +In place of {\tt SCALAR} one can also use the declarations +{\tt INTEGER}\ttindex{INTEGER} or {\tt REAL}\ttindex{REAL}. In the present +version of {\REDUCE} variables declared {\tt INTEGER} are expected to have +only integer values, and are initialized to 0. {\tt REAL} +variables on the other hand are currently treated as algebraic mode {\tt +SCALAR}s. + +{\it CAUTION:} {\tt INTEGER}, {\tt REAL} and {\tt SCALAR} declarations can +only be given immediately after a {\tt BEGIN}. An error will result if +they are used after other statements in a block (including {\tt ARRAY} and +{\tt OPERATOR} declarations, which are global in scope), or outside the +top-most block (e.g., at the top level). All variables declared {\tt +SCALAR} are automatically initialized to zero in algebraic mode ({\tt NIL} +in symbolic mode). + +Any symbols not declared as local variables in a block refer to the +variables of the same name in the current calling environment. In +particular, if they are not so declared at a higher level (e.g., in a +surrounding block or as parameters in a calling procedure), their values can +be permanently changed. + +Following the {\tt SCALAR}\ttindex{SCALAR} declaration(s), if any, write the +statements to be executed, one after the other, separated by delimiters +(e.g., {\tt ;} or {\tt \$}) (it doesn't matter which). However, from a +stylistic point of view, {\tt ;} is preferred. + +The last statement in the body, just before {\tt END}, need not have a +terminator (since the {\tt BEGIN \ldots END} are in a sense brackets +confining the block statements). The last statement must also be the +command {\tt RETURN}\ttindex{RETURN} followed by the variable or +expression whose value is to be the value returned by the procedure. If +the {\tt RETURN} is omitted (or nothing is written after the word +{\tt RETURN}) the procedure will have no value or the value zero, depending +on how it is used (and {\tt NIL} in symbolic mode). Remember to put a +terminator after the {\tt END}. + +{\it Example:} + +Given a previously assigned integer value for {\tt N}, the following block +will compute the Legendre polynomial of degree {\tt N} in the variable +{\tt X}: +\begin{verbatim} + begin scalar seed,deriv,top,fact; + seed:=1/(y^2 - 2*x*y +1)^(1/2); + deriv:=df(seed,y,n); + top:=sub(y=0,deriv); + fact:=for i:=1:n product i; + return top/fact + end; +\end{verbatim} + +\subsection{Compound Statements with GO TO} + +It is possible to have more complicated structures inside the {\tt BEGIN +\ldots END}\ttindex{BEGIN \ldots END} brackets than indicated in the +previous example. That the individual lines of the program need not be +assignment\index{Assignment} statements, but could be almost any other +kind of statement or command, needs no explanation. For example, +conditional statements, and {\tt WHILE}\ttindex{WHILE} and {\tt REPEAT} +\ttindex{REPEAT} constructions, have an obvious role in defining more +intricate blocks. + +If these structured constructs don't suffice, it is possible to use labels +\index{Label} and {\tt GO} {\tt TO}s\ttindex{GO TO} within a compound +statement,\index{Compound statement} and also to use {\tt RETURN} +\ttindex{RETURN} in places within the block other than just before the +{\tt END}. The following subsections discuss these matters in detail. +For many readers the following example, presenting one possible definition +of a process to calculate the factorial of {\tt N} for preassigned {\tt N} +will suffice: + +{\it Example:} +\begin{verbatim} + begin scalar m; + m:=1; + l: if n=0 then return m; + m:=m*n; + n:=n-1; + go to l + end; +\end{verbatim} + +\subsection{Labels and GO TO Statements} + +\index{Label}\ttindex{GO TO}Within a {\tt BEGIN \ldots END} compound +statement it is possible to label statements, and transfer to them out of +sequence using {\tt GO} {\tt TO} statements. Only statements on the top +level inside compound statements can be labeled, not ones inside +subsidiary constructions like {\tt $<<$} \ldots {\tt $>>$}, {\tt IF} \ldots +{\tt THEN} \ldots , {\tt WHILE} \ldots {\tt DO} \ldots , etc. + +Labels and {\tt GO TO} statements have the syntax: +\begin{verbatim} + ::= GO TO \redref.hlp - where is the path, - and then double click the yellow question mark. - -Mode (3) allows one to have the book as on line document available -independent of a reduce session. That is how Microsoft deliver deliver -their system documentation. - -Please have also a look at the index which I have built -partially automatically, partially by inserting lots of -\index statements. E.g. - push the Search button - and then enter - polynomial (or any other central item) - as search item. - -================================================================ - -When working on the material I first had started to keep track -of any modification, but I gave that up rather soon. - -I have modified several formats - latex accepts the object still, -bit I didn't look at the dvi output. 330 is too much for printing -anyway. - -General remarks regarding the information: - -In some places I have modified the REDUCE kernel material substantially. -I am sure that you will find better words for these points - I am happy -with *any* improvement. I ran spell on the data sets, but that does not -find bad grammar or wrong words. - -Substantial points are: - - SOLVE+its sub-operators and switches - ARBINT ARBCOMPLEX ROOT_OF ONE_OF EXPAND_CASES - FULLROOTS FULLPREC - - RULE (new type) - - LET, WHEN, WHERE - - EQUATION - - BLOCK - - TRUE - -====================================================== -some details: ---------------------------------------------------------- - -numeric.tex - -I don't like the heading of this chapter, as most of the -operators described here are more general than just -numeric. How about "Arithmetic Operators?" - ---------------------------------------------------------- -REMAINDER: - -remainder(sin(2*x),x*y); & SIN(2*X) -\end{Examples} - -\begin{Comments} -If the first argument to \name{remainder} is not a polynomial, an error -occurs. - -> Here the example and the comment contradict each other -> sin(2*x) is *not* a polynomial ->>>> not repaired (I have no idea what to write here) - --------------------------------------------------------- - -boolean.tex - - -I have introduced a node which explains the meaning -of "true". This also could be a member of a "glossary". - -The description of NOT - -\meta{logical expression} must evaluate to {\it true} or {\it nil}. - -is too restrictive. I have deleted this line. - ----------------------------------------------------------- - -command.tex - -not very important, but is WS a command? I would prefer -an operator because its main purpose is to deliver a value. - ----------------------------------------------------------- - -algebra.tex - -RESULTANT: please have a look at the TEX-parts: I think that -the 2nd polynomial should have a different degree (namely m -as in the INFO parts). - -SOLVE: You sell SOLVE below its facilities. According to the -original description the following examples would fail: - -8: solve({x+y=1,x+2y=2,2x+3y=3},{x,y}); - -{{x=0,y=1}} - -9: solve({x+y+z=1,x-y-z=1},{x,y,z}); - -{{x=1,y= - arbcomplex(4),z=arbcomplex(4)}} - -Fortunately they don't! I have commented these restrictions -in the description. - --------------------------------------------------------- - -switch.tex - -RATIONAL: - -The \nameref{factorize} command does not accept -polynomials with rational coefficients. - -> this is not true! I have commented this lines. - -SOLVESINGULAR: - -This switch seems to have no effect at all. At least the -example doesn't work. Is that a bug in solve or should -we remove this switch?? - -============================================================= - -matrix.tex - -Cofactor had a completely different syntax style - -============================================================= - -library.tex : upgraded from the current manual - -======== EOF =============================================== +Date: Fri, 5 Nov 93 16:15:43 +0100 +From: melenk@sc.ZIB-Berlin.DE (Herbert Melenk) +Subject: help milestone + +Finally I'm done with the help material. It took me much longer +as originally expected, but I think that the result justifies +the effort. Please pick up the following data sets: + +408064: /silo/herbert/redhelp/redref/helptar.Z these are the .tex files + +230217 /silo/herbert/redhelp/redref.hlp.Z the windows binary help file + +325179 /silo/herbert/redhelp/txt/txttar.Z the bare ascii documents + thanks to Rainer. + +If you want to have a look at the hypertext connections +as implemented in the windows help file: + +- uncompress under unix +- move the .hlp file to a DOS-Windows (or NT) machine +- do one of + (1) double click it with the windows file manager, + (2) (NT only) enter the command line + winhelp redref.hlp + (3) install an icon with title + REDUCE reference + and command line + winhelp \redref.hlp + where is the path, + and then double click the yellow question mark. + +Mode (3) allows one to have the book as on line document available +independent of a reduce session. That is how Microsoft deliver deliver +their system documentation. + +Please have also a look at the index which I have built +partially automatically, partially by inserting lots of +\index statements. E.g. + push the Search button + and then enter + polynomial (or any other central item) + as search item. + +================================================================ + +When working on the material I first had started to keep track +of any modification, but I gave that up rather soon. + +I have modified several formats - latex accepts the object still, +bit I didn't look at the dvi output. 330 is too much for printing +anyway. + +General remarks regarding the information: + +In some places I have modified the REDUCE kernel material substantially. +I am sure that you will find better words for these points - I am happy +with *any* improvement. I ran spell on the data sets, but that does not +find bad grammar or wrong words. + +Substantial points are: + + SOLVE+its sub-operators and switches + ARBINT ARBCOMPLEX ROOT_OF ONE_OF EXPAND_CASES + FULLROOTS FULLPREC + + RULE (new type) + + LET, WHEN, WHERE + + EQUATION + + BLOCK + + TRUE + +====================================================== +some details: +--------------------------------------------------------- + +numeric.tex + +I don't like the heading of this chapter, as most of the +operators described here are more general than just +numeric. How about "Arithmetic Operators?" + +--------------------------------------------------------- +REMAINDER: + +remainder(sin(2*x),x*y); & SIN(2*X) +\end{Examples} + +\begin{Comments} +If the first argument to \name{remainder} is not a polynomial, an error +occurs. + +> Here the example and the comment contradict each other +> sin(2*x) is *not* a polynomial +>>>> not repaired (I have no idea what to write here) + +-------------------------------------------------------- + +boolean.tex + + +I have introduced a node which explains the meaning +of "true". This also could be a member of a "glossary". + +The description of NOT + +\meta{logical expression} must evaluate to {\it true} or {\it nil}. + +is too restrictive. I have deleted this line. + +---------------------------------------------------------- + +command.tex + +not very important, but is WS a command? I would prefer +an operator because its main purpose is to deliver a value. + +---------------------------------------------------------- + +algebra.tex + +RESULTANT: please have a look at the TEX-parts: I think that +the 2nd polynomial should have a different degree (namely m +as in the INFO parts). + +SOLVE: You sell SOLVE below its facilities. According to the +original description the following examples would fail: + +8: solve({x+y=1,x+2y=2,2x+3y=3},{x,y}); + +{{x=0,y=1}} + +9: solve({x+y+z=1,x-y-z=1},{x,y,z}); + +{{x=1,y= - arbcomplex(4),z=arbcomplex(4)}} + +Fortunately they don't! I have commented these restrictions +in the description. + +-------------------------------------------------------- + +switch.tex + +RATIONAL: + +The \nameref{factorize} command does not accept +polynomials with rational coefficients. + +> this is not true! I have commented this lines. + +SOLVESINGULAR: + +This switch seems to have no effect at all. At least the +example doesn't work. Is that a bug in solve or should +we remove this switch?? + +============================================================= + +matrix.tex + +Cofactor had a completely different syntax style + +============================================================= + +library.tex : upgraded from the current manual + +======== EOF =============================================== Index: r36/help/HERBERT.REP ================================================================== --- r36/help/HERBERT.REP +++ r36/help/HERBERT.REP @@ -1,75 +1,75 @@ -To: melenk -cc: hearn -Subject: Help Materiall - -Herbert, many thanks for all your work. Below are some brief comments on -your message about this. - -I've updated my files as I've explained below. Should I send you a new -set? - -Thanks, -Tony - -------------------------------- - -> numeric.tex - -> I don't like the heading of this chapter, as most of the -> operators described here are more general than just -> numeric. How about "Arithmetic Operators?" - -Fine with me. I've renamed the file "arith.tex" too. - ---------------------------------------------------------- - -> REMAINDER: - -> remainder(sin(2*x),x*y); & SIN(2*X) -> If the first argument to \name{remainder} is not a polynomial, an error -> occurs. - -> Here the example and the comment contradict each other -> sin(2*x) is *not* a polynomial - -How about "is not a polynomial in its constituent kernels"? - ---------------------------------------------------------- - -> command.tex - -> not very important, but is WS a command? I would prefer -> an operator because its main purpose is to deliver a value. - -You're right. I've moved it to algebra.tex. - ----------------------------------------------------------- - -algebra.tex - -RESULTANT: please have a look at the TEX-parts: I think that -the 2nd polynomial should have a different degree (namely m -as in the INFO parts). - -It is wrong. However, -the index on "a" should be m (as per Buchberger, Collins and Loos). - ----------------------------------------------------------- - -switch.tex - -> SOLVESINGULAR: - -> This switch seems to have no effect at all. At least the -> example doesn't work. Is that a bug in solve or should -> we remove this switch?? - -This was a bug --- I hadn't considered this in the new solvelnr module. - ---------- - -Now a question from me: - -Should we move the single switch ADJPREC from "arith" -to "switch", or should we move some of the entries in -"switch" to other sections? +To: melenk +cc: hearn +Subject: Help Materiall + +Herbert, many thanks for all your work. Below are some brief comments on +your message about this. + +I've updated my files as I've explained below. Should I send you a new +set? + +Thanks, +Tony + +------------------------------- + +> numeric.tex + +> I don't like the heading of this chapter, as most of the +> operators described here are more general than just +> numeric. How about "Arithmetic Operators?" + +Fine with me. I've renamed the file "arith.tex" too. + +--------------------------------------------------------- + +> REMAINDER: + +> remainder(sin(2*x),x*y); & SIN(2*X) +> If the first argument to \name{remainder} is not a polynomial, an error +> occurs. + +> Here the example and the comment contradict each other +> sin(2*x) is *not* a polynomial + +How about "is not a polynomial in its constituent kernels"? + +--------------------------------------------------------- + +> command.tex + +> not very important, but is WS a command? I would prefer +> an operator because its main purpose is to deliver a value. + +You're right. I've moved it to algebra.tex. + +---------------------------------------------------------- + +algebra.tex + +RESULTANT: please have a look at the TEX-parts: I think that +the 2nd polynomial should have a different degree (namely m +as in the INFO parts). + +It is wrong. However, +the index on "a" should be m (as per Buchberger, Collins and Loos). + +---------------------------------------------------------- + +switch.tex + +> SOLVESINGULAR: + +> This switch seems to have no effect at all. At least the +> example doesn't work. Is that a bug in solve or should +> we remove this switch?? + +This was a bug --- I hadn't considered this in the new solvelnr module. + +--------- + +Now a question from me: + +Should we move the single switch ADJPREC from "arith" +to "switch", or should we move some of the entries in +"switch" to other sections? Index: r36/help/INTRO.TEX ================================================================== --- r36/help/INTRO.TEX +++ r36/help/INTRO.TEX @@ -1,81 +1,81 @@ -This manual describes the REDUCE symbolic mathematics system. REDUCE has -two modes of operation: the algebraic mode, which deals with polynomials -and mathematical functions in a simple procedural syntax, and the symbolic -mode, which allows Lisp-like syntax and operations. The commands, -declarations, switches and operators available in algebraic-mode REDUCE -are arranged in this manual in alphabetical order. Symbols are listed -before the letter A. - -Following the general alphabetical reference section is a similar -reference section for the High-Energy Physics operators. After that, you -can find several cross-reference sections. The first section contains -lists of reserved words and an Instant Function Cross-Reference. Next you -will find brief explanations of the common REDUCE error messages. The -next section is organized by type into Commands, Declarations, Operators, -Switches and Variables, with a brief listing for each operation. - -For a general introduction to using algebraic-mode REDUCE, see the {\em -REDUCE User's Guide}, which also contains information on symbolic mode. -The {\em The Standard Lisp Report} is a technical reference on REDUCE's -Lisp language. - -The following symbols are used to describe syntax in this manual: - -\begin{verbatim} -This font means you must type an item exactly as you see it. -\end{verbatim} - -{\em This font indicates a descriptive name for a type of REDUCE expression. -You may choose any REDUCE expression of the appropriate type.} - -\begin{description} -\item[\meta{\{\}}] -Braces surround an item or set of items that may be followed by an -asterisk or plus. Do not type the braces. - -\item[\meta{*}] -An italic asterisk indicates that the preceding item may be repeated zero or -more times. Do not type the asterisk. It does not indicate multiplication. - -\item[\meta{+}] -An italic plus indicates that the preceding item must appear once, and may be -repeated one or more times. Do not type the plus. It does not indicate -addition. - -\item[\meta{\&option(...)}] -\meta{\&option} indicates that the parameters that follow are optional. -\meta{\&options} indicates that options are available and explained in the -text below the command line. \meta{\&option(s)} is not to be typed. -\end{description} - -The switch settings for REDUCE in the examples in this manual are assumed to -be the default settings, unless specifically given otherwise. See the -cross-reference section \meta{Switches} in the back of this volume. - -The examples in this manual should exactly reproduce the results you get -by typing in the statements given. Any non-default switch settings are -shown. Be sure that the variables or operators used have no prior definition -by using the \name{clear} command. The numbered line prompts have generally -been left out. You can find executable files of all the examples shown here -in your \name{\$reduce/refex} directory, named alphabetically. If you are -working your way through this manual, you can run the examples as you go by -starting a new REDUCE session, and entering the command, for example: -\begin{verbatim} -in "$reduce/refex/a-ex"; -\end{verbatim} -There are numerous pauses in the files so that you can enter your own -examples and commands. If you change any switch settings or assign values -to variables in one of the pauses, make sure to restore everything to its -original state before you continue the file (see the entry under \name{CLEAR} -if you need help in clearing variables and operators). - -REDUCE converts all input to upper case, and all its responses are in upper -case. You can type input in upper case, lower case, or mixed, as you wish. -In the examples, the input is lower case, and REDUCE's responses are shown in -upper case. This protocol makes it easy to distinguish input from results. -You can tell whether you are in algebraic or symbolic mode by looking at the -numbered prompt statement REDUCE gives you: the algebraic prompt contains -a colon (\name{:}), while the symbolic prompt contains an asterisk (\name{*}). - - - +This manual describes the REDUCE symbolic mathematics system. REDUCE has +two modes of operation: the algebraic mode, which deals with polynomials +and mathematical functions in a simple procedural syntax, and the symbolic +mode, which allows Lisp-like syntax and operations. The commands, +declarations, switches and operators available in algebraic-mode REDUCE +are arranged in this manual in alphabetical order. Symbols are listed +before the letter A. + +Following the general alphabetical reference section is a similar +reference section for the High-Energy Physics operators. After that, you +can find several cross-reference sections. The first section contains +lists of reserved words and an Instant Function Cross-Reference. Next you +will find brief explanations of the common REDUCE error messages. The +next section is organized by type into Commands, Declarations, Operators, +Switches and Variables, with a brief listing for each operation. + +For a general introduction to using algebraic-mode REDUCE, see the {\em +REDUCE User's Guide}, which also contains information on symbolic mode. +The {\em The Standard Lisp Report} is a technical reference on REDUCE's +Lisp language. + +The following symbols are used to describe syntax in this manual: + +\begin{verbatim} +This font means you must type an item exactly as you see it. +\end{verbatim} + +{\em This font indicates a descriptive name for a type of REDUCE expression. +You may choose any REDUCE expression of the appropriate type.} + +\begin{description} +\item[\meta{\{\}}] +Braces surround an item or set of items that may be followed by an +asterisk or plus. Do not type the braces. + +\item[\meta{*}] +An italic asterisk indicates that the preceding item may be repeated zero or +more times. Do not type the asterisk. It does not indicate multiplication. + +\item[\meta{+}] +An italic plus indicates that the preceding item must appear once, and may be +repeated one or more times. Do not type the plus. It does not indicate +addition. + +\item[\meta{\&option(...)}] +\meta{\&option} indicates that the parameters that follow are optional. +\meta{\&options} indicates that options are available and explained in the +text below the command line. \meta{\&option(s)} is not to be typed. +\end{description} + +The switch settings for REDUCE in the examples in this manual are assumed to +be the default settings, unless specifically given otherwise. See the +cross-reference section \meta{Switches} in the back of this volume. + +The examples in this manual should exactly reproduce the results you get +by typing in the statements given. Any non-default switch settings are +shown. Be sure that the variables or operators used have no prior definition +by using the \name{clear} command. The numbered line prompts have generally +been left out. You can find executable files of all the examples shown here +in your \name{\$reduce/refex} directory, named alphabetically. If you are +working your way through this manual, you can run the examples as you go by +starting a new REDUCE session, and entering the command, for example: +\begin{verbatim} +in "$reduce/refex/a-ex"; +\end{verbatim} +There are numerous pauses in the files so that you can enter your own +examples and commands. If you change any switch settings or assign values +to variables in one of the pauses, make sure to restore everything to its +original state before you continue the file (see the entry under \name{CLEAR} +if you need help in clearing variables and operators). + +REDUCE converts all input to upper case, and all its responses are in upper +case. You can type input in upper case, lower case, or mixed, as you wish. +In the examples, the input is lower case, and REDUCE's responses are shown in +upper case. This protocol makes it easy to distinguish input from results. +You can tell whether you are in algebraic or symbolic mode by looking at the +numbered prompt statement REDUCE gives you: the algebraic prompt contains +a colon (\name{:}), while the symbolic prompt contains an asterisk (\name{*}). + + + Index: r36/help/IO.TEX ================================================================== --- r36/help/IO.TEX +++ r36/help/IO.TEX @@ -1,135 +1,135 @@ -\section{Input and Output} - -\begin{Command}{IN} -\index{input} -The \name{in} command takes a list of file names and inputs each file into -the system. -\begin{Syntax} -\name{in} \meta{filename}\{,\meta{filename}\}\optional -\end{Syntax} - -\meta{filename} must be in the current directory, or be a valid pathname. -If the file name is not an identifier, double quote marks (\name{"}) are -needed around the file name. - -\begin{Comments} -A message is given if the file cannot be found, or has a mistake -in it. - -Ending the command with a semicolon causes the file to be echoed to the -screen; ending it with a dollar sign does not echo the file. If you want -some but not all of a file echoed, turn the switch \nameref{echo} on or off -in the file. - -An efficient way to develop procedures in REDUCE is to write them into a file -using a system editor of your choice, and then input the -files into an active REDUCE session. REDUCE reparses the procedure as -it takes information from the file, overwriting the previous procedure -definition. When it accepts the procedure, it echoes its name to the screen. -Data can also be input to the system from files. - -Files to be read in should always end in \nameref{end}\name{;} to avoid -end-of-file problems. Note that this is an additional \name{end;} to any -ending procedures in the file. -\end{Comments} -\end{Command} - - -\begin{Command}{INPUT} -\index{interactive} -The \name{input} command returns the input expression to the REDUCE numbered -prompt that is its argument. -\begin{Syntax} -\name{input}\(\meta{number}\) or \name{input} \meta{number} - -\end{Syntax} - -\meta{number} must be between 1 and the current REDUCE prompt number. - -%%%\begin{Examples} -%%%\explanation{(In the following examples, unlike most others, the numbered -%%%prompt is shown.)} -%%%\end{Examples} -\begin{Comments} -An expression brought back by \name{input} can be reexecuted with new -values or switch settings, or used as an argument in another expression. -The command \nameref{ws} brings back the results of a numbered REDUCE -statement. Two lists contain every input and every output statement since -the beginning of the session. If your session is very long, storage space -begins to fill up with these expressions, so it is a good idea to end the -session once in a while, saving needed expressions to files with the -\nameref{saveas} and \nameref{out} commands. -%%% You can also clear the history lists with the \name{forget} command. - -Switch settings and \nameref{let} statements can also be reexecuted by using -\name{input}. - -An error message is given if a number is called for that has not yet been used. -\end{Comments} -\end{Command} - - -\begin{Command}{OUT} -\index{output}\index{open} -The \name{out} command directs output to the filename that is its argument, -until another \name{out} changes the output file, or \nameref{shut} closes it. -\begin{Syntax} -\name{out} \meta{filename} or \name{out "}\meta{pathname} \name{"} or \name{out t} -\end{Syntax} - -\meta{filename} must be in the current directory, or be a valid complete -file description for your system. If the file name is not -in the current directory, quote marks are needed around the file name. -If the file already exists, a message is printed allowing you to decide -whether to supersede the contents of the file with new material. - -\begin{Comments} -To restore output to the terminal, type \name{out t}, or \nameref{shut} the -file. When you use \name{out t}, the file remains available, and if you -open it again (with another \name{out}), new material is appended rather -than overwriting. - -To write a file using \name{out} that can be input at a later time, the -switch \nameref{nat} must be turned off, so that the standard linear form -is saved that can be read in by \nameref{in}. If \name{nat} is on, exponents -are printed on the line above the expression, which causes trouble -when REDUCE tries to read the file. - -There is a slight complication if you are using the \name{out} command from -inside a file to create another file. The \nameref{echo} switch is normally -off at the top-level and on while reading files (so you can see what is -being read in). If you create a file using \name{out} at the top-level, -the result lines are printed into the file as you want them. But if you -create such a file from inside a file, the \name{echo} switch is on, and -every line is echoed, first as you typed it, then as REDUCE parsed it, and -then once more for the file. Therefore, when you create a file {\it from} -a file, you need to turn \name{echo} off explicitly before the \name{out} -command, and turn it back on when you \name{shut} the created file, so your -executing file echoes as it should. This behavior also means that as you -watch the file execute, you cannot see the lines that are being put into -the \name{out} file. As soon as you turn \name{echo} on, you can see -output again. -\end{Comments} -\end{Command} - - -\begin{Command}{SHUT} -\index{output}\index{close} -The \name{shut} command closes output files. -\begin{Syntax} -\name{shut} \meta{filename}\{,\meta{filename}\}\optional -\end{Syntax} - -\meta{filename} must have been a file opened by \nameref{out}. - -\begin{Comments} -A file that has been opened by \nameref{out} must be \name{shut} before it is -brought in by \nameref{in}. Files that have been opened by \name{out} should -always be \name{shut} before the end of the REDUCE session, to avoid either -loss of information or the printing of extraneous information into the file. -In most systems, terminating a session by \nameref{bye} closes all open -output files. -\end{Comments} -\end{Command} - - +\section{Input and Output} + +\begin{Command}{IN} +\index{input} +The \name{in} command takes a list of file names and inputs each file into +the system. +\begin{Syntax} +\name{in} \meta{filename}\{,\meta{filename}\}\optional +\end{Syntax} + +\meta{filename} must be in the current directory, or be a valid pathname. +If the file name is not an identifier, double quote marks (\name{"}) are +needed around the file name. + +\begin{Comments} +A message is given if the file cannot be found, or has a mistake +in it. + +Ending the command with a semicolon causes the file to be echoed to the +screen; ending it with a dollar sign does not echo the file. If you want +some but not all of a file echoed, turn the switch \nameref{echo} on or off +in the file. + +An efficient way to develop procedures in REDUCE is to write them into a file +using a system editor of your choice, and then input the +files into an active REDUCE session. REDUCE reparses the procedure as +it takes information from the file, overwriting the previous procedure +definition. When it accepts the procedure, it echoes its name to the screen. +Data can also be input to the system from files. + +Files to be read in should always end in \nameref{end}\name{;} to avoid +end-of-file problems. Note that this is an additional \name{end;} to any +ending procedures in the file. +\end{Comments} +\end{Command} + + +\begin{Command}{INPUT} +\index{interactive} +The \name{input} command returns the input expression to the REDUCE numbered +prompt that is its argument. +\begin{Syntax} +\name{input}\(\meta{number}\) or \name{input} \meta{number} + +\end{Syntax} + +\meta{number} must be between 1 and the current REDUCE prompt number. + +%%%\begin{Examples} +%%%\explanation{(In the following examples, unlike most others, the numbered +%%%prompt is shown.)} +%%%\end{Examples} +\begin{Comments} +An expression brought back by \name{input} can be reexecuted with new +values or switch settings, or used as an argument in another expression. +The command \nameref{ws} brings back the results of a numbered REDUCE +statement. Two lists contain every input and every output statement since +the beginning of the session. If your session is very long, storage space +begins to fill up with these expressions, so it is a good idea to end the +session once in a while, saving needed expressions to files with the +\nameref{saveas} and \nameref{out} commands. +%%% You can also clear the history lists with the \name{forget} command. + +Switch settings and \nameref{let} statements can also be reexecuted by using +\name{input}. + +An error message is given if a number is called for that has not yet been used. +\end{Comments} +\end{Command} + + +\begin{Command}{OUT} +\index{output}\index{open} +The \name{out} command directs output to the filename that is its argument, +until another \name{out} changes the output file, or \nameref{shut} closes it. +\begin{Syntax} +\name{out} \meta{filename} or \name{out "}\meta{pathname} \name{"} or \name{out t} +\end{Syntax} + +\meta{filename} must be in the current directory, or be a valid complete +file description for your system. If the file name is not +in the current directory, quote marks are needed around the file name. +If the file already exists, a message is printed allowing you to decide +whether to supersede the contents of the file with new material. + +\begin{Comments} +To restore output to the terminal, type \name{out t}, or \nameref{shut} the +file. When you use \name{out t}, the file remains available, and if you +open it again (with another \name{out}), new material is appended rather +than overwriting. + +To write a file using \name{out} that can be input at a later time, the +switch \nameref{nat} must be turned off, so that the standard linear form +is saved that can be read in by \nameref{in}. If \name{nat} is on, exponents +are printed on the line above the expression, which causes trouble +when REDUCE tries to read the file. + +There is a slight complication if you are using the \name{out} command from +inside a file to create another file. The \nameref{echo} switch is normally +off at the top-level and on while reading files (so you can see what is +being read in). If you create a file using \name{out} at the top-level, +the result lines are printed into the file as you want them. But if you +create such a file from inside a file, the \name{echo} switch is on, and +every line is echoed, first as you typed it, then as REDUCE parsed it, and +then once more for the file. Therefore, when you create a file {\it from} +a file, you need to turn \name{echo} off explicitly before the \name{out} +command, and turn it back on when you \name{shut} the created file, so your +executing file echoes as it should. This behavior also means that as you +watch the file execute, you cannot see the lines that are being put into +the \name{out} file. As soon as you turn \name{echo} on, you can see +output again. +\end{Comments} +\end{Command} + + +\begin{Command}{SHUT} +\index{output}\index{close} +The \name{shut} command closes output files. +\begin{Syntax} +\name{shut} \meta{filename}\{,\meta{filename}\}\optional +\end{Syntax} + +\meta{filename} must have been a file opened by \nameref{out}. + +\begin{Comments} +A file that has been opened by \nameref{out} must be \name{shut} before it is +brought in by \nameref{in}. Files that have been opened by \name{out} should +always be \name{shut} before the end of the REDUCE session, to avoid either +loss of information or the printing of extraneous information into the file. +In most systems, terminating a session by \nameref{bye} closes all open +output files. +\end{Comments} +\end{Command} + + Index: r36/help/MATRIX.TEX ================================================================== --- r36/help/MATRIX.TEX +++ r36/help/MATRIX.TEX @@ -1,368 +1,368 @@ -\section{Matrix Operations} - -\begin{Operator}{COFACTOR} -\index{matrix} -The operator \name{cofactor} returns the cofactor of the element in row -\meta{row} and column \meta{column} of a \nameref{matrix}. Errors occur -if \meta{row} or \meta{column} do not evaluate to integer expressions or if -the matrix is not square. - -\begin{Syntax} -\name{cofactor}\(\meta{matrix\_expression},\meta{row},\meta{column}\) -% COFACTOR(EXPRN:matrix_expression,ROW:integer,COLUMN:integer):algebraic -\end{Syntax} - -\begin{Examples} -cofactor(mat((a,b,c),(d,e,f),(p,q,r)),2,2); & A*R - C*P \\ -cofactor(mat((a,b,c),(d,e,f)),1,1); & ***** non-square matrix -\end{Examples} -\end{Operator} - - -\begin{Operator}{DET} -\index{matrix}\index{determinant} -The \name{det} operator returns the determinant of its -(square \nameref{matrix}) argument. - -\begin{Syntax} -\name{det}\(\meta{expression}\) or \name{det} \meta{expression} -\end{Syntax} - -\meta{expression} must evaluate to a square matrix. - -\begin{Examples} - -matrix m,n; \\ - -m := mat((a,b),(c,d)); & \begin{multilineoutput}{4cm} -M(1,1) := A -M(1,2) := B -M(2,1) := C -M(2,2) := D - \end{multilineoutput}\\ -det m; & A*D - B*C \\ -n := mat((1,2),(1,2)); & \begin{multilineoutput}{4cm} -N(1,1) := 1 -N(1,2) := 2 -N(2,1) := 1 -N(2,2) := 2 - \end{multilineoutput} \\ - -det(n); & 0 \\ - -det(5); & 5 -\end{Examples} - -\begin{Comments} -Given a numerical argument, \name{det} returns the number. However, given a -variable name that has not been declared of type matrix, or a non-square -matrix, \name{det} returns an error message. -\end{Comments} -\end{Operator} - - -\begin{Operator}{MAT} -\index{matrix} -The \name{mat} operator is used to represent a two-dimensional -\nameref{matrix}. -\begin{Syntax} -\name{mat}\(\(\meta{expr}\{,\meta{expr}\}\optional\)% - \{\(\meta{expr}\{\name{,}\meta{expr}\}\optional\)\}\optional\) -\end{Syntax} - - -\meta{expr} may be any valid REDUCE scalar expression. - -\begin{Examples} -mat((1,2),(3,4)); & -\begin{multilineoutput}{6cm} -MAT(1,1) := 1 -MAT(2,3) := 2 -MAT(2,1) := 3 -MAT(2,2) := 4 -\end{multilineoutput}\\ -mat(2,1); & \begin{multilineoutput}{6cm} -***** Matrix mismatch -Cont? (Y or N) -\end{multilineoutput}\\ -matrix qt; \\ -qt := ws; & \begin{multilineoutput}{6cm} -QT(1,1) := 1 -QT(1,2) := 2 -QT(2,1) := 3 -QT(2,2) := 4 -\end{multilineoutput}\\ -matrix a,b; \\ -a := mat((x),(y),(z)); & \begin{multilineoutput}{6cm} -A(1,1) := X -A(2,1) := Y -A(3,1) := Z -\end{multilineoutput}\\ -b := mat((sin x,cos x,1)); & \begin{multilineoutput}{6cm} -B(1,1) := SIN(X) -B(1,2) := COS(X) -B(1,3) := 1 -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -Matrices need not have a size declared (unlike arrays). \name{mat} -redimensions a matrix variable as needed. It is necessary, of course, -that all rows be the same length. An anonymous matrix, as shown in the -first example, must be named before it can be referenced (note error -message). When using \name{mat} to fill a \IFTEX{$1 \times n$}{1 x n} -matrix, the row of values must be inside a second set of parentheses, to -eliminate ambiguity. -\end{Comments} -\end{Operator} - - -\begin{Operator}{MATEIGEN} -\index{matrix}\index{eigenvalue} -The \name{mateigen} operator calculates the eigenvalue equation and the -corresponding eigenvectors of a \nameref{matrix}. -\begin{Syntax} -\name{mateigen}\(\meta{matrix-id},\meta{tag-id}\) -\end{Syntax} - - -\meta{matrix-id} must be a declared matrix of values, and \meta{tag-id} must be -a legal REDUCE identifier. - -\begin{Examples} -aa := mat((2,5),(1,0))\$ \\ -mateigen(aa,alpha); & -\begin{multilineoutput}{2cm} -\{\{ALPHA^{2} - 2*ALPHA - 5, - 1, - MAT(1,1) := \rfrac{5*ARBCOMPLEX(1)}{ALPHA - 2}, \\\\ - - MAT(2,1) := ARBCOMPLEX(1) - \}\} -\end{multilineoutput}\\ -charpoly := first first ws; & CHARPOLY := ALPHA^{2} - 2*ALPHA - 5 \\ -bb := mat((1,0,1),(1,1,0),(0,0,1))\$ \\ -mateigen(bb,lamb); & -\begin{multilineoutput}{6cm} -\{\{LAMB - 1,3, - [ 0 ] - [ARBCOMPLEX(2)] - [ 0 ] - \}\} -\end{multilineoutput} -\end{Examples} - - -\begin{Comments} -The \name{mateigen} operator returns a list of lists of three -elements. The first element is a square free factor of the characteristic -polynomial; the second element is its multiplicity; and the third element -is the corresponding eigenvector. If the characteristic polynomial can be -completely factored, the product of the first elements of all the sublists -will produce the minimal polynomial. You can access the various parts of -the answer with the usual list access operators. - -If the matrix is degenerate, more than one eigenvector can be produced for -the same eigenvalue, as shown by more than one arbitrary variable in the -eigenvector. The identification numbers of the arbitrary complex variables -shown in the examples above may not be the same as yours. Note that since -\name{lambda} is a reserved word in REDUCE, you cannot use it as a {\it -tag-id} for this operator. -\end{Comments} -\end{Operator} - - -\begin{Declaration}{MATRIX} -Identifiers are declared to be of type \name{matrix}. -\begin{Syntax} -\name{matrix} \meta{identifier} \&option \(\meta{index},\meta{index}\)\\ - \{,\meta{identifier} \&option - \(\meta{index},\meta{index}\)\}\optional -\end{Syntax} - -\meta{identifier} must not be an already-defined operator or array or -the name of a scalar variable. Dimensions are optional, and if used appear -inside parentheses. \meta{index} must be a positive integer. - -\begin{Examples} -matrix a,b(1,4),c(4,4); \\ -b(1,1); & 0 \\ -a(1,1); & ***** Matrix A not set \\ -a := mat((x0,y0),(x1,y1)); & \begin{multilineoutput}{6cm} -A(1,1) := X0 -A(1,2) := Y0 -A(2,1) := X0 -A(2,2) := X1 -\end{multilineoutput}\\ -length a; & \{2,2\} \\ -b := a**2; & \begin{multilineoutput}{6cm} -B(1,1) := X0^{2} + X1*Y0 -B(1,2) := Y0*(X0 + Y1) -B(2,1) := X1*(X0 + Y1) -B(2,2) := X1*Y0 + Y1^{2} -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -When a matrix variable has not been dimensioned, matrix elements cannot be -referenced until the matrix is set by the \nameref{mat} operator. When a -matrix is dimensioned in its declaration, matrix elements are set to 0. -Matrix elements cannot stand for themselves. When you use \nameref{let} on -a matrix element, there is no effect unless the element contains a -constant, in which case an error message is returned. The same behavior -occurs with \nameref{clear}. Do \meta{not} use \nameref{clear} to try to -set a matrix element to 0. \nameref{let} statements can be applied to -matrices as a whole, if the right-hand side of the expression is a matrix -expression, and the left-hand side identifier has been declared to be a matrix. - -Arithmetical operators apply to matrices of the correct dimensions. The -operators \name{+} and \name{-} can be used with matrices of the same -dimensions. The operator \name{*} can be used to multiply -\IFTEX{$m \times n$}{m x n} matrices by \IFTEX{$n \times p$}{n x p} -matrices. Matrix multiplication is non-commutative. Scalars can also be -multiplied with matrices, with the result that each element of the matrix -is multiplied by the scalar. The operator \name{/} applied to two -matrices computes the first matrix multiplied by the inverse of the -second, if the inverse exists, and produces an error message otherwise. -Matrices can be divided by scalars, which results in dividing each element -of the matrix. Scalars can also be divided by matrices when the matrices -are invertible, and the result is the multiplication of the scalar by the -inverse of the matrix. Matrix inverses can by found by \name{1/A} or -\name{/A}, where \name{A} is a matrix. Square matrices can be raised to -positive integer powers, and also to negative integer powers if they are -nonsingular. - -When a matrix variable is assigned to the results of a calculation, the -matrix is redimensioned if necessary. -\end{Comments} -\end{Declaration} - - -\begin{Operator}{NULLSPACE} -\index{matrix} -\begin{Syntax} -\name{nullspace}(\meta{matrix\_expression}) -\end{Syntax} - -\meta{nullspace} calculates for its \nameref{matrix} argument, -\name{a}, a list of -linear independent vectors (a basis) whose linear combinations satisfy the -equation $a x = 0$. The basis is provided in a form such that as many -upper components as possible are isolated. - -\begin{Examples} -nullspace mat((1,2,3,4),(5,6,7,8)); & -\begin{multilineoutput}{6cm} - \{ - [ 1 ] - [ ] - [ 0 ] - [ ] - [ - 3] - [ ] - [ 2 ] - , - [ 0 ] - [ ] - [ 1 ] - [ ] - [ - 2] - [ ] - [ 1 ] - \} -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -Note that with \name{b := nullspace a}, the expression \name{length b} is -the {\em nullity\/} of A, and that \name{second length a - length b} -calculates the {\em rank\/} of A. The rank of a matrix expression can -also be found more directly by the \nameref{rank} operator. - -In addition to the REDUCE matrix form, \name{nullspace} accepts as input a -matrix given as a \nameref{list} of lists, that is interpreted as a row matrix. If -that form of input is chosen, the vectors in the result will be -represented by lists as well. This additional input syntax facilitates -the use of \name{nullspace} in applications different from classical linear -algebra. -\end{Comments} - -\end{Operator} - - -\begin{Operator}{RANK} -\index{matrix} -\begin{Syntax} -\name{rank}(\meta{matrix\_expression}) -\end{Syntax} -\name{rank} calculates the rank of its matrix argument. - -\begin{Examples} -rank mat((a,b,c),(d,e,f)); & 2 -\end{Examples} - -\begin{Comments} -The argument to \name{rank} can also be a \nameref{list} of lists, interpreted -either as a row matrix or a set of equations. If that form of input is -chosen, the vectors in the result will be represented by lists as well. -This additional input syntax facilitates the use of \name{rank} in -applications different from classical linear algebra. -\end{Comments} - -\end{Operator} - - -\begin{Operator}{TP} -\index{transpose}\index{matrix} -The \name{tp} operator returns the transpose of its \nameref{matrix} - argument. -\begin{Syntax} -\name{tp} \meta{identifier} or \name{tp}\(\meta{identifier}\) -\end{Syntax} - -\meta{identifier} must be a matrix, which either has had its dimensions set -in its declaration, or has had values put into it by \name{mat}. - -\begin{Examples} -matrix m,n; \\ -m := mat((1,2,3),(4,5,6))$ \\ -n := tp m; & -\begin{multilineoutput}{6cm} -N(1,1) := 1 -N(1,2) := 4 -N(2,1) := 2 -N(2,2) := 5 -N(3,1) := 3 -N(3,2) := 6 -\end{multilineoutput} -\end{Examples} -\begin{Comments} -In an assignment statement involving \name{tp}, the matrix identifier on the -left-hand side is redimensioned to the correct size for the transpose. -\end{Comments} -\end{Operator} - - -\begin{Operator}{TRACE} -\index{matrix} -The \name{trace} operator finds the trace of its \nameref{matrix} argument. -\begin{Syntax} -\name{trace}\(\meta{expression}\) or \name{trace} \meta{simple\_expression} -\end{Syntax} - -\meta{expression} or \meta{simple\_expression} must evaluate to a square -matrix. - -\begin{Examples} -matrix a; \\ -a := mat((x1,y1),(x2,y2))\$ \\ -trace a; & X1 + Y2 -\end{Examples} -\begin{Comments} -The trace is the sum of the entries along the diagonal of a square matrix. -Given a non-matrix expression, or a non-square matrix, \name{trace} returns -an error message. -\end{Comments} -\end{Operator} - - +\section{Matrix Operations} + +\begin{Operator}{COFACTOR} +\index{matrix} +The operator \name{cofactor} returns the cofactor of the element in row +\meta{row} and column \meta{column} of a \nameref{matrix}. Errors occur +if \meta{row} or \meta{column} do not evaluate to integer expressions or if +the matrix is not square. + +\begin{Syntax} +\name{cofactor}\(\meta{matrix\_expression},\meta{row},\meta{column}\) +% COFACTOR(EXPRN:matrix_expression,ROW:integer,COLUMN:integer):algebraic +\end{Syntax} + +\begin{Examples} +cofactor(mat((a,b,c),(d,e,f),(p,q,r)),2,2); & A*R - C*P \\ +cofactor(mat((a,b,c),(d,e,f)),1,1); & ***** non-square matrix +\end{Examples} +\end{Operator} + + +\begin{Operator}{DET} +\index{matrix}\index{determinant} +The \name{det} operator returns the determinant of its +(square \nameref{matrix}) argument. + +\begin{Syntax} +\name{det}\(\meta{expression}\) or \name{det} \meta{expression} +\end{Syntax} + +\meta{expression} must evaluate to a square matrix. + +\begin{Examples} + +matrix m,n; \\ + +m := mat((a,b),(c,d)); & \begin{multilineoutput}{4cm} +M(1,1) := A +M(1,2) := B +M(2,1) := C +M(2,2) := D + \end{multilineoutput}\\ +det m; & A*D - B*C \\ +n := mat((1,2),(1,2)); & \begin{multilineoutput}{4cm} +N(1,1) := 1 +N(1,2) := 2 +N(2,1) := 1 +N(2,2) := 2 + \end{multilineoutput} \\ + +det(n); & 0 \\ + +det(5); & 5 +\end{Examples} + +\begin{Comments} +Given a numerical argument, \name{det} returns the number. However, given a +variable name that has not been declared of type matrix, or a non-square +matrix, \name{det} returns an error message. +\end{Comments} +\end{Operator} + + +\begin{Operator}{MAT} +\index{matrix} +The \name{mat} operator is used to represent a two-dimensional +\nameref{matrix}. +\begin{Syntax} +\name{mat}\(\(\meta{expr}\{,\meta{expr}\}\optional\)% + \{\(\meta{expr}\{\name{,}\meta{expr}\}\optional\)\}\optional\) +\end{Syntax} + + +\meta{expr} may be any valid REDUCE scalar expression. + +\begin{Examples} +mat((1,2),(3,4)); & +\begin{multilineoutput}{6cm} +MAT(1,1) := 1 +MAT(2,3) := 2 +MAT(2,1) := 3 +MAT(2,2) := 4 +\end{multilineoutput}\\ +mat(2,1); & \begin{multilineoutput}{6cm} +***** Matrix mismatch +Cont? (Y or N) +\end{multilineoutput}\\ +matrix qt; \\ +qt := ws; & \begin{multilineoutput}{6cm} +QT(1,1) := 1 +QT(1,2) := 2 +QT(2,1) := 3 +QT(2,2) := 4 +\end{multilineoutput}\\ +matrix a,b; \\ +a := mat((x),(y),(z)); & \begin{multilineoutput}{6cm} +A(1,1) := X +A(2,1) := Y +A(3,1) := Z +\end{multilineoutput}\\ +b := mat((sin x,cos x,1)); & \begin{multilineoutput}{6cm} +B(1,1) := SIN(X) +B(1,2) := COS(X) +B(1,3) := 1 +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +Matrices need not have a size declared (unlike arrays). \name{mat} +redimensions a matrix variable as needed. It is necessary, of course, +that all rows be the same length. An anonymous matrix, as shown in the +first example, must be named before it can be referenced (note error +message). When using \name{mat} to fill a \IFTEX{$1 \times n$}{1 x n} +matrix, the row of values must be inside a second set of parentheses, to +eliminate ambiguity. +\end{Comments} +\end{Operator} + + +\begin{Operator}{MATEIGEN} +\index{matrix}\index{eigenvalue} +The \name{mateigen} operator calculates the eigenvalue equation and the +corresponding eigenvectors of a \nameref{matrix}. +\begin{Syntax} +\name{mateigen}\(\meta{matrix-id},\meta{tag-id}\) +\end{Syntax} + + +\meta{matrix-id} must be a declared matrix of values, and \meta{tag-id} must be +a legal REDUCE identifier. + +\begin{Examples} +aa := mat((2,5),(1,0))\$ \\ +mateigen(aa,alpha); & +\begin{multilineoutput}{2cm} +\{\{ALPHA^{2} - 2*ALPHA - 5, + 1, + MAT(1,1) := \rfrac{5*ARBCOMPLEX(1)}{ALPHA - 2}, \\\\ + + MAT(2,1) := ARBCOMPLEX(1) + \}\} +\end{multilineoutput}\\ +charpoly := first first ws; & CHARPOLY := ALPHA^{2} - 2*ALPHA - 5 \\ +bb := mat((1,0,1),(1,1,0),(0,0,1))\$ \\ +mateigen(bb,lamb); & +\begin{multilineoutput}{6cm} +\{\{LAMB - 1,3, + [ 0 ] + [ARBCOMPLEX(2)] + [ 0 ] + \}\} +\end{multilineoutput} +\end{Examples} + + +\begin{Comments} +The \name{mateigen} operator returns a list of lists of three +elements. The first element is a square free factor of the characteristic +polynomial; the second element is its multiplicity; and the third element +is the corresponding eigenvector. If the characteristic polynomial can be +completely factored, the product of the first elements of all the sublists +will produce the minimal polynomial. You can access the various parts of +the answer with the usual list access operators. + +If the matrix is degenerate, more than one eigenvector can be produced for +the same eigenvalue, as shown by more than one arbitrary variable in the +eigenvector. The identification numbers of the arbitrary complex variables +shown in the examples above may not be the same as yours. Note that since +\name{lambda} is a reserved word in REDUCE, you cannot use it as a {\it +tag-id} for this operator. +\end{Comments} +\end{Operator} + + +\begin{Declaration}{MATRIX} +Identifiers are declared to be of type \name{matrix}. +\begin{Syntax} +\name{matrix} \meta{identifier} \&option \(\meta{index},\meta{index}\)\\ + \{,\meta{identifier} \&option + \(\meta{index},\meta{index}\)\}\optional +\end{Syntax} + +\meta{identifier} must not be an already-defined operator or array or +the name of a scalar variable. Dimensions are optional, and if used appear +inside parentheses. \meta{index} must be a positive integer. + +\begin{Examples} +matrix a,b(1,4),c(4,4); \\ +b(1,1); & 0 \\ +a(1,1); & ***** Matrix A not set \\ +a := mat((x0,y0),(x1,y1)); & \begin{multilineoutput}{6cm} +A(1,1) := X0 +A(1,2) := Y0 +A(2,1) := X0 +A(2,2) := X1 +\end{multilineoutput}\\ +length a; & \{2,2\} \\ +b := a**2; & \begin{multilineoutput}{6cm} +B(1,1) := X0^{2} + X1*Y0 +B(1,2) := Y0*(X0 + Y1) +B(2,1) := X1*(X0 + Y1) +B(2,2) := X1*Y0 + Y1^{2} +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +When a matrix variable has not been dimensioned, matrix elements cannot be +referenced until the matrix is set by the \nameref{mat} operator. When a +matrix is dimensioned in its declaration, matrix elements are set to 0. +Matrix elements cannot stand for themselves. When you use \nameref{let} on +a matrix element, there is no effect unless the element contains a +constant, in which case an error message is returned. The same behavior +occurs with \nameref{clear}. Do \meta{not} use \nameref{clear} to try to +set a matrix element to 0. \nameref{let} statements can be applied to +matrices as a whole, if the right-hand side of the expression is a matrix +expression, and the left-hand side identifier has been declared to be a matrix. + +Arithmetical operators apply to matrices of the correct dimensions. The +operators \name{+} and \name{-} can be used with matrices of the same +dimensions. The operator \name{*} can be used to multiply +\IFTEX{$m \times n$}{m x n} matrices by \IFTEX{$n \times p$}{n x p} +matrices. Matrix multiplication is non-commutative. Scalars can also be +multiplied with matrices, with the result that each element of the matrix +is multiplied by the scalar. The operator \name{/} applied to two +matrices computes the first matrix multiplied by the inverse of the +second, if the inverse exists, and produces an error message otherwise. +Matrices can be divided by scalars, which results in dividing each element +of the matrix. Scalars can also be divided by matrices when the matrices +are invertible, and the result is the multiplication of the scalar by the +inverse of the matrix. Matrix inverses can by found by \name{1/A} or +\name{/A}, where \name{A} is a matrix. Square matrices can be raised to +positive integer powers, and also to negative integer powers if they are +nonsingular. + +When a matrix variable is assigned to the results of a calculation, the +matrix is redimensioned if necessary. +\end{Comments} +\end{Declaration} + + +\begin{Operator}{NULLSPACE} +\index{matrix} +\begin{Syntax} +\name{nullspace}(\meta{matrix\_expression}) +\end{Syntax} + +\meta{nullspace} calculates for its \nameref{matrix} argument, +\name{a}, a list of +linear independent vectors (a basis) whose linear combinations satisfy the +equation $a x = 0$. The basis is provided in a form such that as many +upper components as possible are isolated. + +\begin{Examples} +nullspace mat((1,2,3,4),(5,6,7,8)); & +\begin{multilineoutput}{6cm} + \{ + [ 1 ] + [ ] + [ 0 ] + [ ] + [ - 3] + [ ] + [ 2 ] + , + [ 0 ] + [ ] + [ 1 ] + [ ] + [ - 2] + [ ] + [ 1 ] + \} +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +Note that with \name{b := nullspace a}, the expression \name{length b} is +the {\em nullity\/} of A, and that \name{second length a - length b} +calculates the {\em rank\/} of A. The rank of a matrix expression can +also be found more directly by the \nameref{rank} operator. + +In addition to the REDUCE matrix form, \name{nullspace} accepts as input a +matrix given as a \nameref{list} of lists, that is interpreted as a row matrix. If +that form of input is chosen, the vectors in the result will be +represented by lists as well. This additional input syntax facilitates +the use of \name{nullspace} in applications different from classical linear +algebra. +\end{Comments} + +\end{Operator} + + +\begin{Operator}{RANK} +\index{matrix} +\begin{Syntax} +\name{rank}(\meta{matrix\_expression}) +\end{Syntax} +\name{rank} calculates the rank of its matrix argument. + +\begin{Examples} +rank mat((a,b,c),(d,e,f)); & 2 +\end{Examples} + +\begin{Comments} +The argument to \name{rank} can also be a \nameref{list} of lists, interpreted +either as a row matrix or a set of equations. If that form of input is +chosen, the vectors in the result will be represented by lists as well. +This additional input syntax facilitates the use of \name{rank} in +applications different from classical linear algebra. +\end{Comments} + +\end{Operator} + + +\begin{Operator}{TP} +\index{transpose}\index{matrix} +The \name{tp} operator returns the transpose of its \nameref{matrix} + argument. +\begin{Syntax} +\name{tp} \meta{identifier} or \name{tp}\(\meta{identifier}\) +\end{Syntax} + +\meta{identifier} must be a matrix, which either has had its dimensions set +in its declaration, or has had values put into it by \name{mat}. + +\begin{Examples} +matrix m,n; \\ +m := mat((1,2,3),(4,5,6))$ \\ +n := tp m; & +\begin{multilineoutput}{6cm} +N(1,1) := 1 +N(1,2) := 4 +N(2,1) := 2 +N(2,2) := 5 +N(3,1) := 3 +N(3,2) := 6 +\end{multilineoutput} +\end{Examples} +\begin{Comments} +In an assignment statement involving \name{tp}, the matrix identifier on the +left-hand side is redimensioned to the correct size for the transpose. +\end{Comments} +\end{Operator} + + +\begin{Operator}{TRACE} +\index{matrix} +The \name{trace} operator finds the trace of its \nameref{matrix} argument. +\begin{Syntax} +\name{trace}\(\meta{expression}\) or \name{trace} \meta{simple\_expression} +\end{Syntax} + +\meta{expression} or \meta{simple\_expression} must evaluate to a square +matrix. + +\begin{Examples} +matrix a; \\ +a := mat((x1,y1),(x2,y2))\$ \\ +trace a; & X1 + Y2 +\end{Examples} +\begin{Comments} +The trace is the sum of the entries along the diagonal of a square matrix. +Given a non-matrix expression, or a non-square matrix, \name{trace} returns +an error message. +\end{Comments} +\end{Operator} + + Index: r36/help/MKHELP ================================================================== --- r36/help/MKHELP +++ r36/help/MKHELP @@ -1,7 +1,7 @@ -# The REDUCE Reference Manual - -latex redhelp -latex redhelp -latex redhelp -makeindex redhelp -latex redhelp +# The REDUCE Reference Manual + +latex redhelp +latex redhelp +latex redhelp +makeindex redhelp +latex redhelp Index: r36/help/MKTABLE ================================================================== --- r36/help/MKTABLE +++ r36/help/MKTABLE @@ -1,14 +1,14 @@ -# Creates a table of all keywords defined the in the help files. - -grep '***** To' *.tex -grep '\begin{Command}' *.tex -grep '\begin{Operator}' *.tex -grep '\begin{Switch}' *.tex -grep '\begin{Variable}' *.tex -grep '\begin{Declaration}' *.tex -grep '\begin{Package}' *.tex -grep '\begin{Concept}' *.tex -grep '\begin{Constant}' *.tex -grep '\begin{Type}' *.tex -grep '\begin{info}' *.tex -grep '\section' *.tex +# Creates a table of all keywords defined the in the help files. + +grep '***** To' *.tex +grep '\begin{Command}' *.tex +grep '\begin{Operator}' *.tex +grep '\begin{Switch}' *.tex +grep '\begin{Variable}' *.tex +grep '\begin{Declaration}' *.tex +grep '\begin{Package}' *.tex +grep '\begin{Concept}' *.tex +grep '\begin{Constant}' *.tex +grep '\begin{Type}' *.tex +grep '\begin{info}' *.tex +grep '\section' *.tex Index: r36/help/OBSOLETE.TEX ================================================================== --- r36/help/OBSOLETE.TEX +++ r36/help/OBSOLETE.TEX @@ -1,7 +1,7 @@ -\begin{Switch}{NONLNR} - -***** No longer needed ***** - -\end{Switch} - - +\begin{Switch}{NONLNR} + +***** No longer needed ***** + +\end{Switch} + + Index: r36/help/PK-NUMER.TEX ================================================================== --- r36/help/PK-NUMER.TEX +++ r36/help/PK-NUMER.TEX @@ -1,394 +1,394 @@ -\section{Numeric Package} -\begin{Introduction}{Numeric Package} -The numeric package supplies algorithms based on approximation -techniques of numerical mathematics. The algorithms use -the \nameref{rounded} mode arithmetic of REDUCE, including -the variable precision feature which is exploited in some -algorithms in an adaptive manner in order to reach the -desired accuracy. -\end{Introduction} - -\begin{Type}{Interval} -Intervals are generally coded as lower bound and -upper bound connected by the operator \name{..}, usually -associated to a variable in an -equation. - -\begin{Syntax} - \meta{var} = \(\meta{low} .. \meta{high}\) -\end{Syntax} - -where \meta{var} is a \nameref{kernel} and \meta{low}, \meta{high} are -numbers or expression which evaluate to numbers with \meta{low}<=\meta{high}. - -\begin{Examples} - x= (2.5 .. 3.5) -\end{Examples} - -means that the variable x is taken in the range from 2.5 up to -3.5. - - -\end{Type} - -\begin{Concept}{numeric accuracy} -The keyword parameters \name{accuracy=a} and \name{iterations=i}, -where \name{a}and \name{i} must be positive integer numbers, control the -iterative algorithms: the iteration is continued until -the local error is below 10**{-a}; if that is impossible -within \name{i} steps, the iteration is terminated with an -error message. The values reached so far are then returned -as the result. -\end{Concept} - -\begin{Switch}{TRNUMERIC} -Normally the algorithms produce only a minimum of printed -output during their operation. In cases of an unsuccessful -or unexpected long operation a \name{trace of the iteration} can be -printed by setting \name{trnumeric} \name{on}. -\end{Switch} - -\begin{Operator}{num_min} -\index{minimum}\index{steepest descent}\index{Fletcher Reeves} -The Fletcher Reeves version of the \name{steepest descent} -algorithms is used to find the \name{minimum} of a -function of one or more variables. The -function must have continuous partial derivatives with respect to all -variables. The starting point of the search can be -specified; if not, random values are taken instead. -The steepest descent algorithms in general find only local -minima. - -\begin{Syntax} - - \name{num\_min}\(\meta{exp}, - \meta{var}[=\meta{val}] [,\meta{var}[=\meta{val}] ... - [,accuracy=\meta{a}] [,iterations=\meta{i}]\) - - -or - - \name{num\_min}\(exp, \{ - \meta{var}[=\meta{val}] [,\meta{var}[=\meta{val}] ...] \} - [,accuracy=\meta{a}] [,iterations=\meta{i}]\) -\end{Syntax} - -where \meta{exp} is a function expression, -\meta{var} are the variables in \meta{exp} and -\meta{val} are the (optional) start values. -For \meta{a} and \meta{i} see \nameref{numeric accuracy}. - -\name{Num\_min} tries to find the next local minimum along the descending -path starting at the given point. The result is a \nameref{list} -with the minimum function value as first element followed by a list -of \nameref{equation}\name{s}, where the variables are equated to the coordinates -of the result point. - - -\begin{Examples} -num_min(sin(x)+x/5, x)&\{4.9489585606,\{X=29.643767785\}\}\\ -num_min(sin(x)+x/5, x=0)&\{ - 1.3342267466,\{X= - 1.7721582671\}\} -\end{Examples} -\end{Operator} - -\begin{Operator}{num_solve} -\index{equation solving}\index{equation system}\index{Newton iteration} -\index{root} -An adaptively damped Newton iteration is used to find -an approximative root of a function (function vector) or the -solution of an \nameref{equation} (equation system). The expressions -must have continuous derivatives for all variables. -A starting point for the iteration can be given. If not given -random values are taken instead. When the number of -forms is not equal to the number of variables, the -Newton method cannot be applied. Then the minimum -of the sum of absolute squares is located instead. - -With \nameref{complex} on, solutions with imaginary parts can be -found, if either the expression(s) or the starting point -contain a nonzero imaginary part. - -\begin{Syntax} - \name{num\_solve}\(\meta{exp}, \meta{var}[=\meta{val}][,accuracy=\meta{a}][,iterations=\meta{i}]\) - -or - - \name{num\_solve}\(\{\meta{exp},...,\meta{exp}\}, \meta{var}[=\meta{val}],...,\meta{var}[=\meta{val}] - [,accuracy=\meta{a}][,iterations=\meta{i}]\) - -or - - \name{num\_solve}\(\{\meta{exp},...,\meta{exp}\}, \{\meta{var}[=\meta{val}],...,\meta{var}[=\meta{val}]\} - [,accuracy=\meta{a}][,iterations=\meta{i}]\) - -\end{Syntax} - - -where \meta{exp} are function expressions, - \meta{var} are the variables, - \meta{val} are optional start values. -For \meta{a} and \meta{i} see \nameref{numeric accuracy}. - -\name{num_solve} tries to find a zero/solution of the expression(s). -Result is a list of equations, where the variables are -equated to the coordinates of the result point. - -The \nameindex{Jacobian matrix} is stored as side effect the shared -variable \name{jacobian}. - - -\begin{Examples} -num_solve({sin x=cos y, x + y = 1},{x=1,y=2});& - \{X= - 1.8561957251,Y=2.856195584\}\\ -jacobian;& -\begin{multilineoutput}{5cm} - [COS(X) SIN(Y)] - [ ] - [ 1 1 ] -\end{multilineoutput} -\end{Examples} -\end{Operator} - -\begin{Operator}{num_int} -\index{integration} -For the numerical evaluation of univariate integrals -over a finite interval the following strategy is used: -If \nameref{int} finds a formal antiderivative - which is bounded in the integration interval, this - is evaluated and the end points and the difference - is returned. -Otherwise a \nameref{Chebyshev fit} is computed, - starting with order 20, eventually up to order 80. - If that is recognized as sufficiently convergent - it is used for computing the integral by directly - integrating the coefficient sequence. -If none of these methods is successful, an - adaptive multilevel quadrature algorithm is used. - -For multivariate integrals only the adaptive quadrature is used. -This algorithm tolerates isolated singularities. -The value \name{iterations} here limits the number of -local interval intersection levels. -\meta{a} is a measure for the relative total discretization -error (comparison of order 1 and order 2 approximations). - - -\begin{Syntax} - \name{num_int}\(\meta{exp},\meta{var}=\(\meta{l} .. \meta{u}\) - [,\meta{var}=\(\meta{l} .. \meta{u}\),...] - [,accuracy=\meta{a}][,iterations=\meta{i}]\) -\end{Syntax} - -where \meta{exp} is the function to be integrated, -\meta{var} are the integration variables, -\meta{l} are the lower bounds, -\meta{u} are the upper bounds. - -Result is the value of the integral. - -\begin{Examples} -num_int(sin x,x=(0 .. 3.1415926));& 2.0000010334 -\end{Examples} -\end{Operator} - -\begin{Operator}{num_odesolve} -\index{Runge-Kutta}\index{initial value problem}\index{ODE} -The \name{Runge-Kutta} method of order 3 finds an approximate graph for -the solution of real \name{ODE initial value problem}. - -\begin{Syntax} - \name{num_odesolve}\(\meta{exp},\meta{depvar}=\meta{start}, - \meta{indep}=\(\meta{from} .. \meta{to}\) - [,accuracy=\meta{a}][,iterations=\meta{i}]\) - -or - -\name{num_odesolve}\(\{\meta{exp},\meta{exp},...\}, - \{ \meta{depvar}=\meta{start},\meta{depvar}=\meta{start},...\} - \meta{indep}=\(\meta{from} .. \meta{to}\) - [,accuracy=\meta{a}][,iterations=\meta{i}]\) - -\end{Syntax} - -where -\meta{depvar} and \meta{start} specify the dependent variable(s) -and the starting point value (vector), -\meta{indep}, \meta{from} and \meta{to} specify the independent variable -and the integration interval (starting point and end point), -\meta{exp} are equations or expressions which -contain the first derivative of the independent variable -with respect to the dependent variable. - -The ODEs are converted to an explicit form, which then is -used for a Runge Kutta iteration over the given range. The -number of steps is controlled by the value of \meta{i} -(default: 20). If the steps are too coarse to reach the desired -accuracy in the neighborhood of the starting point, the number is -increased automatically. - -Result is a list of pairs, each representing a point of the -approximate solution of the ODE problem. - -\begin{Examples} -depend(y,x);\\ -num_odesolve(df(y,x)=y,y=1,x=(0 .. 1), iterations=5);& -\begin{multilineoutput} - \{\{0.0,1.0\},\{0.2,1.2214\},\{0.4,1.49181796\},\{0.6,1.8221064563\}, - \{0.8,2.2255208258\},\{1.0,2.7182511366\}\}\\ -\end{multilineoutput} -\end{Examples} - -In most cases you must declare the dependency relation -between the variables explicitly using \nameref{depend}; -otherwise the formal derivative might be converted to zero. - -The operator \nameref{solve} is used to convert the form into -an explicit ODE. If that process fails or if it has no unique result, -the evaluation is stopped with an error message. - -\end{Operator} - -\begin{Operator}{bounds} - -Upper and lower bounds of a real valued function over an -\nameref{interval} or a rectangular multivariate domain are computed -by the operator \name{bounds}. The algorithmic basis is the computation -with inequalities: starting from the interval(s) of the -variables, the bounds are propagated in the expression -using the rules for inequality computation. Some knowledge -about the behavior of special functions like ABS, SIN, COS, EXP, LOG, -fractional exponentials etc. is integrated and can be evaluated -if the operator \name{bounds} is called with rounded mode on -(otherwise only algebraic evaluation rules are available). - -If \name{bounds} finds a singularity within an interval, the evaluation -is stopped with an error message indicating the problem part -of the expression. - -\begin{Syntax} - \name{bounds}\(\meta{exp},\meta{var}=\(\meta{l} .. \meta{u}\) - [,\meta{var}=\(\meta{l} .. \meta{u}\) ...]\) - -or - - \name{bounds}\(\meta{exp},\{\meta{var}=\(\meta{l} .. \meta{u}\) - [,\meta{var}=\(\meta{l} .. \meta{u}\) ...]\}\) - - -\end{Syntax} - -where \meta{exp} is the function to be investigated, -\meta{var} are the variables of \meta{exp}, -\meta{l} and \meta{u} specify the area as set of \nameref{interval}\name{s}. - -\name{bounds} computes upper and lower bounds for the expression in the -given area. An \nameref{interval} is returned. - -\begin{Examples} -bounds(sin x,x=(1 .. 2));& -1 .. 1\\ -on rounded;\\ -bounds(sin x,x=(1 .. 2));& 0.84147098481 .. 1\\ -bounds(x**2+x,x=(-0.5 .. 0.5));& - 0.25 .. 0.75\\ -\end{Examples} -\end{Operator} - -\begin{Concept}{Chebyshev fit} -\index{approximation} -The operator family \name{Chebyshev\_...} implements approximation -and evaluation of functions by the Chebyshev method. -Let \name{T(n,a,b,x)} be the Chebyshev polynomial of order \name{n} -transformed to the interval \name{(a,b)}. -Then a function \name{f(x)} can be -approximated in \name{(a,b)} by a series - -\begin{verbatim} - for i := 0:n sum c(i)*T(i,a,b,x) -\end{verbatim} - -The operator \name{chebyshev\_fit} computes this approximation and -returns a list, which has as first element the sum expressed -as a polynomial and as second element the sequence -of Chebyshev coefficients. -\name{Chebyshev\_df} and \name{Chebyshev\_int} transform a Chebyshev -coefficient list into the coefficients of the corresponding -derivative or integral respectively. For evaluating a Chebyshev -approximation at a given point in the basic interval the -operator \name{Chebyshev\_eval} can be used. -\name{Chebyshev\_eval} is based on a recurrence relation which is -in general more stable than a direct evaluation of the -complete polynomial. - -\begin{Syntax} - \name{chebyshev\_fit}\(\meta{fcn},\meta{var}=\(\meta{lo} .. \meta{hi}\),\meta{n}\) - - \name{chebyshev\_eval}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\), - \meta{var}=\meta{pt}\) - - \name{chebyshev\_df}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\)\) - - \name{chebyshev\_int}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\)\) -\end{Syntax} - -where \meta{fcn} is an algebraic expression (the target function), -\meta{var} is the variable of \meta{fcn}, -\meta{lo} and \meta{hi} are -numerical real values which describe an \nameref{interval} \meta{lo} < \meta{hi}, -the integer \meta{n} is the approximation order (set to 20 if missing), -\meta{pt} is a number in the interval and \meta{coeffs} is -a series of Chebyshev coefficients. - -\begin{Examples} - -on rounded;\\ - -w:=chebyshev_fit(sin x/x,x=(1 .. 3),5);& -\begin{multilineoutput}{6cm} -w := \{0.03824*x^3 - 0.2398*x^2 + 0.06514*x + 0.9778, - \{0.8991,-0.4066,-0.005198,0.009464,-0.00009511\}\} -\end{multilineoutput}\\ -chebyshev_eval(second w, x=(1 .. 3), x=2.1);& 0.4111\\ -\end{Examples} -\end{Concept} - -\begin{Operator}{num_fit} -\index{approximation}\index{least squares} -The operator \name{num_fit} finds for a set of -points the linear combination of a given set of -functions (function basis) which approximates the -points best under the objective of the \name{least squares} -criterion (minimum of the sum of the squares of the deviation). -The solution is found as zero of the -gradient vector of the sum of squared errors. - - -\begin{Syntax} - \name{num_fit}\(\meta{vals},\meta{basis},\meta{var}=\meta{pts}\) -\end{Syntax} - -where \meta{vals} is a list of numeric values, -\meta{var} is a variable used for the approximation, -\meta{pts} is a list of coordinate values which correspond to -\meta{var}, -\meta{basis} is a set of functions varying in \name{var} which is used - for the approximation. - - -The result is a list containing as first element the -function which approximates the given values, and as -second element a list of coefficients which were used -to build this function from the basis. - -\begin{Examples} - -pts:=for i:=1 step 1 until 5 collect i$\\ -vals:=for i:=1 step 1 until 5 collect\\ - for j:=1:i product j$\\ -num_fit(vals,{1,x,x**2},x=pts);& -\begin{multilineoutput}{6cm} - \{14.571428571*X^2 - 61.428571429*X + 54.6,\{54.6, - - 61.428571429,14.571428571\}\} -\end{multilineoutput} - -\end{Examples} - -\end{Operator} +\section{Numeric Package} +\begin{Introduction}{Numeric Package} +The numeric package supplies algorithms based on approximation +techniques of numerical mathematics. The algorithms use +the \nameref{rounded} mode arithmetic of REDUCE, including +the variable precision feature which is exploited in some +algorithms in an adaptive manner in order to reach the +desired accuracy. +\end{Introduction} + +\begin{Type}{Interval} +Intervals are generally coded as lower bound and +upper bound connected by the operator \name{..}, usually +associated to a variable in an +equation. + +\begin{Syntax} + \meta{var} = \(\meta{low} .. \meta{high}\) +\end{Syntax} + +where \meta{var} is a \nameref{kernel} and \meta{low}, \meta{high} are +numbers or expression which evaluate to numbers with \meta{low}<=\meta{high}. + +\begin{Examples} + x= (2.5 .. 3.5) +\end{Examples} + +means that the variable x is taken in the range from 2.5 up to +3.5. + + +\end{Type} + +\begin{Concept}{numeric accuracy} +The keyword parameters \name{accuracy=a} and \name{iterations=i}, +where \name{a}and \name{i} must be positive integer numbers, control the +iterative algorithms: the iteration is continued until +the local error is below 10**{-a}; if that is impossible +within \name{i} steps, the iteration is terminated with an +error message. The values reached so far are then returned +as the result. +\end{Concept} + +\begin{Switch}{TRNUMERIC} +Normally the algorithms produce only a minimum of printed +output during their operation. In cases of an unsuccessful +or unexpected long operation a \name{trace of the iteration} can be +printed by setting \name{trnumeric} \name{on}. +\end{Switch} + +\begin{Operator}{num_min} +\index{minimum}\index{steepest descent}\index{Fletcher Reeves} +The Fletcher Reeves version of the \name{steepest descent} +algorithms is used to find the \name{minimum} of a +function of one or more variables. The +function must have continuous partial derivatives with respect to all +variables. The starting point of the search can be +specified; if not, random values are taken instead. +The steepest descent algorithms in general find only local +minima. + +\begin{Syntax} + + \name{num\_min}\(\meta{exp}, + \meta{var}[=\meta{val}] [,\meta{var}[=\meta{val}] ... + [,accuracy=\meta{a}] [,iterations=\meta{i}]\) + + +or + + \name{num\_min}\(exp, \{ + \meta{var}[=\meta{val}] [,\meta{var}[=\meta{val}] ...] \} + [,accuracy=\meta{a}] [,iterations=\meta{i}]\) +\end{Syntax} + +where \meta{exp} is a function expression, +\meta{var} are the variables in \meta{exp} and +\meta{val} are the (optional) start values. +For \meta{a} and \meta{i} see \nameref{numeric accuracy}. + +\name{Num\_min} tries to find the next local minimum along the descending +path starting at the given point. The result is a \nameref{list} +with the minimum function value as first element followed by a list +of \nameref{equation}\name{s}, where the variables are equated to the coordinates +of the result point. + + +\begin{Examples} +num_min(sin(x)+x/5, x)&\{4.9489585606,\{X=29.643767785\}\}\\ +num_min(sin(x)+x/5, x=0)&\{ - 1.3342267466,\{X= - 1.7721582671\}\} +\end{Examples} +\end{Operator} + +\begin{Operator}{num_solve} +\index{equation solving}\index{equation system}\index{Newton iteration} +\index{root} +An adaptively damped Newton iteration is used to find +an approximative root of a function (function vector) or the +solution of an \nameref{equation} (equation system). The expressions +must have continuous derivatives for all variables. +A starting point for the iteration can be given. If not given +random values are taken instead. When the number of +forms is not equal to the number of variables, the +Newton method cannot be applied. Then the minimum +of the sum of absolute squares is located instead. + +With \nameref{complex} on, solutions with imaginary parts can be +found, if either the expression(s) or the starting point +contain a nonzero imaginary part. + +\begin{Syntax} + \name{num\_solve}\(\meta{exp}, \meta{var}[=\meta{val}][,accuracy=\meta{a}][,iterations=\meta{i}]\) + +or + + \name{num\_solve}\(\{\meta{exp},...,\meta{exp}\}, \meta{var}[=\meta{val}],...,\meta{var}[=\meta{val}] + [,accuracy=\meta{a}][,iterations=\meta{i}]\) + +or + + \name{num\_solve}\(\{\meta{exp},...,\meta{exp}\}, \{\meta{var}[=\meta{val}],...,\meta{var}[=\meta{val}]\} + [,accuracy=\meta{a}][,iterations=\meta{i}]\) + +\end{Syntax} + + +where \meta{exp} are function expressions, + \meta{var} are the variables, + \meta{val} are optional start values. +For \meta{a} and \meta{i} see \nameref{numeric accuracy}. + +\name{num_solve} tries to find a zero/solution of the expression(s). +Result is a list of equations, where the variables are +equated to the coordinates of the result point. + +The \nameindex{Jacobian matrix} is stored as side effect the shared +variable \name{jacobian}. + + +\begin{Examples} +num_solve({sin x=cos y, x + y = 1},{x=1,y=2});& + \{X= - 1.8561957251,Y=2.856195584\}\\ +jacobian;& +\begin{multilineoutput}{5cm} + [COS(X) SIN(Y)] + [ ] + [ 1 1 ] +\end{multilineoutput} +\end{Examples} +\end{Operator} + +\begin{Operator}{num_int} +\index{integration} +For the numerical evaluation of univariate integrals +over a finite interval the following strategy is used: +If \nameref{int} finds a formal antiderivative + which is bounded in the integration interval, this + is evaluated and the end points and the difference + is returned. +Otherwise a \nameref{Chebyshev fit} is computed, + starting with order 20, eventually up to order 80. + If that is recognized as sufficiently convergent + it is used for computing the integral by directly + integrating the coefficient sequence. +If none of these methods is successful, an + adaptive multilevel quadrature algorithm is used. + +For multivariate integrals only the adaptive quadrature is used. +This algorithm tolerates isolated singularities. +The value \name{iterations} here limits the number of +local interval intersection levels. +\meta{a} is a measure for the relative total discretization +error (comparison of order 1 and order 2 approximations). + + +\begin{Syntax} + \name{num_int}\(\meta{exp},\meta{var}=\(\meta{l} .. \meta{u}\) + [,\meta{var}=\(\meta{l} .. \meta{u}\),...] + [,accuracy=\meta{a}][,iterations=\meta{i}]\) +\end{Syntax} + +where \meta{exp} is the function to be integrated, +\meta{var} are the integration variables, +\meta{l} are the lower bounds, +\meta{u} are the upper bounds. + +Result is the value of the integral. + +\begin{Examples} +num_int(sin x,x=(0 .. 3.1415926));& 2.0000010334 +\end{Examples} +\end{Operator} + +\begin{Operator}{num_odesolve} +\index{Runge-Kutta}\index{initial value problem}\index{ODE} +The \name{Runge-Kutta} method of order 3 finds an approximate graph for +the solution of real \name{ODE initial value problem}. + +\begin{Syntax} + \name{num_odesolve}\(\meta{exp},\meta{depvar}=\meta{start}, + \meta{indep}=\(\meta{from} .. \meta{to}\) + [,accuracy=\meta{a}][,iterations=\meta{i}]\) + +or + +\name{num_odesolve}\(\{\meta{exp},\meta{exp},...\}, + \{ \meta{depvar}=\meta{start},\meta{depvar}=\meta{start},...\} + \meta{indep}=\(\meta{from} .. \meta{to}\) + [,accuracy=\meta{a}][,iterations=\meta{i}]\) + +\end{Syntax} + +where +\meta{depvar} and \meta{start} specify the dependent variable(s) +and the starting point value (vector), +\meta{indep}, \meta{from} and \meta{to} specify the independent variable +and the integration interval (starting point and end point), +\meta{exp} are equations or expressions which +contain the first derivative of the independent variable +with respect to the dependent variable. + +The ODEs are converted to an explicit form, which then is +used for a Runge Kutta iteration over the given range. The +number of steps is controlled by the value of \meta{i} +(default: 20). If the steps are too coarse to reach the desired +accuracy in the neighborhood of the starting point, the number is +increased automatically. + +Result is a list of pairs, each representing a point of the +approximate solution of the ODE problem. + +\begin{Examples} +depend(y,x);\\ +num_odesolve(df(y,x)=y,y=1,x=(0 .. 1), iterations=5);& +\begin{multilineoutput} + \{\{0.0,1.0\},\{0.2,1.2214\},\{0.4,1.49181796\},\{0.6,1.8221064563\}, + \{0.8,2.2255208258\},\{1.0,2.7182511366\}\}\\ +\end{multilineoutput} +\end{Examples} + +In most cases you must declare the dependency relation +between the variables explicitly using \nameref{depend}; +otherwise the formal derivative might be converted to zero. + +The operator \nameref{solve} is used to convert the form into +an explicit ODE. If that process fails or if it has no unique result, +the evaluation is stopped with an error message. + +\end{Operator} + +\begin{Operator}{bounds} + +Upper and lower bounds of a real valued function over an +\nameref{interval} or a rectangular multivariate domain are computed +by the operator \name{bounds}. The algorithmic basis is the computation +with inequalities: starting from the interval(s) of the +variables, the bounds are propagated in the expression +using the rules for inequality computation. Some knowledge +about the behavior of special functions like ABS, SIN, COS, EXP, LOG, +fractional exponentials etc. is integrated and can be evaluated +if the operator \name{bounds} is called with rounded mode on +(otherwise only algebraic evaluation rules are available). + +If \name{bounds} finds a singularity within an interval, the evaluation +is stopped with an error message indicating the problem part +of the expression. + +\begin{Syntax} + \name{bounds}\(\meta{exp},\meta{var}=\(\meta{l} .. \meta{u}\) + [,\meta{var}=\(\meta{l} .. \meta{u}\) ...]\) + +or + + \name{bounds}\(\meta{exp},\{\meta{var}=\(\meta{l} .. \meta{u}\) + [,\meta{var}=\(\meta{l} .. \meta{u}\) ...]\}\) + + +\end{Syntax} + +where \meta{exp} is the function to be investigated, +\meta{var} are the variables of \meta{exp}, +\meta{l} and \meta{u} specify the area as set of \nameref{interval}\name{s}. + +\name{bounds} computes upper and lower bounds for the expression in the +given area. An \nameref{interval} is returned. + +\begin{Examples} +bounds(sin x,x=(1 .. 2));& -1 .. 1\\ +on rounded;\\ +bounds(sin x,x=(1 .. 2));& 0.84147098481 .. 1\\ +bounds(x**2+x,x=(-0.5 .. 0.5));& - 0.25 .. 0.75\\ +\end{Examples} +\end{Operator} + +\begin{Concept}{Chebyshev fit} +\index{approximation} +The operator family \name{Chebyshev\_...} implements approximation +and evaluation of functions by the Chebyshev method. +Let \name{T(n,a,b,x)} be the Chebyshev polynomial of order \name{n} +transformed to the interval \name{(a,b)}. +Then a function \name{f(x)} can be +approximated in \name{(a,b)} by a series + +\begin{verbatim} + for i := 0:n sum c(i)*T(i,a,b,x) +\end{verbatim} + +The operator \name{chebyshev\_fit} computes this approximation and +returns a list, which has as first element the sum expressed +as a polynomial and as second element the sequence +of Chebyshev coefficients. +\name{Chebyshev\_df} and \name{Chebyshev\_int} transform a Chebyshev +coefficient list into the coefficients of the corresponding +derivative or integral respectively. For evaluating a Chebyshev +approximation at a given point in the basic interval the +operator \name{Chebyshev\_eval} can be used. +\name{Chebyshev\_eval} is based on a recurrence relation which is +in general more stable than a direct evaluation of the +complete polynomial. + +\begin{Syntax} + \name{chebyshev\_fit}\(\meta{fcn},\meta{var}=\(\meta{lo} .. \meta{hi}\),\meta{n}\) + + \name{chebyshev\_eval}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\), + \meta{var}=\meta{pt}\) + + \name{chebyshev\_df}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\)\) + + \name{chebyshev\_int}\(\meta{coeffs},\meta{var}=\(\meta{lo} .. \meta{hi}\)\) +\end{Syntax} + +where \meta{fcn} is an algebraic expression (the target function), +\meta{var} is the variable of \meta{fcn}, +\meta{lo} and \meta{hi} are +numerical real values which describe an \nameref{interval} \meta{lo} < \meta{hi}, +the integer \meta{n} is the approximation order (set to 20 if missing), +\meta{pt} is a number in the interval and \meta{coeffs} is +a series of Chebyshev coefficients. + +\begin{Examples} + +on rounded;\\ + +w:=chebyshev_fit(sin x/x,x=(1 .. 3),5);& +\begin{multilineoutput}{6cm} +w := \{0.03824*x^3 - 0.2398*x^2 + 0.06514*x + 0.9778, + \{0.8991,-0.4066,-0.005198,0.009464,-0.00009511\}\} +\end{multilineoutput}\\ +chebyshev_eval(second w, x=(1 .. 3), x=2.1);& 0.4111\\ +\end{Examples} +\end{Concept} + +\begin{Operator}{num_fit} +\index{approximation}\index{least squares} +The operator \name{num_fit} finds for a set of +points the linear combination of a given set of +functions (function basis) which approximates the +points best under the objective of the \name{least squares} +criterion (minimum of the sum of the squares of the deviation). +The solution is found as zero of the +gradient vector of the sum of squared errors. + + +\begin{Syntax} + \name{num_fit}\(\meta{vals},\meta{basis},\meta{var}=\meta{pts}\) +\end{Syntax} + +where \meta{vals} is a list of numeric values, +\meta{var} is a variable used for the approximation, +\meta{pts} is a list of coordinate values which correspond to +\meta{var}, +\meta{basis} is a set of functions varying in \name{var} which is used + for the approximation. + + +The result is a list containing as first element the +function which approximates the given values, and as +second element a list of coefficients which were used +to build this function from the basis. + +\begin{Examples} + +pts:=for i:=1 step 1 until 5 collect i$\\ +vals:=for i:=1 step 1 until 5 collect\\ + for j:=1:i product j$\\ +num_fit(vals,{1,x,x**2},x=pts);& +\begin{multilineoutput}{6cm} + \{14.571428571*X^2 - 61.428571429*X + 54.6,\{54.6, + - 61.428571429,14.571428571\}\} +\end{multilineoutput} + +\end{Examples} + +\end{Operator} Index: r36/help/PK-ROOTS.TEX ================================================================== --- r36/help/PK-ROOTS.TEX +++ r36/help/PK-ROOTS.TEX @@ -1,179 +1,179 @@ -\section{Roots Package} -\begin{Introduction}{Roots Package} -\index{roots}\index{polynomial} -The root finding package is designed so that it can -be used to find some or all of the roots of univariate -polynomials with real or complex coefficients, to the accuracy -specified by the user. - -Not all operators of \name{roots package} are described here. For using -the operators - -\nameindex{isolater} (intervals isolating real roots) - -\nameindex{rlrootno} (number of real roots in an interval) - -\nameindex{rootsat-prec} (roots at system precision) - -\nameindex{rootval} (result in equation form) - -\nameindex{firstroot} (computing only one root) - -\nameindex{getroot} (selecting roots from a collection) - -please consult the full documentation of the package. - -\end{Introduction} - -\begin{Operator}{MKPOLY} -\index{polynomial}\index{roots}\index{interpolation} -Given a roots list as returned by \nameref{roots}, -the operator \name{mkpoly} constructs a -polynomial which has these numbers as roots. -\begin{Syntax} -\name{mkpoly} \meta{rl} -\end{Syntax} -where \meta{rl} is a \nameref{list} with equations, which -all have the same \nameref{kernel} on their left-hand sides -and numbers as right-hand sides. - -\begin{Examples} -mkpoly{x=1,x=-2,x=i,x=-i};& -x**4 + x**3 - x**2 + x - 2\\ -\end{Examples} - -Note that this polynomial is unique only up to a numeric -factor. -\end{Operator} - - -\begin{Operator}{NEARESTROOT} -\index{roots}\index{solve} -The operator \name{nearestroot} finds one root of a polynomial -with an iteration using a given starting point. - -\begin{Syntax} -\name{nearestroot}\(\meta{p}\,\meta{pt}\) -\end{Syntax} - -where \meta{p} is a univariate polynomial -and \meta{pt} is a number. - -\begin{Examples} -nearestroot(x^2+2,2);&\{x=1.41421*i\}\\ -\end{Examples} -The minimal accuracy of the result values is controlled by -\nameref{rootacc}. -\end{Operator} - -\begin{Operator}{REALROOTS} -\index{roots}\index{solve} -The operator \name{realroots} finds that real roots of a polynomial -to an accuracy that is sufficient to separate them and which is -a minimum of 6 decimal places. - -\begin{Syntax} -\name{realroots}\(\meta{p}\) or \\ -\name{realroots}\(\meta{p}\,\meta{from},\meta{to}\) -\end{Syntax} - -where \meta{p} is a univariate polynomial. -The optional parameters \meta{from} and \meta{to} classify -an interval: if given, exactly the real roots in this -interval will be returned. \meta{from} and \meta{to} -can also take the values \name{infinity} or \name{-infinity}. -If omitted all real roots will be returned. -Result is a \nameref{list} -of equations which represent the roots of the polynomial at the -given accuracy. - -\begin{Examples} -realroots(x^5-2);&\{x=1.1487\}\\ -realroots(x^3-104*x^2+403*x-300,2,infinity);&\{x=3.0,x=100.0\}\\ -realroots(x^3-104*x^2+403*x-300,-infinity,2);&\{x=1\}\\ -\end{Examples} -The minimal accuracy of the result values is controlled by -\nameref{rootacc}. -\end{Operator} - - -\begin{Operator}{ROOTACC} -\index{roots}\index{accuracy} -The operator \name{rootacc} allows you to set the accuracy -up to which the roots package computes its results. -\begin{Syntax} -\name{rootacc}\(\meta{n}\) -\end{Syntax} -Here \meta{n} is an integer value. The internal accuracy of -the \name{roots} package is adjusted to a value of -\name{max(6,n)}. The default value is \name{6}. -\end{Operator} - -\begin{Operator}{ROOTS} -\index{roots}\index{solve}\index{polynomial} -The operator \name{roots} -is the main top level function of the roots package. -It will find all roots, real and complex, of the polynomial p -to an accuracy that is sufficient to separate them and which is -a minimum of 6 decimal places. - -\begin{Syntax} -\name{roots}\(\meta{p}\) -\end{Syntax} - -where \meta{p} is a univariate polynomial. Result is a \nameref{list} -of equations which represent the roots of the polynomial at the -given accuracy. In addition, \name{roots} stores -separate lists of real roots and complex roots in the global -variables \nameref{rootsreal} and \nameref{rootscomplex}. - -\begin{Examples} -roots(x^5-2);&\begin{multilineoutput}{3cm} -\{x=-0.929316 + 0.675188*i, - x=-0.929316 - 0.675188*i, - x=0.354967 + 1.09248*i, - x=0.354967 - 1.09248*i, - x=1.1487\} -\end{multilineoutput}\\ -\end{Examples} -The minimal accuracy of the result values is controlled by -\nameref{rootacc}. -\end{Operator} - -\begin{Operator}{ROOT\_VAL} -\index{roots}\index{solve}\index{polynomial} -The operator \name{root\_val} computes the roots of a -univariate polynomial at system precision -(or greater if required for root separation) and presents -its result as a list of numbers. -\begin{Syntax} -\name{roots}\(\meta{p}\) -\end{Syntax} - -where \meta{p} is a univariate polynomial. - -\begin{Examples} -root_val(x^5-2);&\begin{multilineoutput}{3cm} -\{-0.929316490603 + 0.6751879524*i, - -0.929316490603 - 0.6751879524*i, - 0.354967313105 + 1.09247705578*i, - 0.354967313105 - 1.09247705578*i, - 1.148698355\} -\end{multilineoutput}\\ -\end{Examples} -\end{Operator} - -\begin{Variable}{ROOTSCOMPLEX} -\index{roots}\index{complex} -When the operator \nameref{roots} is called the complex -roots are collected in the global variable \name{rootscomplex} -as \nameref{list}. -\end{Variable} - - -\begin{Variable}{ROOTSREAL} -\index{roots}\index{complex} -When the operator \nameref{roots} is called the real -roots are collected in the global variable \name{rootreal} -as \nameref{list}. -\end{Variable} +\section{Roots Package} +\begin{Introduction}{Roots Package} +\index{roots}\index{polynomial} +The root finding package is designed so that it can +be used to find some or all of the roots of univariate +polynomials with real or complex coefficients, to the accuracy +specified by the user. + +Not all operators of \name{roots package} are described here. For using +the operators + +\nameindex{isolater} (intervals isolating real roots) + +\nameindex{rlrootno} (number of real roots in an interval) + +\nameindex{rootsat-prec} (roots at system precision) + +\nameindex{rootval} (result in equation form) + +\nameindex{firstroot} (computing only one root) + +\nameindex{getroot} (selecting roots from a collection) + +please consult the full documentation of the package. + +\end{Introduction} + +\begin{Operator}{MKPOLY} +\index{polynomial}\index{roots}\index{interpolation} +Given a roots list as returned by \nameref{roots}, +the operator \name{mkpoly} constructs a +polynomial which has these numbers as roots. +\begin{Syntax} +\name{mkpoly} \meta{rl} +\end{Syntax} +where \meta{rl} is a \nameref{list} with equations, which +all have the same \nameref{kernel} on their left-hand sides +and numbers as right-hand sides. + +\begin{Examples} +mkpoly{x=1,x=-2,x=i,x=-i};& +x**4 + x**3 - x**2 + x - 2\\ +\end{Examples} + +Note that this polynomial is unique only up to a numeric +factor. +\end{Operator} + + +\begin{Operator}{NEARESTROOT} +\index{roots}\index{solve} +The operator \name{nearestroot} finds one root of a polynomial +with an iteration using a given starting point. + +\begin{Syntax} +\name{nearestroot}\(\meta{p}\,\meta{pt}\) +\end{Syntax} + +where \meta{p} is a univariate polynomial +and \meta{pt} is a number. + +\begin{Examples} +nearestroot(x^2+2,2);&\{x=1.41421*i\}\\ +\end{Examples} +The minimal accuracy of the result values is controlled by +\nameref{rootacc}. +\end{Operator} + +\begin{Operator}{REALROOTS} +\index{roots}\index{solve} +The operator \name{realroots} finds that real roots of a polynomial +to an accuracy that is sufficient to separate them and which is +a minimum of 6 decimal places. + +\begin{Syntax} +\name{realroots}\(\meta{p}\) or \\ +\name{realroots}\(\meta{p}\,\meta{from},\meta{to}\) +\end{Syntax} + +where \meta{p} is a univariate polynomial. +The optional parameters \meta{from} and \meta{to} classify +an interval: if given, exactly the real roots in this +interval will be returned. \meta{from} and \meta{to} +can also take the values \name{infinity} or \name{-infinity}. +If omitted all real roots will be returned. +Result is a \nameref{list} +of equations which represent the roots of the polynomial at the +given accuracy. + +\begin{Examples} +realroots(x^5-2);&\{x=1.1487\}\\ +realroots(x^3-104*x^2+403*x-300,2,infinity);&\{x=3.0,x=100.0\}\\ +realroots(x^3-104*x^2+403*x-300,-infinity,2);&\{x=1\}\\ +\end{Examples} +The minimal accuracy of the result values is controlled by +\nameref{rootacc}. +\end{Operator} + + +\begin{Operator}{ROOTACC} +\index{roots}\index{accuracy} +The operator \name{rootacc} allows you to set the accuracy +up to which the roots package computes its results. +\begin{Syntax} +\name{rootacc}\(\meta{n}\) +\end{Syntax} +Here \meta{n} is an integer value. The internal accuracy of +the \name{roots} package is adjusted to a value of +\name{max(6,n)}. The default value is \name{6}. +\end{Operator} + +\begin{Operator}{ROOTS} +\index{roots}\index{solve}\index{polynomial} +The operator \name{roots} +is the main top level function of the roots package. +It will find all roots, real and complex, of the polynomial p +to an accuracy that is sufficient to separate them and which is +a minimum of 6 decimal places. + +\begin{Syntax} +\name{roots}\(\meta{p}\) +\end{Syntax} + +where \meta{p} is a univariate polynomial. Result is a \nameref{list} +of equations which represent the roots of the polynomial at the +given accuracy. In addition, \name{roots} stores +separate lists of real roots and complex roots in the global +variables \nameref{rootsreal} and \nameref{rootscomplex}. + +\begin{Examples} +roots(x^5-2);&\begin{multilineoutput}{3cm} +\{x=-0.929316 + 0.675188*i, + x=-0.929316 - 0.675188*i, + x=0.354967 + 1.09248*i, + x=0.354967 - 1.09248*i, + x=1.1487\} +\end{multilineoutput}\\ +\end{Examples} +The minimal accuracy of the result values is controlled by +\nameref{rootacc}. +\end{Operator} + +\begin{Operator}{ROOT\_VAL} +\index{roots}\index{solve}\index{polynomial} +The operator \name{root\_val} computes the roots of a +univariate polynomial at system precision +(or greater if required for root separation) and presents +its result as a list of numbers. +\begin{Syntax} +\name{roots}\(\meta{p}\) +\end{Syntax} + +where \meta{p} is a univariate polynomial. + +\begin{Examples} +root_val(x^5-2);&\begin{multilineoutput}{3cm} +\{-0.929316490603 + 0.6751879524*i, + -0.929316490603 - 0.6751879524*i, + 0.354967313105 + 1.09247705578*i, + 0.354967313105 - 1.09247705578*i, + 1.148698355\} +\end{multilineoutput}\\ +\end{Examples} +\end{Operator} + +\begin{Variable}{ROOTSCOMPLEX} +\index{roots}\index{complex} +When the operator \nameref{roots} is called the complex +roots are collected in the global variable \name{rootscomplex} +as \nameref{list}. +\end{Variable} + + +\begin{Variable}{ROOTSREAL} +\index{roots}\index{complex} +When the operator \nameref{roots} is called the real +roots are collected in the global variable \name{rootreal} +as \nameref{list}. +\end{Variable} Index: r36/help/README ================================================================== --- r36/help/README +++ r36/help/README @@ -1,53 +1,53 @@ -The following are support files, not part of the reference manual - - guide.tex - help.tex - mktable % produces list of all keywords. - redref.tex - rhelp.tex - -The following are not normally included in the general reference manual - - deferred.tex - obsolete.tex - rdebug.tex - sl.tex - symbolic.tex - -The following are support for building the reference manual - -array.sty -mkhelp -redhelp.tex % Used to build paper copy of reference manual -redindex.sty -xredhelp.tex % Copy of redhelp.tex (so you can do rm redhelp.* - % after building reference manual - - -The following are reference manual text - -algebra.tex -arith.tex -boolean.tex -command.tex -concept.tex -declare.tex -elemfn.tex -hephys.tex -intro.tex -io.tex -linalg.tex -matrix.tex -normform.tex -outmode.tex -pk-gplot.tex -pk-groeb.tex -pk-misc.tex -pk-numer.tex -pk-roots.tex -pk-specf.tex -switch.tex -symbolic.tex -syntax.tex -taylor.tex -variable.tex +The following are support files, not part of the reference manual + + guide.tex + help.tex + mktable % produces list of all keywords. + redref.tex + rhelp.tex + +The following are not normally included in the general reference manual + + deferred.tex + obsolete.tex + rdebug.tex + sl.tex + symbolic.tex + +The following are support for building the reference manual + +array.sty +mkhelp +redhelp.tex % Used to build paper copy of reference manual +redindex.sty +xredhelp.tex % Copy of redhelp.tex (so you can do rm redhelp.* + % after building reference manual + + +The following are reference manual text + +algebra.tex +arith.tex +boolean.tex +command.tex +concept.tex +declare.tex +elemfn.tex +hephys.tex +intro.tex +io.tex +linalg.tex +matrix.tex +normform.tex +outmode.tex +pk-gplot.tex +pk-groeb.tex +pk-misc.tex +pk-numer.tex +pk-roots.tex +pk-specf.tex +switch.tex +symbolic.tex +syntax.tex +taylor.tex +variable.tex Index: r36/help/REDHELP.TEX ================================================================== --- r36/help/REDHELP.TEX +++ r36/help/REDHELP.TEX @@ -1,36 +1,36 @@ -\documentstyle[redindex]{article} - -\makeindex - -\begin{document} - -%\setcounter{page}{63} - -%\tracingall - -\input{intro} -\input{concept} -\input{variable} -\input{syntax} -\input{arith} -\input{boolean} -\input{command} -\input{algebra} -\input{declare} -\input{io} -\input{elemfn} -\input{switch} -\input{matrix} -\input{pk-groeb} -\input{hephys} -\input{pk-numer} -\input{pk-roots} -\input{pk-specf} -\input{taylor} -\input{pk-gplot} -\input{linalg} -\input{normform} -\input{pk-misc} -%\input{symbolic} -\input{outmode} -\end{document} +\documentstyle[redindex]{article} + +\makeindex + +\begin{document} + +%\setcounter{page}{63} + +%\tracingall + +\input{intro} +\input{concept} +\input{variable} +\input{syntax} +\input{arith} +\input{boolean} +\input{command} +\input{algebra} +\input{declare} +\input{io} +\input{elemfn} +\input{switch} +\input{matrix} +\input{pk-groeb} +\input{hephys} +\input{pk-numer} +\input{pk-roots} +\input{pk-specf} +\input{taylor} +\input{pk-gplot} +\input{linalg} +\input{normform} +\input{pk-misc} +%\input{symbolic} +\input{outmode} +\end{document} Index: r36/help/REDINDEX.STY ================================================================== --- r36/help/REDINDEX.STY +++ r36/help/REDINDEX.STY @@ -1,410 +1,410 @@ -\ifx\ps@REDUCEreference\undefined - \else\endinput\fi - -\typeout{Document style option `redindex' version 1.24 -- RmS 1994/01/20} - -\ifx\COMPATNOTE\undefined - \@@input reduce.sty\relax -\fi - -\ifx\extrarowheight\undefined - \@@input array.sty\relax -\fi - -%\newcommand{\REDUCE}{REDUCE} - -\if@twoside\else\ds@twoside\fi - -\def\ps@REDUCEreference{\let\@evenhead\@empty\let\@oddhead\@empty - \def\@oddfoot{\rm \hfil REDUCE Reference\ \ \thepage}% - \def\@evenfoot{\rm \thepage\ \ REDUCE Reference\hfil}} - -\newcommand{\indexentry}[1]{\newpage - \markboth{#1}{#1}\section*{#1}} - -\def\in@#1#2{% - \def\in@@##1#1##2##3\in@@{% - \ifx\in@##2\in@false\else\in@true\fi}% - \in@@#2#1\in@\in@@} -\newif\ifin@ - -\newtoks\double@list -\double@list={} -\def\add@to@double@list#1{\double@list=\expandafter{\the\double@list#1\relax}} -\def\check@double@list#1{% - \def\@tempa{\in@{#1}}% - \expandafter\@tempa\expandafter{\the\double@list}} - -\catcode`\_=12 -\def\other@underscore{_} -\catcode`\_=\active -\def_{\ifmmode\expandafter\sb\else\_\fi} -\def\redindex@sanitize{\@sanitize\catcode`\ =10\relax - \catcode`\\=0\relax - \catcode`\{=1\relax - \catcode`\}=2\relax - \catcode`\_=\active} - -\def\check@multiple@label#1,#2,#3{% #1 is name, #2 is type, #3 is value - \@ifundefined{r@#1}{\newlabel@{#1}{#3}}{% - \typeout{Double found: #1, list: \the\double@list}% - \check@double@list{#1}\ifin@\else\global\add@to@double@list{#1}\fi}} - - -\let\newlabel@=\newlabel -\def\newlabel{\begingroup - \redindex@sanitize - \newlabel@@ -} - -\def\newlabel@@#1#2{%\tracingall -% \begingroup - \let_=\other@underscore - \newlabel@{#1}{#2}% - \in@,{#1}\ifin@\check@multiple@label#1,{#2}\fi - \endgroup} - -\let\enddocument@=\enddocument -\def\enddocument{\let_=\other@underscore - \immediate\write\@mainaux{\string\add@to@double@list{\the\double@list}}% - \enddocument@} - -\def\enddocument{\@checkend{document}\clearpage\begingroup -\if@filesw - \let_=\other@underscore - \immediate\write\@mainaux{\string\add@to@double@list{\the\double@list}}% - \immediate\closeout\@mainaux -\def\global\@namedef##1##2{}\def\newlabel{\@testdef r}% -\def\bibcite{\@testdef b}\@tempswafalse \makeatletter -\redindex@sanitize\input \jobname.aux -\if@tempswa \@@warning{Label(s) may have changed. Rerun to get -cross-references right}\fi\fi\endgroup\deadcycles\z@\@@end} - -\def\@testdef #1#2#3{\def\@tempa{#3}\expandafter \ifx \csname #1@#2\endcsname - \@tempa \else - \typeout{Testing #2 failed: old: \csname #1@#2\endcsname <-> new: #3} - \@tempswatrue \fi} - -\newcount\newitem@penalty -\newskip\newitem@preskip -\newskip\newitem@postskip -\newskip\newitem@headsep - -%\def\newitem#1#2{% #1 is type, #2 is name -\def\newitem#1[#2]#3{% #1 is type, #2 is ref key, #3 is name - \endgroup - \ifvmode\else\par\fi - \addpenalty\newitem@penalty - \addvspace\newitem@postskip - \hrule - \nobreak - \vskip \newitem@preskip - \hbox to\hsize{\LARGE\bf\sf \uppercase{#3}\hfil #1}% - \nobreak - \vskip \newitem@headsep - \begingroup - \let_=\other@underscore - \index{#3}\index{#1!#3}% - \def\_{_}\label{#2,#1}\nobreak - \endgroup} - -\newitem@penalty=\@beginparpenalty -\newitem@postskip = 20pt plus 5pt minus 5pt -\newitem@preskip = 10pt -\newitem@headsep = 5pt - -\parskip = 5pt plus 2pt -\parindent = 0pt - - -\def\newitemEnv#1{% - \expandafter\edef\csname#1\endcsname{% - \begingroup\noexpand\redindex@sanitize\csname#1@\endcsname}% - \@namedef{#1@}{\@dblarg{\newitem{#1}}}% - \@namedef{end#1}{}} - -\newitemEnv{Command} -\newitemEnv{Operator} -\newitemEnv{Function} -\newitemEnv{Switch} -\newitemEnv{Variable} -\newitemEnv{Declaration} -\newitemEnv{Package} -\newitemEnv{Concept} -\newitemEnv{Constant} -\newitemEnv{Type} -\newitemEnv{info} -\newitemEnv{Introduction} - -\newskip\itemsec@sep -\newcount\itemsec@penalty - -\itemsec@penalty=\@beginparpenalty -\itemsec@sep=5pt - -\def\begin@itemsection#1{\par\everypar={}% - \addvspace\itemsec@sep - \addpenalty\itemsec@penalty - \hbox{\large\bf\sf #1}\nobreak} - -\def\end@itemsection{\par} - -\def\Comments{\begin@itemsection{Comments}} -\let\endComments\end@itemsection - -\begingroup - \catcode`\^=\active \catcode`\&=\active \catcode`\_=\active - \def\x{\def\setup@special@chars{\catcode`\^=\active \let^=\special@uparrow - \catcode`\&=\active \let&=\special@ampersand}% - \def\protectspecialchars{\def^{\char`\^}\def_{\char`\_}}% - \def\normalspecialchars{\let^=\sp\let_=\sb}% - \def\activespecialchars{\let^=\special@uparrow}} -\expandafter\endgroup\x - -\let\begin@=\begin -\let\end@=\end - -\def\@ifstar#1#2{\def\@tempa{#1}\def\@tempb{#2}\futurelet - \@tempc\@if@star@} - -\def\@if@star@{\ifx \@tempc*\def\@tempd*{\@tempa}\else\let\@tempd\@tempb\fi\@tempd} - -\def\Examples{\begin@itemsection{Examples}% - \setup@special@chars\protectspecialchars%\tracingall - \def\{{{\tt\char`\{}}% - \def\}{{\tt\char`\}}}% - \def\arraystretch{1.5}% - \extrarowheight=1mm - \def\end{% - \ifnum\catcode`\{=12\relax \expandafter \special@ampersand\fi\end@}% - \let \protect \relax - \lineskip \z@ - \baselineskip \z@ - \frenchspacing - \m@th - \def\\{{\ifnum 0=`}\fi - \@ifstar {\@xarraycr\noalign{\penalty\@M}} \@xarraycr} - \let\par=\@empty - \setbox \@arstrutbox \hbox{\vrule - \@height \arraystretch \ht \strutbox - \@depth \arraystretch \dp \strutbox - \@width \z@}% - \ialign\bgroup\@arstrut - \global\@startnewrowfalse - \catcode`\{=12\relax - \catcode`\}=12\relax - \catcode`\%=12\relax - \catcode`\$=12\relax - \catcode`\~=12\relax - \setbox0=\hbox\bgroup\protect\tt##\unskip\hfil\egroup\checkcolwidth - &$\quad\protect\Rightarrow\quad$% - \global\setbox0=\hbox\bgroup\activespecialchars##\egroup\checkcolwidtho\cr -} - -\def\endExamples{\crcr\egroup\end@itemsection} - -%\def\Examples{\begin@itemsection{Examples}% -% \setup@special@chars\protectspecialchars%\tracingall -% \def\{{{\tt\char`\{}}% -% \def\}{{\tt\char`\}}}% -% \def\arraystretch{1.5}% -% \extrarowheight=1mm -% \def\end{% -% \ifnum\catcode`\{=12\relax \expandafter \special@ampersand\fi\end@}% -% \begin{tabular}[b]{>{%\protectspecialchars -% \global\@startnewrowfalse -% \catcode`\{=12\relax -% \catcode`\}=12\relax -% \catcode`\%=12\relax -% \catcode`\$=12\relax -% \setbox0=\hbox\bgroup\protect\tt}l<{\egroup\checkcolwidth}% -% >{$\quad\protect\Rightarrow\quad$% -% \global\setbox0=\hbox\bgroup\activespecialchars}l% -% <{\egroup\checkcolwidtho}}} -%\def\endExamples{\end{tabular}\end@itemsection} - -\def\explanationi#1{\multicolumn{2}{p{0.95\textwidth}}{% - \normalspecialchars \em#1}} -\let\explanation=\explanationi -\def\explanationo#1{\parbox[t]{0.95\MaxOutputWidth}{\em#1}} - -\def\start@new@row@for@output{% - \multicolumn{2}{@{\protect\DoOutputIndent}l}{\box0}} - -\def\DoOutputIndent{ - \dimen@=\textwidth - \advance\dimen@ -\wd\z@ - \ifdim\dimen@>\OutputIndent \dimen@=\OutputIndent - \else\ifdim\dimen@<\z@ \dimen@=\OutputIndent\fi\fi - \hspace{\dimen@}} - -\newdimen\OutputIndent \OutputIndent=10mm - -\begingroup \catcode `|=0 \catcode `[= 1 -\catcode`]=2 \catcode `\{=12 \catcode `\}=12 -\catcode`\\=12 |gdef|@bixample#1\end{Bigexample}[#1|end[Bigexample]] -|endgroup - -\def\Bigexample{\begin@itemsection{Example}% - \@verbatim \frenchspacing\@vobeyspaces \@bixample} -\def\endBigexample{\endtrivlist\end@itemsection} - -\def\Related{\begin@itemsection{Related information}\begin{description}} -\def\endRelated{\end{description}} - -\newif\if@startnewrow \@startnewrowfalse -\newif\if@startneworow \@startneworowfalse -\def\special@uparrow#1{\vbox{\vskip2\p@ - \hbox{\raise.8\normalbaselineskip\hbox{#1}}}} -\def\special@ampersand{&\if@startnewrow\expandafter\startnewrow\fi\tt} - -\def\startnewrow{\omit\\&\global\@startnewrowfalse} - -\newdimen\maxexamplecolwidth -\maxexamplecolwidth = 5cm - -\def\checkcolwidth{% - \ifdim\wd0>\maxexamplecolwidth - \hbox to\maxexamplecolwidth{\unhbox0\hss}% - \hskip-25pt\null - \global\@startnewrowtrue - \else \unhbox0 \fi -} - -\def\checkcolwidtho{% - \ifdim\wd0>\MaxOutputWidth - \global\everycr={\start@new@row@for@output - \global\everycr={}\cr}% -% \global\@startneworowtrue - \else \unhbox0 \fi -} - - -\def\multilineinput{\catcode`\{=1 \catcode`\}=2 - \begin{minipage}[b]{\maxexamplecolwidth}\@vobeyspaces\obeylines} -\def\endmultilineinput{\end{minipage}} - -\def\multilineoutput#1{\begin{minipage}[t]{#1}\@vobeyspaces\obeylines - \baselineskip =1.5\baselineskip} -\def\endmultilineoutput{\end{minipage}} - -\newdimen\MaxOutputWidth \MaxOutputWidth=7cm -\def\multilineoutput#1{% - \vtop\bgroup\@parboxrestore - \lineskip \baselineskip - \@tempswafalse - \def\par{\if@tempswa\egroup - \ifdim\wd0>\z@\box0\fi - \setbox0=\hbox\bgroup\fi - \@tempswatrue} - \@vobeyspaces\obeylines - \setbox0=\hbox\bgroup} - -\def\endmultilineoutput{\egroup\ifdim\wd0>\z@\box0\fi \egroup} - -\def\multilineinput{% - \vbox\bgroup\@parboxrestore - \def\end{\catcode`\{=1 \catcode`\}=2 \end@}% - \@tempswafalse - \def\par{\if@tempswa\egroup - \ifdim\wd0>\z@\box0\fi - \setbox0=\hbox\bgroup\fi - \@tempswatrue} - \@vobeyspaces\obeylines - \addvspace{.8\baselineskip}% - \setbox0=\hbox\bgroup} - -\let\endmultilineinput=\endmultilineoutput - -\def\privateshowbox{\showboxbreadth\maxdimen\showboxdepth\maxdimen\showbox} - -\def\rfrac#1#2{\begingroup - \lineskip2pt \baselineskip \z@ - \setbox0=\hbox{\tt#1}% - \setbox1=\hbox{\tt#2}% - \setbox2=\hbox{\tt-}% - \ifdim \wd0>\wd1 \dimen@=\wd0 \else \dimen@=\wd1 \fi - \advance \dimen@ by2\wd2\relax - \setbox3=\vtop{\hbox to\dimen@{\hss\unhcopy0\hss}% - \hbox to\dimen@{\leaders\copy2\hfill}% - \hbox to\dimen@{\hss\unhcopy1\hss}}% - \dimen@=\dp0 \advance\dimen@ by\ht2 \advance\dimen@ by\lineskip - \@tempdima=\ht3 \advance \@tempdima by\dimen@ \ht3=\@tempdima - \@tempdima=\dp3 \advance \@tempdima by-\dimen@ \dp3=\@tempdima -% \privateshowbox3 - \box3 - \endgroup} - -\def\def@protected#1#2{% - \expandafter\edef\csname#1\endcsname{\begingroup\noexpand\redindex@sanitize - \catcode32=10 - \csname#1@\endcsname}% - \@namedef{#1@}##1{\endgroup#2}} - -\def@protected{name}{\mbox{\tt#1}} -%\let\keyw=\name -%\let\operator=\name -\def@protected{nameindex}{\name{#1}\index{#1}\label{#1}} -\def@protected{hyperref}{#1} -%\def@protected{nameref}{\name{#1}, p.~\pageref{#1}} -\def@protected{nameref}{\name{#1}} -\def@protected{see}{(see \hyperref@{#1})} -\def@protected{key}{\fbox{\sf #1}} -\def@protected{arg}{\mbox{\it #1}} - -\newdimen \Syntaxindent \Syntaxindent=2mm -\def\Syntax{\large - \list{}{\leftmargin\Syntaxindent\def\({$(}\def\){)$}% - \mathcode`\ =32768}\item[]} -\def\endSyntax{\endlist} -\def\repeated{$+$} -\def\optional{\relax\ifmmode\ast\else$\ast$\fi} -%\def\meta#1{\mbox{\it#1}} -\def\meta{\begingroup\catcode`\_=\active\meta@} -\def\meta@#1{\ifmmode\mbox\fi{\it#1\/}\endgroup} - -\def\alternative{$\displaystyle - \left\{\begin{tabular}{l}} -\def\endalternative{\end{tabular}\right\}$} - -\def\section{\@startsection {section}{1}{\z@}{-3.5ex plus-1ex minus - -.2ex}{2.3ex plus.2ex}{\reset@font\LARGE\bf}} -\def\subsection{\@startsection{subsection}{2}{\z@}{-3.25ex plus-1ex - minus-.2ex}{1.5ex plus.2ex}{\reset@font\Large\bf}} -\def\subsubsection{\@startsection{subsubsection}{3}{\z@}{-3.25ex plus - -1ex minus-.2ex}{1.5ex plus.2ex}{\reset@font\large\bf}} - -%%%% -%%%% error message file -%%%% - -\def\tableoferrormessages{\@restonecolfalse - \if@twocolumn\@restonecoltrue\onecolumn\fi - \chapter*{\contentsname - \@mkboth{\uppercase{\contentsname}}{\uppercase{\contentsname}}}% - \@starttoc{emg}\if@restonecol\twocolumn\fi} - -\def\ErrorMessage#1{% - \addcontentsline{emg}{#1}} - -%%%% conditionals - -\def\IFTEX#1#2{#1} - -\long\def\INFO#1\end#2{\def\@tempa{#2}\def\@tempb{INFO}% - \ifx\@tempa\@tempb\else\errmessage{\string\end{#2} not allowed - inside INFO environment.}\@eha\fi - \end{INFO}} -\def\endINFO{\global\@ignoretrue} - -\def\TEX{} -\def\endTEX{\global\@ignoretrue} - - -\@ifundefined{reset@font}{\let\reset@font\@empty}{} - -\pagestyle{REDUCEreference} - -\endinput - - +\ifx\ps@REDUCEreference\undefined + \else\endinput\fi + +\typeout{Document style option `redindex' version 1.24 -- RmS 1994/01/20} + +\ifx\COMPATNOTE\undefined + \@@input reduce.sty\relax +\fi + +\ifx\extrarowheight\undefined + \@@input array.sty\relax +\fi + +%\newcommand{\REDUCE}{REDUCE} + +\if@twoside\else\ds@twoside\fi + +\def\ps@REDUCEreference{\let\@evenhead\@empty\let\@oddhead\@empty + \def\@oddfoot{\rm \hfil REDUCE Reference\ \ \thepage}% + \def\@evenfoot{\rm \thepage\ \ REDUCE Reference\hfil}} + +\newcommand{\indexentry}[1]{\newpage + \markboth{#1}{#1}\section*{#1}} + +\def\in@#1#2{% + \def\in@@##1#1##2##3\in@@{% + \ifx\in@##2\in@false\else\in@true\fi}% + \in@@#2#1\in@\in@@} +\newif\ifin@ + +\newtoks\double@list +\double@list={} +\def\add@to@double@list#1{\double@list=\expandafter{\the\double@list#1\relax}} +\def\check@double@list#1{% + \def\@tempa{\in@{#1}}% + \expandafter\@tempa\expandafter{\the\double@list}} + +\catcode`\_=12 +\def\other@underscore{_} +\catcode`\_=\active +\def_{\ifmmode\expandafter\sb\else\_\fi} +\def\redindex@sanitize{\@sanitize\catcode`\ =10\relax + \catcode`\\=0\relax + \catcode`\{=1\relax + \catcode`\}=2\relax + \catcode`\_=\active} + +\def\check@multiple@label#1,#2,#3{% #1 is name, #2 is type, #3 is value + \@ifundefined{r@#1}{\newlabel@{#1}{#3}}{% + \typeout{Double found: #1, list: \the\double@list}% + \check@double@list{#1}\ifin@\else\global\add@to@double@list{#1}\fi}} + + +\let\newlabel@=\newlabel +\def\newlabel{\begingroup + \redindex@sanitize + \newlabel@@ +} + +\def\newlabel@@#1#2{%\tracingall +% \begingroup + \let_=\other@underscore + \newlabel@{#1}{#2}% + \in@,{#1}\ifin@\check@multiple@label#1,{#2}\fi + \endgroup} + +\let\enddocument@=\enddocument +\def\enddocument{\let_=\other@underscore + \immediate\write\@mainaux{\string\add@to@double@list{\the\double@list}}% + \enddocument@} + +\def\enddocument{\@checkend{document}\clearpage\begingroup +\if@filesw + \let_=\other@underscore + \immediate\write\@mainaux{\string\add@to@double@list{\the\double@list}}% + \immediate\closeout\@mainaux +\def\global\@namedef##1##2{}\def\newlabel{\@testdef r}% +\def\bibcite{\@testdef b}\@tempswafalse \makeatletter +\redindex@sanitize\input \jobname.aux +\if@tempswa \@@warning{Label(s) may have changed. Rerun to get +cross-references right}\fi\fi\endgroup\deadcycles\z@\@@end} + +\def\@testdef #1#2#3{\def\@tempa{#3}\expandafter \ifx \csname #1@#2\endcsname + \@tempa \else + \typeout{Testing #2 failed: old: \csname #1@#2\endcsname <-> new: #3} + \@tempswatrue \fi} + +\newcount\newitem@penalty +\newskip\newitem@preskip +\newskip\newitem@postskip +\newskip\newitem@headsep + +%\def\newitem#1#2{% #1 is type, #2 is name +\def\newitem#1[#2]#3{% #1 is type, #2 is ref key, #3 is name + \endgroup + \ifvmode\else\par\fi + \addpenalty\newitem@penalty + \addvspace\newitem@postskip + \hrule + \nobreak + \vskip \newitem@preskip + \hbox to\hsize{\LARGE\bf\sf \uppercase{#3}\hfil #1}% + \nobreak + \vskip \newitem@headsep + \begingroup + \let_=\other@underscore + \index{#3}\index{#1!#3}% + \def\_{_}\label{#2,#1}\nobreak + \endgroup} + +\newitem@penalty=\@beginparpenalty +\newitem@postskip = 20pt plus 5pt minus 5pt +\newitem@preskip = 10pt +\newitem@headsep = 5pt + +\parskip = 5pt plus 2pt +\parindent = 0pt + + +\def\newitemEnv#1{% + \expandafter\edef\csname#1\endcsname{% + \begingroup\noexpand\redindex@sanitize\csname#1@\endcsname}% + \@namedef{#1@}{\@dblarg{\newitem{#1}}}% + \@namedef{end#1}{}} + +\newitemEnv{Command} +\newitemEnv{Operator} +\newitemEnv{Function} +\newitemEnv{Switch} +\newitemEnv{Variable} +\newitemEnv{Declaration} +\newitemEnv{Package} +\newitemEnv{Concept} +\newitemEnv{Constant} +\newitemEnv{Type} +\newitemEnv{info} +\newitemEnv{Introduction} + +\newskip\itemsec@sep +\newcount\itemsec@penalty + +\itemsec@penalty=\@beginparpenalty +\itemsec@sep=5pt + +\def\begin@itemsection#1{\par\everypar={}% + \addvspace\itemsec@sep + \addpenalty\itemsec@penalty + \hbox{\large\bf\sf #1}\nobreak} + +\def\end@itemsection{\par} + +\def\Comments{\begin@itemsection{Comments}} +\let\endComments\end@itemsection + +\begingroup + \catcode`\^=\active \catcode`\&=\active \catcode`\_=\active + \def\x{\def\setup@special@chars{\catcode`\^=\active \let^=\special@uparrow + \catcode`\&=\active \let&=\special@ampersand}% + \def\protectspecialchars{\def^{\char`\^}\def_{\char`\_}}% + \def\normalspecialchars{\let^=\sp\let_=\sb}% + \def\activespecialchars{\let^=\special@uparrow}} +\expandafter\endgroup\x + +\let\begin@=\begin +\let\end@=\end + +\def\@ifstar#1#2{\def\@tempa{#1}\def\@tempb{#2}\futurelet + \@tempc\@if@star@} + +\def\@if@star@{\ifx \@tempc*\def\@tempd*{\@tempa}\else\let\@tempd\@tempb\fi\@tempd} + +\def\Examples{\begin@itemsection{Examples}% + \setup@special@chars\protectspecialchars%\tracingall + \def\{{{\tt\char`\{}}% + \def\}{{\tt\char`\}}}% + \def\arraystretch{1.5}% + \extrarowheight=1mm + \def\end{% + \ifnum\catcode`\{=12\relax \expandafter \special@ampersand\fi\end@}% + \let \protect \relax + \lineskip \z@ + \baselineskip \z@ + \frenchspacing + \m@th + \def\\{{\ifnum 0=`}\fi + \@ifstar {\@xarraycr\noalign{\penalty\@M}} \@xarraycr} + \let\par=\@empty + \setbox \@arstrutbox \hbox{\vrule + \@height \arraystretch \ht \strutbox + \@depth \arraystretch \dp \strutbox + \@width \z@}% + \ialign\bgroup\@arstrut + \global\@startnewrowfalse + \catcode`\{=12\relax + \catcode`\}=12\relax + \catcode`\%=12\relax + \catcode`\$=12\relax + \catcode`\~=12\relax + \setbox0=\hbox\bgroup\protect\tt##\unskip\hfil\egroup\checkcolwidth + &$\quad\protect\Rightarrow\quad$% + \global\setbox0=\hbox\bgroup\activespecialchars##\egroup\checkcolwidtho\cr +} + +\def\endExamples{\crcr\egroup\end@itemsection} + +%\def\Examples{\begin@itemsection{Examples}% +% \setup@special@chars\protectspecialchars%\tracingall +% \def\{{{\tt\char`\{}}% +% \def\}{{\tt\char`\}}}% +% \def\arraystretch{1.5}% +% \extrarowheight=1mm +% \def\end{% +% \ifnum\catcode`\{=12\relax \expandafter \special@ampersand\fi\end@}% +% \begin{tabular}[b]{>{%\protectspecialchars +% \global\@startnewrowfalse +% \catcode`\{=12\relax +% \catcode`\}=12\relax +% \catcode`\%=12\relax +% \catcode`\$=12\relax +% \setbox0=\hbox\bgroup\protect\tt}l<{\egroup\checkcolwidth}% +% >{$\quad\protect\Rightarrow\quad$% +% \global\setbox0=\hbox\bgroup\activespecialchars}l% +% <{\egroup\checkcolwidtho}}} +%\def\endExamples{\end{tabular}\end@itemsection} + +\def\explanationi#1{\multicolumn{2}{p{0.95\textwidth}}{% + \normalspecialchars \em#1}} +\let\explanation=\explanationi +\def\explanationo#1{\parbox[t]{0.95\MaxOutputWidth}{\em#1}} + +\def\start@new@row@for@output{% + \multicolumn{2}{@{\protect\DoOutputIndent}l}{\box0}} + +\def\DoOutputIndent{ + \dimen@=\textwidth + \advance\dimen@ -\wd\z@ + \ifdim\dimen@>\OutputIndent \dimen@=\OutputIndent + \else\ifdim\dimen@<\z@ \dimen@=\OutputIndent\fi\fi + \hspace{\dimen@}} + +\newdimen\OutputIndent \OutputIndent=10mm + +\begingroup \catcode `|=0 \catcode `[= 1 +\catcode`]=2 \catcode `\{=12 \catcode `\}=12 +\catcode`\\=12 |gdef|@bixample#1\end{Bigexample}[#1|end[Bigexample]] +|endgroup + +\def\Bigexample{\begin@itemsection{Example}% + \@verbatim \frenchspacing\@vobeyspaces \@bixample} +\def\endBigexample{\endtrivlist\end@itemsection} + +\def\Related{\begin@itemsection{Related information}\begin{description}} +\def\endRelated{\end{description}} + +\newif\if@startnewrow \@startnewrowfalse +\newif\if@startneworow \@startneworowfalse +\def\special@uparrow#1{\vbox{\vskip2\p@ + \hbox{\raise.8\normalbaselineskip\hbox{#1}}}} +\def\special@ampersand{&\if@startnewrow\expandafter\startnewrow\fi\tt} + +\def\startnewrow{\omit\\&\global\@startnewrowfalse} + +\newdimen\maxexamplecolwidth +\maxexamplecolwidth = 5cm + +\def\checkcolwidth{% + \ifdim\wd0>\maxexamplecolwidth + \hbox to\maxexamplecolwidth{\unhbox0\hss}% + \hskip-25pt\null + \global\@startnewrowtrue + \else \unhbox0 \fi +} + +\def\checkcolwidtho{% + \ifdim\wd0>\MaxOutputWidth + \global\everycr={\start@new@row@for@output + \global\everycr={}\cr}% +% \global\@startneworowtrue + \else \unhbox0 \fi +} + + +\def\multilineinput{\catcode`\{=1 \catcode`\}=2 + \begin{minipage}[b]{\maxexamplecolwidth}\@vobeyspaces\obeylines} +\def\endmultilineinput{\end{minipage}} + +\def\multilineoutput#1{\begin{minipage}[t]{#1}\@vobeyspaces\obeylines + \baselineskip =1.5\baselineskip} +\def\endmultilineoutput{\end{minipage}} + +\newdimen\MaxOutputWidth \MaxOutputWidth=7cm +\def\multilineoutput#1{% + \vtop\bgroup\@parboxrestore + \lineskip \baselineskip + \@tempswafalse + \def\par{\if@tempswa\egroup + \ifdim\wd0>\z@\box0\fi + \setbox0=\hbox\bgroup\fi + \@tempswatrue} + \@vobeyspaces\obeylines + \setbox0=\hbox\bgroup} + +\def\endmultilineoutput{\egroup\ifdim\wd0>\z@\box0\fi \egroup} + +\def\multilineinput{% + \vbox\bgroup\@parboxrestore + \def\end{\catcode`\{=1 \catcode`\}=2 \end@}% + \@tempswafalse + \def\par{\if@tempswa\egroup + \ifdim\wd0>\z@\box0\fi + \setbox0=\hbox\bgroup\fi + \@tempswatrue} + \@vobeyspaces\obeylines + \addvspace{.8\baselineskip}% + \setbox0=\hbox\bgroup} + +\let\endmultilineinput=\endmultilineoutput + +\def\privateshowbox{\showboxbreadth\maxdimen\showboxdepth\maxdimen\showbox} + +\def\rfrac#1#2{\begingroup + \lineskip2pt \baselineskip \z@ + \setbox0=\hbox{\tt#1}% + \setbox1=\hbox{\tt#2}% + \setbox2=\hbox{\tt-}% + \ifdim \wd0>\wd1 \dimen@=\wd0 \else \dimen@=\wd1 \fi + \advance \dimen@ by2\wd2\relax + \setbox3=\vtop{\hbox to\dimen@{\hss\unhcopy0\hss}% + \hbox to\dimen@{\leaders\copy2\hfill}% + \hbox to\dimen@{\hss\unhcopy1\hss}}% + \dimen@=\dp0 \advance\dimen@ by\ht2 \advance\dimen@ by\lineskip + \@tempdima=\ht3 \advance \@tempdima by\dimen@ \ht3=\@tempdima + \@tempdima=\dp3 \advance \@tempdima by-\dimen@ \dp3=\@tempdima +% \privateshowbox3 + \box3 + \endgroup} + +\def\def@protected#1#2{% + \expandafter\edef\csname#1\endcsname{\begingroup\noexpand\redindex@sanitize + \catcode32=10 + \csname#1@\endcsname}% + \@namedef{#1@}##1{\endgroup#2}} + +\def@protected{name}{\mbox{\tt#1}} +%\let\keyw=\name +%\let\operator=\name +\def@protected{nameindex}{\name{#1}\index{#1}\label{#1}} +\def@protected{hyperref}{#1} +%\def@protected{nameref}{\name{#1}, p.~\pageref{#1}} +\def@protected{nameref}{\name{#1}} +\def@protected{see}{(see \hyperref@{#1})} +\def@protected{key}{\fbox{\sf #1}} +\def@protected{arg}{\mbox{\it #1}} + +\newdimen \Syntaxindent \Syntaxindent=2mm +\def\Syntax{\large + \list{}{\leftmargin\Syntaxindent\def\({$(}\def\){)$}% + \mathcode`\ =32768}\item[]} +\def\endSyntax{\endlist} +\def\repeated{$+$} +\def\optional{\relax\ifmmode\ast\else$\ast$\fi} +%\def\meta#1{\mbox{\it#1}} +\def\meta{\begingroup\catcode`\_=\active\meta@} +\def\meta@#1{\ifmmode\mbox\fi{\it#1\/}\endgroup} + +\def\alternative{$\displaystyle + \left\{\begin{tabular}{l}} +\def\endalternative{\end{tabular}\right\}$} + +\def\section{\@startsection {section}{1}{\z@}{-3.5ex plus-1ex minus + -.2ex}{2.3ex plus.2ex}{\reset@font\LARGE\bf}} +\def\subsection{\@startsection{subsection}{2}{\z@}{-3.25ex plus-1ex + minus-.2ex}{1.5ex plus.2ex}{\reset@font\Large\bf}} +\def\subsubsection{\@startsection{subsubsection}{3}{\z@}{-3.25ex plus + -1ex minus-.2ex}{1.5ex plus.2ex}{\reset@font\large\bf}} + +%%%% +%%%% error message file +%%%% + +\def\tableoferrormessages{\@restonecolfalse + \if@twocolumn\@restonecoltrue\onecolumn\fi + \chapter*{\contentsname + \@mkboth{\uppercase{\contentsname}}{\uppercase{\contentsname}}}% + \@starttoc{emg}\if@restonecol\twocolumn\fi} + +\def\ErrorMessage#1{% + \addcontentsline{emg}{#1}} + +%%%% conditionals + +\def\IFTEX#1#2{#1} + +\long\def\INFO#1\end#2{\def\@tempa{#2}\def\@tempb{INFO}% + \ifx\@tempa\@tempb\else\errmessage{\string\end{#2} not allowed + inside INFO environment.}\@eha\fi + \end{INFO}} +\def\endINFO{\global\@ignoretrue} + +\def\TEX{} +\def\endTEX{\global\@ignoretrue} + + +\@ifundefined{reset@font}{\let\reset@font\@empty}{} + +\pagestyle{REDUCEreference} + +\endinput + + Index: r36/help/REDREF.TEX ================================================================== --- r36/help/REDREF.TEX +++ r36/help/REDREF.TEX @@ -1,186 +1,186 @@ -%%% -%%% The tree structure for the information browser is -%%% given by the \section, \subsection, \subsubsection commands -%%% - -\section{System interaction} - -%%% -%%% Environments like Switch serve a triple purpose: -%%% - the node is defined -%%% - an index entry "demo switch" is generated -%%% - a cross reference with symbolic name "switch:demo" is generated. -%%% This can be used used the \ref, \pageref, \nameref, -%%% and \see commands. -%%% Additional \index entries or cross reference keys can be generated -%%% with the \index and \label commands. -%%% - -\begin{Switch}{demo} - The \name{demo} switch is used for interactive files, causing - the system to pause after each command in the file until you type a - \key{Return}. Default is \name{off}. - -%%% -%%% The parts of a node are given as environments. Defined are: -%%% Comments, Examples, Related -%%% - \begin{Comments} - The switch \name{demo} has no effect on top level interactive - statements. Use it when you want to slow down operations in a file - so you can see what is happening. - - You can either include the \name{on demo} command in the file, - or enter it from the top level before bringing in any file. Unlike - the \name{pause} command, \name{on demo} does not permit you to - interrupt the file for questions of your own. - \end{Comments} -%%% -%%% The Related environment points to related information. It should -%%% also use a cross ref, but that is not yet implemented -%%% - \begin{Related} - \item [\name{in} command] Reading from files. - \item [\name{echo} switch] Seeing what is read in. - \end{Related} -\end{Switch} - -\section{Polynomials} - -\subsection{Polynomial operators} - -\begin{Operator}{den} - The {den} operator returns the denominator of its argument. -%%% -%%% The syntax description needs perhaps a bit more work. -%%% \name and \arg are purely for printing (i.e. selecting a different -%%% typeface -%%% - \begin{Syntax} - \name{den}\(\arg{expression}\) - \end{Syntax} - \arg{expression} is ordinarily a rational expression, but may be - any valid scalar \REDUCE\ expression. - \begin{Examples} - a := x**3 + 3*x**2 + 12*x; & A := X*(X^2 + 3*X + 12) \\ - b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ - den(a/b); & SIN(X) + 4*Y \\ - den(a/4 + b/5); & 20 \\ - den(100/6); & 3 \\ - den(sin(x)); & 1 \\ - for i := 1:3 sum part(firstlis,i)*part(secondlis,i); & - A*X + B*Y + C*Z - \end{Examples} -\end{Operator} -\begin{Comments} - \name{den} returns the denominator of the expression after it has - been simplified by \REDUCE. As seen in the examples, this includes - putting sums of rational expressions over a common denominator, and - reducing common factors where possible. If the expression does not - have any other denominator, $1$ is returned. - - Switch settings, such as \name{mcd} or \name{rational}, have an - effect on the denominator of an expression. -\end{Comments} - -\subsection{Dependency information} - -\begin{Declaration}{depend} - \name{depend} declares that its first argument depends on the rest - of its arguments. - \begin{Syntax} - \name{depend} \arg{kernel}\{,\arg{kernel}\}\repeated - \end{Syntax} - \arg{kernel} must be a legal variable name or a prefix operator - \see{kernel}). - \begin{Examples} - depend y,x; \\ - df(y**2,x); & 2*DF(Y,X)*Y \\ - depend z,cos(x),y; \\ - df(sin(z),cos(x)); & COS(Z)*DF(Z,COS(X)) \\ - df(z**2,x); & 2*DF(Z,X)*Z \\ - nodepend z,y; \\ - df(z**2,x); & 2*DF(Z,X)*Z \\ - cc := df(y**2,x); & CC := 2*DF(Y,x)*Y \\ - y := tan x; & Y := TAN(X) \\ - cc; & 2*TAN(X)*(TAN(X)^{2} + 1) - \end{Examples} - \begin{Comments} - Dependencies can be removed by using the declaration - \nameref{nodepend}. The differentiation opeartor uses this - information, as shown in the examples above. Linear operators alos - use knowledge of dependencies (see \nameref{linear}). Note that - dependencies can be nested: Having declared $y$ to depend on $x$, - and $z$ to depend on $y$, we see that the chain rule was applied - to the derivative of a function of $z$ wiht respect to $x$. If the - explicit function of the dependencyis later entered into the - system, terms with \name{DF(Y,X)}, for example, are expanded when - they are displayed again, as shown in the last example. - \end{Comments} -\end{Declaration} - -\section{The Taylor package} - -\begin{Operator}{taylor} - The \name{taylor} operator is used for expansion in power - series\index{series}. - \begin{Syntax} - \name{taylor}\(\arg{expression},% - \{\arg{kernel},\arg{expression},\arg{integer}\}% - \repeated\) - \end{Syntax} - This returns the expansion of the first argument with respect to - \arg{kernel} about \arg{expression} to order \arg{integer}. - \begin{Examples} - taylor(e^(x^2+y^2),x,0,2,y,0,2); & - 1 + Y^2 + X^2 + Y^2*X^2 + O(X^{3},Y^{3})\\ - taylor(log(1+x),x,0,2); & X - \rfrac{1}{2}*X^{2} + O(X^{3}) - \end{Examples} - \begin{Comments} - The expansion is performed variable per variable, i.e.\ in the - example above by first expanding $\exp(x^{2}+y^{2})$ with respect - to $x$ and then expanding every coefficient with respect to $y$. - - If the switch \nameref{taylorkeeporiginal} is set to \name{on} the - original expression is kept for later reference. - - Printing is controlled by the variable \nameref{taylorprintterms}. - - \end{Comments} - \begin{Related} - \item[tps] Truncated Power Series. - \item[Koepff] Complete power series - \end{Related} -\end{Operator} - -\subsection{Controlling the package} - -\begin{Switch}{taylorkeeporiginal} - The \name{taylorkeeporiginal} switch determines whether the - \nameref{taylor} operator keeps the expression to be expanded for - later use. Default is \name{on}. -\end{Switch} - -\begin{Operator}{taylororiginal} - \name{taylororiginal} extracts the original expression from a Taylor - kernel. - \begin{Syntax} - \name{taylororiginal}\(\arg{taylor\_kernel}\) - \end{Syntax} - If the argument is not a Taylor kernel, or if the expression was not - kept, an error is signaled. -\end{Operator} - -\begin{Variable}{taylorprintterms} - - Only a certain number of (non-zero) coefficients of a Taylor - kernel are printed usually. If there are more, \verb|...| is - printed as part of the expression to indicate this. The number of - terms printed is given by the value of the shared algebraic - variable \nameref{taylorprintterms}. Allowed values are integers - and the special identifier \name{all}. The latter setting - specifies that all terms are to be printed. The default setting is - $5$. - -\end{Variable} - +%%% +%%% The tree structure for the information browser is +%%% given by the \section, \subsection, \subsubsection commands +%%% + +\section{System interaction} + +%%% +%%% Environments like Switch serve a triple purpose: +%%% - the node is defined +%%% - an index entry "demo switch" is generated +%%% - a cross reference with symbolic name "switch:demo" is generated. +%%% This can be used used the \ref, \pageref, \nameref, +%%% and \see commands. +%%% Additional \index entries or cross reference keys can be generated +%%% with the \index and \label commands. +%%% + +\begin{Switch}{demo} + The \name{demo} switch is used for interactive files, causing + the system to pause after each command in the file until you type a + \key{Return}. Default is \name{off}. + +%%% +%%% The parts of a node are given as environments. Defined are: +%%% Comments, Examples, Related +%%% + \begin{Comments} + The switch \name{demo} has no effect on top level interactive + statements. Use it when you want to slow down operations in a file + so you can see what is happening. + + You can either include the \name{on demo} command in the file, + or enter it from the top level before bringing in any file. Unlike + the \name{pause} command, \name{on demo} does not permit you to + interrupt the file for questions of your own. + \end{Comments} +%%% +%%% The Related environment points to related information. It should +%%% also use a cross ref, but that is not yet implemented +%%% + \begin{Related} + \item [\name{in} command] Reading from files. + \item [\name{echo} switch] Seeing what is read in. + \end{Related} +\end{Switch} + +\section{Polynomials} + +\subsection{Polynomial operators} + +\begin{Operator}{den} + The {den} operator returns the denominator of its argument. +%%% +%%% The syntax description needs perhaps a bit more work. +%%% \name and \arg are purely for printing (i.e. selecting a different +%%% typeface +%%% + \begin{Syntax} + \name{den}\(\arg{expression}\) + \end{Syntax} + \arg{expression} is ordinarily a rational expression, but may be + any valid scalar \REDUCE\ expression. + \begin{Examples} + a := x**3 + 3*x**2 + 12*x; & A := X*(X^2 + 3*X + 12) \\ + b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ + den(a/b); & SIN(X) + 4*Y \\ + den(a/4 + b/5); & 20 \\ + den(100/6); & 3 \\ + den(sin(x)); & 1 \\ + for i := 1:3 sum part(firstlis,i)*part(secondlis,i); & + A*X + B*Y + C*Z + \end{Examples} +\end{Operator} +\begin{Comments} + \name{den} returns the denominator of the expression after it has + been simplified by \REDUCE. As seen in the examples, this includes + putting sums of rational expressions over a common denominator, and + reducing common factors where possible. If the expression does not + have any other denominator, $1$ is returned. + + Switch settings, such as \name{mcd} or \name{rational}, have an + effect on the denominator of an expression. +\end{Comments} + +\subsection{Dependency information} + +\begin{Declaration}{depend} + \name{depend} declares that its first argument depends on the rest + of its arguments. + \begin{Syntax} + \name{depend} \arg{kernel}\{,\arg{kernel}\}\repeated + \end{Syntax} + \arg{kernel} must be a legal variable name or a prefix operator + \see{kernel}). + \begin{Examples} + depend y,x; \\ + df(y**2,x); & 2*DF(Y,X)*Y \\ + depend z,cos(x),y; \\ + df(sin(z),cos(x)); & COS(Z)*DF(Z,COS(X)) \\ + df(z**2,x); & 2*DF(Z,X)*Z \\ + nodepend z,y; \\ + df(z**2,x); & 2*DF(Z,X)*Z \\ + cc := df(y**2,x); & CC := 2*DF(Y,x)*Y \\ + y := tan x; & Y := TAN(X) \\ + cc; & 2*TAN(X)*(TAN(X)^{2} + 1) + \end{Examples} + \begin{Comments} + Dependencies can be removed by using the declaration + \nameref{nodepend}. The differentiation opeartor uses this + information, as shown in the examples above. Linear operators alos + use knowledge of dependencies (see \nameref{linear}). Note that + dependencies can be nested: Having declared $y$ to depend on $x$, + and $z$ to depend on $y$, we see that the chain rule was applied + to the derivative of a function of $z$ wiht respect to $x$. If the + explicit function of the dependencyis later entered into the + system, terms with \name{DF(Y,X)}, for example, are expanded when + they are displayed again, as shown in the last example. + \end{Comments} +\end{Declaration} + +\section{The Taylor package} + +\begin{Operator}{taylor} + The \name{taylor} operator is used for expansion in power + series\index{series}. + \begin{Syntax} + \name{taylor}\(\arg{expression},% + \{\arg{kernel},\arg{expression},\arg{integer}\}% + \repeated\) + \end{Syntax} + This returns the expansion of the first argument with respect to + \arg{kernel} about \arg{expression} to order \arg{integer}. + \begin{Examples} + taylor(e^(x^2+y^2),x,0,2,y,0,2); & + 1 + Y^2 + X^2 + Y^2*X^2 + O(X^{3},Y^{3})\\ + taylor(log(1+x),x,0,2); & X - \rfrac{1}{2}*X^{2} + O(X^{3}) + \end{Examples} + \begin{Comments} + The expansion is performed variable per variable, i.e.\ in the + example above by first expanding $\exp(x^{2}+y^{2})$ with respect + to $x$ and then expanding every coefficient with respect to $y$. + + If the switch \nameref{taylorkeeporiginal} is set to \name{on} the + original expression is kept for later reference. + + Printing is controlled by the variable \nameref{taylorprintterms}. + + \end{Comments} + \begin{Related} + \item[tps] Truncated Power Series. + \item[Koepff] Complete power series + \end{Related} +\end{Operator} + +\subsection{Controlling the package} + +\begin{Switch}{taylorkeeporiginal} + The \name{taylorkeeporiginal} switch determines whether the + \nameref{taylor} operator keeps the expression to be expanded for + later use. Default is \name{on}. +\end{Switch} + +\begin{Operator}{taylororiginal} + \name{taylororiginal} extracts the original expression from a Taylor + kernel. + \begin{Syntax} + \name{taylororiginal}\(\arg{taylor\_kernel}\) + \end{Syntax} + If the argument is not a Taylor kernel, or if the expression was not + kept, an error is signaled. +\end{Operator} + +\begin{Variable}{taylorprintterms} + + Only a certain number of (non-zero) coefficients of a Taylor + kernel are printed usually. If there are more, \verb|...| is + printed as part of the expression to indicate this. The number of + terms printed is given by the value of the shared algebraic + variable \nameref{taylorprintterms}. Allowed values are integers + and the special identifier \name{all}. The latter setting + specifies that all terms are to be printed. The default setting is + $5$. + +\end{Variable} + Index: r36/help/RHELP.TEX ================================================================== --- r36/help/RHELP.TEX +++ r36/help/RHELP.TEX @@ -1,6 +1,6 @@ -\documentstyle[redindex]{article} -\makeindex -\begin{document} -\input{redref1.tex} -\input{pk-groeb.old} -\end{document} +\documentstyle[redindex]{article} +\makeindex +\begin{document} +\input{redref1.tex} +\input{pk-groeb.old} +\end{document} Index: r36/help/SYMBOLIC.TEX ================================================================== --- r36/help/SYMBOLIC.TEX +++ r36/help/SYMBOLIC.TEX @@ -1,61 +1,61 @@ -\section{Symbolic Mode} - -\begin{Operator}{EQ} -\begin{Syntax} -\meta{expression} \name{eq} \meta{expression} -\end{Syntax} - -\name{eq} is an infix binary comparison operator that returns {\em true\/} -if the first expression points to the same object as the second. Users -should be completely familiar with the concept of Lisp pointers and their -comparison before using this operator. - -\begin{Comments} -\name{eq} is {\em not\/} -a reliable comparison between numeric arguments. -\end{Comments} - -\end{Operator} - -\begin{Switch}{FASTFOR} -The switch \name{fastfor} causes \nameref{for} loops to use so-called -``inum'' arithmetic in which simple arithmetic operations, such as -updating operations on the looping variable, are replaced by machine -operations. - -\begin{Comments} -This switch should be used with care. Only code that is compiled should -utilize its effect, since some of the operations used are not supported -in interpreted mode. It is also the user's responsibility to ensure that -the arithmetic operations are within the appropriate range, since no -overflow is checked. -\end{Comments} - -\end{Switch} - - -\begin{Operator}{MEMQ} - -\begin{Syntax} -\meta{expression} \name{memq} \meta{list} -\end{Syntax} - -\name{member} is an infix binary comparison operator that evaluates to -{\em true\/} if \meta{expression} is a \nameref{eq} to any member of -\meta{list}. - -\begin{Examples} -if 'a memq {'a,'b} then 1 else 0; & 1 \\ -if '(a) memq {'(a),'(b)} then 1 else 0; & 0 -\end{Examples} - -\begin{Comments} -Since \name{eq} is not a reliable comparison between numeric arguments, -one can't be sure that 1 for example is \name{memq} the list -\name{\{1,2\}}. -\end{Comments} - - -\end{Operator} - - +\section{Symbolic Mode} + +\begin{Operator}{EQ} +\begin{Syntax} +\meta{expression} \name{eq} \meta{expression} +\end{Syntax} + +\name{eq} is an infix binary comparison operator that returns {\em true\/} +if the first expression points to the same object as the second. Users +should be completely familiar with the concept of Lisp pointers and their +comparison before using this operator. + +\begin{Comments} +\name{eq} is {\em not\/} +a reliable comparison between numeric arguments. +\end{Comments} + +\end{Operator} + +\begin{Switch}{FASTFOR} +The switch \name{fastfor} causes \nameref{for} loops to use so-called +``inum'' arithmetic in which simple arithmetic operations, such as +updating operations on the looping variable, are replaced by machine +operations. + +\begin{Comments} +This switch should be used with care. Only code that is compiled should +utilize its effect, since some of the operations used are not supported +in interpreted mode. It is also the user's responsibility to ensure that +the arithmetic operations are within the appropriate range, since no +overflow is checked. +\end{Comments} + +\end{Switch} + + +\begin{Operator}{MEMQ} + +\begin{Syntax} +\meta{expression} \name{memq} \meta{list} +\end{Syntax} + +\name{member} is an infix binary comparison operator that evaluates to +{\em true\/} if \meta{expression} is a \nameref{eq} to any member of +\meta{list}. + +\begin{Examples} +if 'a memq {'a,'b} then 1 else 0; & 1 \\ +if '(a) memq {'(a),'(b)} then 1 else 0; & 0 +\end{Examples} + +\begin{Comments} +Since \name{eq} is not a reliable comparison between numeric arguments, +one can't be sure that 1 for example is \name{memq} the list +\name{\{1,2\}}. +\end{Comments} + + +\end{Operator} + + Index: r36/help/TAYLOR.TEX ================================================================== --- r36/help/TAYLOR.TEX +++ r36/help/TAYLOR.TEX @@ -1,435 +1,435 @@ -\section{Taylor series} - -\begin{Introduction}{TAYLOR} -This short note describes a package of REDUCE procedures that allow -Taylor expansion in one or more variables and efficient manipulation -of the resulting Taylor series. Capabilities include basic operations -(addition, subtraction, multiplication and division) and also -application of certain algebraic and transcendental functions. To a -certain extent, Laurent expansion can be performed as well. -\end{Introduction} - -\begin{Operator}{taylor} - The \name{taylor} operator is used for expanding an expression into a - Taylor series. - - \begin{Syntax} - \name{taylor}\(\meta{expression} - \name{,}\meta{var}\name{,} - \meta{expression}\name{,}\meta{number}\\ - \{\name{,}\meta{var}\name{,} - \meta{expression}\name{,}\meta{number}\}\optional\) - \end{Syntax} - \meta{expression} can be any valid REDUCE algebraic expression. - \meta{var} must be a \nameref{kernel}, and is the expansion - variable. The \meta{expression} following it denotes the point - about which the expansion is to take place. \meta{number} must be a - non-negative integer and denotes the maximum expansion order. If - more than one triple is specified \name{taylor} will expand its - first argument independently with respect to all the variables. - Note that once the expansion has been done it is not possible to - calculate higher orders. - - Instead of a \nameref{kernel}, \meta{var} may also be a list of - kernels. In this case expansion will take place in a way so that - the {\em sum\/} of the degrees of the kernels does not exceed the - maximum expansion order. If the expansion point evaluates to the - special identifier \name{infinity}, \name{taylor} tries to expand in - a series in 1/\meta{var}. - - The expansion is performed variable per variable, i.e.\ in the - example above by first expanding - \IFTEX{$\exp(x^{2}+y^{2})$}{exp(x^2+y^2)} - with respect to - \name{x} and then expanding every coefficient with respect to \name{y}. - - \begin{Examples} - taylor(e^(x^2+y^2),x,0,2,y,0,2); & - 1 + Y^{2} + X^{2} + Y^{2}*X^{2} + O(X^{2},Y^{2}) \\ - taylor(e^(x^2+y^2),{x,y},0,2); & 1 + Y^{2} + X^{2} + O(\{X^{2},Y^{2}\})\\ - \explanation{The following example shows the case of a non-analytical function.}\\ - taylor(x*y/(x+y),x,0,2,y,0,2); & ***** Not a unit in argument to QUOTTAYLOR \\ - \end{Examples} - - \begin{Comments} - Note that it is not generally possible to apply the standard - reduce operators to a Taylor kernel. For example, \nameref{part}, - \nameref{coeff}, or \nameref{coeffn} cannot be used. Instead, the - expression at hand has to be converted to standard form first - using the \nameref{taylortostandard} operator. - - Differentiation of a Taylor expression is possible. If you - differentiate with respect to one of the Taylor variables the - order will decrease by one. - - Substitution is a bit restricted: Taylor variables can only be - replaced by other kernels. There is one exception to this rule: - you can always substitute a Taylor variable by an expression that - evaluates to a constant. Note that REDUCE will not always be able - to determine that an expression is constant: an example is - sin(acos(4)). - - Only simple taylor kernels can be integrated. More complicated - expressions that contain Taylor kernels as parts of themselves are - automatically converted into a standard representation by means of - the \nameref{taylortostandard} operator. In this case a suitable - warning is printed. - - \end{Comments} - -\end{Operator} - - -\begin{Switch}{taylorautocombine} - If you set \name{taylorautocombine} to \name{on}, REDUCE - automatically combines Taylor expressions during the simplification - process. This is equivalent to applying \nameref{taylorcombine} to - every expression that contains Taylor kernels. Default is - \name{on}. -\end{Switch} - -\begin{Switch}{taylorautoexpand} - \name{taylorautoexpand} makes Taylor expressions ``contagious'' in - the sense that \nameref{taylorcombine} tries to Taylor expand all - non-Taylor subexpressions and to combine the result with the rest. - Default is \name{off}. -\end{Switch} - -\begin{Operator}{taylorcombine} - This operator tries to combine all Taylor kernels found in its - argument into one. Operations currently possible are: - \begin{itemize} - \item Addition, subtraction, multiplication, and division. - \item Roots, exponentials, and logarithms. - \item Trigonometric and hyperbolic functions and their inverses. - \end{itemize} - - \begin{Examples} - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - taylorcombine log hugo; & X + O(X^{3})\\ - taylorcombine(hugo + x); & (1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})) + X\\ - on taylorautoexpand; \\ - taylorcombine(hugo + x); & 1 + 2*X + \rfrac{1}{2}*X^{2} + O(X^{3}) - \end{Examples} - - \begin{Comments} - Application of unary operators like \name{log} and \name{atan} - will nearly always succeed. For binary operations their arguments - have to be Taylor kernels with the same template. This means that - the expansion variable and the expansion point must match. - Expansion order is not so important, different order usually means - that one of them is truncated before doing the operation. - - If \nameref{taylorkeeporiginal} is set to \name{on} and if all - Taylor kernels in its argument have their original expressions - kept \name{taylorcombine} will also combine these and store the - result as the original expression of the resulting Taylor kernel. - There is also the switch \nameref{taylorautoexpand}. - - There are a few restrictions to avoid mathematically undefined - expressions: it is not possible to take the logarithm of a Taylor - kernel which has no terms (i.e. is zero), or to divide by such a - beast. There are some provisions made to detect singularities - during expansion: poles that arise because the denominator has - zeros at the expansion point are detected and properly treated, - i.e.\ the Taylor kernel will start with a negative power. (This - is accomplished by expanding numerator and denominator separately - and combining the results.) Essential singularities of the known - functions (see above) are handled correctly. - \end{Comments} -\end{Operator} - -\begin{Switch}{taylorkeeporiginal} - \name{taylorkeeporiginal}, if set to \name{on}, forces the - \nameref{taylor} and all Taylor kernel manipulation operators to - keep the original expression, i.e.\ the expression that was Taylor - expanded. All operations performed on the Taylor kernels are also - applied to this expression which can be recovered using the operator - \nameref{taylororiginal}. Default is \name{off}. -\end{Switch} - -\begin{Operator}{taylororiginal} - Recovers the original expression (the one that was expanded) from - the Taylor kernel that is given as its argument. - - \begin{Syntax} - \name{taylororiginal}\(\meta{expression}\) or - \name{taylororiginal} \meta{simple_expression} - \end{Syntax} - - \begin{Examples} - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - taylororiginal hugo; & - ***** Taylor kernel doesn't have an original part in TAYLORORIGINAL\\ - on taylorkeeporiginal; \\ - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - taylororiginal hugo; & E^{X} - \end{Examples} - - \begin{Comments} - An error is signalled if the argument is not a Taylor kernel or if - the original expression was not kept, i.e.\ if - \nameref{taylorkeeporiginal} was set \name{off} during expansion. - \end{Comments} - -\end{Operator} - -\begin{Switch}{taylorprintorder} - \name{taylorprintorder}, if set to \name{on}, causes the remainder - to be printed in big-O notation. Otherwise, three dots are printed. - Default is \name{on}. -\end{Switch} - -\begin{Variable}{taylorprintterms} - Only a certain number of (non-zero) coefficients are printed. If - there are more, an expression of the form \name{n terms} is printed - to indicate how many non-zero terms have been suppressed. The - number of terms printed is given by the value of the shared - algebraic variable \name{taylorprintterms}. Allowed values are - integers and the special identifier \name{all}. The latter setting - specifies that all terms are to be printed. The default setting is - 5. - - \begin{Examples} - taylor(e^(x^2+y^2),x,0,4,y,0,4); & - 1 + Y^{2} + \rfrac{1}{2}*Y^{4} + X^{2} + Y^{2}*X^{2} + - (4 terms) + O(X^{5},Y^{5})\\ - taylorprintterms := all; & TAYLORPRINTTERMS := ALL \\ - taylor(e^(x^2+y^2),x,0,4,y,0,4); & - \begin{multilineoutput}{} -1 + Y^{2} + \rfrac{1}{2}*Y^{4} + X^{2} + Y^{2}*X^{2} +% - \rfrac{1}{2}*Y^{4}*X^{2} + \rfrac{1}{2}*X^{4} +% - \rfrac{1}{2}*Y^{2}*X^{4}\\ - + \rfrac{1}{4}*Y^{4}*X^{4} + O(X^{5},Y^{5}) - \end{multilineoutput} - \end{Examples} - -\end{Variable} - - -\begin{Operator}{taylorrevert} - \name{taylorrevert} allows reversion of a Taylor series of a - function f, i.e., to compute the first terms of the expansion of the - inverse of $f$ from the expansion of $f$. - - \begin{Syntax} - \name{taylorrevert}\(\meta{expression}\name{,} - \meta{var}\name{,}\meta{var}\) - \end{Syntax} - - The first argument must evaluate to a Taylor kernel with the second - argument being one of its expansion variables. - - \begin{Examples} - taylor(u - u**2,u,0,5); & U - U^{2} + O(U^{6}) \\ - taylorrevert (ws,u,x); & X + X^{2} + 2*X^{3} + 5*X^{4} + 14*X^{5} + O(X^{6}) - \end{Examples} - -\end{Operator} - -\begin{Operator}{taylorseriesp} - This operator may be used to determine if its argument is a Taylor - kernel. - - \begin{Syntax} - \name{taylorseriesp}\(\meta{expression}\) or \name{taylorseriesp} - \meta{simple_expression} - \end{Syntax} - - \begin{Examples} - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - if taylorseriesp hugo then OK;& OK \\ - if taylorseriesp(hugo + y) then OK else NO; & NO - \end{Examples} - - \begin{Comments} - Note that this operator is subject to the same restrictions as, - e.g., \name{ordp} or \name{numberp}, i.e.\ it may only be used in - boolean expressions in \name{if} or \name{let} statements. - \end{Comments} - -\end{Operator} - - -\begin{Operator}{taylortemplate} - The template of a Taylor kernel, i.e.\ the list of all variables - with respect to which expansion took place together with expansion - point and order can be extracted using - - \begin{Syntax} - \name{taylortemplate}\(\meta{expression}\) or - \name{taylortemplate} \meta{simple_expression} - \end{Syntax} - - This returns a list of lists with the three elements - (VAR,VAR0,ORDER). An error is signalled if the argument is not a - Taylor kernel. - - \begin{Examples} - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - taylortemplate hugo; & \{\{X,0,2\}\} - \end{Examples} - -\end{Operator} - -\begin{Operator}{taylortostandard} - This operator converts all Taylor kernels in its argument into - standard form and resimplifies the result. - -\begin{Syntax} - \name{taylortostandard}\(\meta{expression}\) or - \name{taylortostandard} \meta{simple_expression} -\end{Syntax} - - \begin{Examples} - hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ - taylortostandard hugo; & \rfrac{X^{2} + 2*X + 2}{2} - \end{Examples} - -\end{Operator} - -\endinput - -\section{Warnings and error messages} -\index{errors ! TAYLOR package} -\begin{itemize} - -\item \name{Branch point detected in ...}\\ - This occurs if you take a rational power of a Taylor kernel - and raising the lowest order term of the kernel to this - power yields a non analytical term (i.e.\ a fractional power). - -\item \name{Cannot expand further... truncation done}\\ - You will get this warning if you try to expand a Taylor kernel to - a higher order. - -\item \name{Converting Taylor kernels to standard representation}\\ - This warning appears if you try to integrate an expression that - contains Taylor kernels. - -\item \name{Error during expansion (possible singularity)}\\ - The expression you are trying to expand caused an error. - As far as I know this can only happen if it contains a function - with a pole or an essential singularity at the expansion point. - (But one can never be sure.) - -\item \name{Essential singularity in ...}\\ - An essential singularity was detected while applying a - special function to a Taylor kernel. - This error occurs, for example, if you try to take - the logarithm of a Taylor kernel that starts with a negative - power in one of its variables, i.e.\ that has a pole - at the expansion point. - -\item \name{Expansion point lies on branch cut in ...}\\ - The only functions with branch cuts this package knows of are - (natural) logarithm, inverse circular and hyperbolic tangent and - cotangent. The branch cut of the logarithm is assumed to lie on - the negative real axis. Those of the arc tangent and arc - cotangent functions are chosen to be compatible with this: both - have essential singularities at the points $\pm i$. The branch - cut of arc tangent is the straight line along the imaginary axis - connecting $+1$ to $-1$ going through $\infty$ whereas that of arc - cotangent goes through the origin. Consequently, the branch cut - of the inverse hyperbolic tangent resp.\ cotangent lies on the - real axis and goes from $-1$ to $+1$, that of the latter across - $0$, the other across $\infty$. - - The error message can currently only appear when you try to - calculate the inverse tangent or cotangent of a Taylor - kernel that starts with a negative degree. - The case of a logarithm of a Taylor kernel whose constant term - is a negative real number is not caught since it is - difficult to detect this in general. - -\item \name{Not a unity in ...}\\ - This will happen if you try to divide by or take the logarithm of - a Taylor series whose constant term vanishes. - -\item \name{Not implemented yet (...)}\\ - Sorry, but I haven't had the time to implement this feature. - Tell me if you really need it, maybe I have already an improved - version of the package. - -\item \name{Reversion of Taylor series not possible: ...}\\ -\ttindex{TAYLORREVERT} - You tried to call the \name{TAYLORREVERT} operator with - inappropriate arguments. The second half of this error message - tells you why this operation is not possible. - -\item \name{Substitution of dependent variables ...}\\ - You tried to substitute a variable that is already present in the - Taylor kernel or on which one of the Taylor variables depend. - -\item \name{Taylor kernel doesn't have an original part}\\ -\ttindex{TAYLORORIGINAL} \ttindex{TAYLORKEEPORIGINAL} - The Taylor kernel upon which you try to use \name{TAYLORORIGINAL} - was created with the switch \name{TAYLORKEEPORIGINAL} - set to \name{OFF} - and does therefore not keep the original expression. - -\item \name{Wrong number of arguments to TAYLOR}\\ - You try to use the operator \name{TAYLOR} with a wrong number of - arguments. - -\item \name{Zero divisor in TAYLOREXPAND}\\ - A zero divisor was found while an expression was being expanded. - This should not normally occur. - -\item \name{Zero divisor in Taylor substitution}\\ - That's exactly what the message says. As an example consider the - case of a Taylor kernel containing the term \name{1/x} and you try - to substitute \name{x| by \verb|0}. - -\item \name{... invalid as kernel}\\ - You tried to expand with respect to an expression that is not a - kernel. - -\item \name{... invalid as order of Taylor expansion}\\ - The order parameter you gave to \name{TAYLOR} is not an integer. - -\item \name{... invalid as Taylor kernel}\\ -\ttindex{TAYLORORIGINAL} \ttindex{TAYLORTEMPLATE} - You tried to apply \name{TAYLORORIGINAL| or \verb|TAYLORTEMPLATE} - to an expression that is not a Taylor kernel. - -\item \name{... invalid as Taylor variable}\\ - You tried to substitute a Taylor variable by an expression that is - not a kernel. - -\item \name{... invalid as value of TaylorPrintTerms}\\ -\ttindex{TAYLORPRINTTERMS} - You have assigned an invalid value to \name{TAYLORPRINTTERMS}. - Allowed values are: an integer or the special identifier - \name{ALL}. - -\item \name{TAYLOR PACKAGE (...): this can't happen ...}\\ - This message shows that an internal inconsistency was detected. - This is not your fault, at least as long as you did not try to - work with the internal data structures of \REDUCE. Send input - and output to me, together with the version information that is - printed out. - -\end{itemize} - -\section{Comparison to other packages} - -At the moment there is only one \REDUCE{} package that I know of: -the truncated power series package by Alan Barnes and Julian Padget. -In my opinion there are two major differences: -\begin{itemize} - \item The interface. They use the domain mechanism for their power - series, I decided to invent a special kind of kernel. Both - approaches have advantages and disadvantages: with domain - modes, it is easier - to do certain things automatically, e.g., conversions. - \item The concept of a truncated series. Their idea is to remember - the original expression and to compute more coefficients when - more of them are needed. My approach is to truncate at a - certain order and forget how the unexpanded expression - looked like. I think that their method is more widely - usable, whereas mine is more efficient when you know in - advance exactly how many terms you need. -\end{itemize} - -\end{document} +\section{Taylor series} + +\begin{Introduction}{TAYLOR} +This short note describes a package of REDUCE procedures that allow +Taylor expansion in one or more variables and efficient manipulation +of the resulting Taylor series. Capabilities include basic operations +(addition, subtraction, multiplication and division) and also +application of certain algebraic and transcendental functions. To a +certain extent, Laurent expansion can be performed as well. +\end{Introduction} + +\begin{Operator}{taylor} + The \name{taylor} operator is used for expanding an expression into a + Taylor series. + + \begin{Syntax} + \name{taylor}\(\meta{expression} + \name{,}\meta{var}\name{,} + \meta{expression}\name{,}\meta{number}\\ + \{\name{,}\meta{var}\name{,} + \meta{expression}\name{,}\meta{number}\}\optional\) + \end{Syntax} + \meta{expression} can be any valid REDUCE algebraic expression. + \meta{var} must be a \nameref{kernel}, and is the expansion + variable. The \meta{expression} following it denotes the point + about which the expansion is to take place. \meta{number} must be a + non-negative integer and denotes the maximum expansion order. If + more than one triple is specified \name{taylor} will expand its + first argument independently with respect to all the variables. + Note that once the expansion has been done it is not possible to + calculate higher orders. + + Instead of a \nameref{kernel}, \meta{var} may also be a list of + kernels. In this case expansion will take place in a way so that + the {\em sum\/} of the degrees of the kernels does not exceed the + maximum expansion order. If the expansion point evaluates to the + special identifier \name{infinity}, \name{taylor} tries to expand in + a series in 1/\meta{var}. + + The expansion is performed variable per variable, i.e.\ in the + example above by first expanding + \IFTEX{$\exp(x^{2}+y^{2})$}{exp(x^2+y^2)} + with respect to + \name{x} and then expanding every coefficient with respect to \name{y}. + + \begin{Examples} + taylor(e^(x^2+y^2),x,0,2,y,0,2); & + 1 + Y^{2} + X^{2} + Y^{2}*X^{2} + O(X^{2},Y^{2}) \\ + taylor(e^(x^2+y^2),{x,y},0,2); & 1 + Y^{2} + X^{2} + O(\{X^{2},Y^{2}\})\\ + \explanation{The following example shows the case of a non-analytical function.}\\ + taylor(x*y/(x+y),x,0,2,y,0,2); & ***** Not a unit in argument to QUOTTAYLOR \\ + \end{Examples} + + \begin{Comments} + Note that it is not generally possible to apply the standard + reduce operators to a Taylor kernel. For example, \nameref{part}, + \nameref{coeff}, or \nameref{coeffn} cannot be used. Instead, the + expression at hand has to be converted to standard form first + using the \nameref{taylortostandard} operator. + + Differentiation of a Taylor expression is possible. If you + differentiate with respect to one of the Taylor variables the + order will decrease by one. + + Substitution is a bit restricted: Taylor variables can only be + replaced by other kernels. There is one exception to this rule: + you can always substitute a Taylor variable by an expression that + evaluates to a constant. Note that REDUCE will not always be able + to determine that an expression is constant: an example is + sin(acos(4)). + + Only simple taylor kernels can be integrated. More complicated + expressions that contain Taylor kernels as parts of themselves are + automatically converted into a standard representation by means of + the \nameref{taylortostandard} operator. In this case a suitable + warning is printed. + + \end{Comments} + +\end{Operator} + + +\begin{Switch}{taylorautocombine} + If you set \name{taylorautocombine} to \name{on}, REDUCE + automatically combines Taylor expressions during the simplification + process. This is equivalent to applying \nameref{taylorcombine} to + every expression that contains Taylor kernels. Default is + \name{on}. +\end{Switch} + +\begin{Switch}{taylorautoexpand} + \name{taylorautoexpand} makes Taylor expressions ``contagious'' in + the sense that \nameref{taylorcombine} tries to Taylor expand all + non-Taylor subexpressions and to combine the result with the rest. + Default is \name{off}. +\end{Switch} + +\begin{Operator}{taylorcombine} + This operator tries to combine all Taylor kernels found in its + argument into one. Operations currently possible are: + \begin{itemize} + \item Addition, subtraction, multiplication, and division. + \item Roots, exponentials, and logarithms. + \item Trigonometric and hyperbolic functions and their inverses. + \end{itemize} + + \begin{Examples} + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + taylorcombine log hugo; & X + O(X^{3})\\ + taylorcombine(hugo + x); & (1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})) + X\\ + on taylorautoexpand; \\ + taylorcombine(hugo + x); & 1 + 2*X + \rfrac{1}{2}*X^{2} + O(X^{3}) + \end{Examples} + + \begin{Comments} + Application of unary operators like \name{log} and \name{atan} + will nearly always succeed. For binary operations their arguments + have to be Taylor kernels with the same template. This means that + the expansion variable and the expansion point must match. + Expansion order is not so important, different order usually means + that one of them is truncated before doing the operation. + + If \nameref{taylorkeeporiginal} is set to \name{on} and if all + Taylor kernels in its argument have their original expressions + kept \name{taylorcombine} will also combine these and store the + result as the original expression of the resulting Taylor kernel. + There is also the switch \nameref{taylorautoexpand}. + + There are a few restrictions to avoid mathematically undefined + expressions: it is not possible to take the logarithm of a Taylor + kernel which has no terms (i.e. is zero), or to divide by such a + beast. There are some provisions made to detect singularities + during expansion: poles that arise because the denominator has + zeros at the expansion point are detected and properly treated, + i.e.\ the Taylor kernel will start with a negative power. (This + is accomplished by expanding numerator and denominator separately + and combining the results.) Essential singularities of the known + functions (see above) are handled correctly. + \end{Comments} +\end{Operator} + +\begin{Switch}{taylorkeeporiginal} + \name{taylorkeeporiginal}, if set to \name{on}, forces the + \nameref{taylor} and all Taylor kernel manipulation operators to + keep the original expression, i.e.\ the expression that was Taylor + expanded. All operations performed on the Taylor kernels are also + applied to this expression which can be recovered using the operator + \nameref{taylororiginal}. Default is \name{off}. +\end{Switch} + +\begin{Operator}{taylororiginal} + Recovers the original expression (the one that was expanded) from + the Taylor kernel that is given as its argument. + + \begin{Syntax} + \name{taylororiginal}\(\meta{expression}\) or + \name{taylororiginal} \meta{simple_expression} + \end{Syntax} + + \begin{Examples} + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + taylororiginal hugo; & + ***** Taylor kernel doesn't have an original part in TAYLORORIGINAL\\ + on taylorkeeporiginal; \\ + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + taylororiginal hugo; & E^{X} + \end{Examples} + + \begin{Comments} + An error is signalled if the argument is not a Taylor kernel or if + the original expression was not kept, i.e.\ if + \nameref{taylorkeeporiginal} was set \name{off} during expansion. + \end{Comments} + +\end{Operator} + +\begin{Switch}{taylorprintorder} + \name{taylorprintorder}, if set to \name{on}, causes the remainder + to be printed in big-O notation. Otherwise, three dots are printed. + Default is \name{on}. +\end{Switch} + +\begin{Variable}{taylorprintterms} + Only a certain number of (non-zero) coefficients are printed. If + there are more, an expression of the form \name{n terms} is printed + to indicate how many non-zero terms have been suppressed. The + number of terms printed is given by the value of the shared + algebraic variable \name{taylorprintterms}. Allowed values are + integers and the special identifier \name{all}. The latter setting + specifies that all terms are to be printed. The default setting is + 5. + + \begin{Examples} + taylor(e^(x^2+y^2),x,0,4,y,0,4); & + 1 + Y^{2} + \rfrac{1}{2}*Y^{4} + X^{2} + Y^{2}*X^{2} + + (4 terms) + O(X^{5},Y^{5})\\ + taylorprintterms := all; & TAYLORPRINTTERMS := ALL \\ + taylor(e^(x^2+y^2),x,0,4,y,0,4); & + \begin{multilineoutput}{} +1 + Y^{2} + \rfrac{1}{2}*Y^{4} + X^{2} + Y^{2}*X^{2} +% + \rfrac{1}{2}*Y^{4}*X^{2} + \rfrac{1}{2}*X^{4} +% + \rfrac{1}{2}*Y^{2}*X^{4}\\ + + \rfrac{1}{4}*Y^{4}*X^{4} + O(X^{5},Y^{5}) + \end{multilineoutput} + \end{Examples} + +\end{Variable} + + +\begin{Operator}{taylorrevert} + \name{taylorrevert} allows reversion of a Taylor series of a + function f, i.e., to compute the first terms of the expansion of the + inverse of $f$ from the expansion of $f$. + + \begin{Syntax} + \name{taylorrevert}\(\meta{expression}\name{,} + \meta{var}\name{,}\meta{var}\) + \end{Syntax} + + The first argument must evaluate to a Taylor kernel with the second + argument being one of its expansion variables. + + \begin{Examples} + taylor(u - u**2,u,0,5); & U - U^{2} + O(U^{6}) \\ + taylorrevert (ws,u,x); & X + X^{2} + 2*X^{3} + 5*X^{4} + 14*X^{5} + O(X^{6}) + \end{Examples} + +\end{Operator} + +\begin{Operator}{taylorseriesp} + This operator may be used to determine if its argument is a Taylor + kernel. + + \begin{Syntax} + \name{taylorseriesp}\(\meta{expression}\) or \name{taylorseriesp} + \meta{simple_expression} + \end{Syntax} + + \begin{Examples} + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + if taylorseriesp hugo then OK;& OK \\ + if taylorseriesp(hugo + y) then OK else NO; & NO + \end{Examples} + + \begin{Comments} + Note that this operator is subject to the same restrictions as, + e.g., \name{ordp} or \name{numberp}, i.e.\ it may only be used in + boolean expressions in \name{if} or \name{let} statements. + \end{Comments} + +\end{Operator} + + +\begin{Operator}{taylortemplate} + The template of a Taylor kernel, i.e.\ the list of all variables + with respect to which expansion took place together with expansion + point and order can be extracted using + + \begin{Syntax} + \name{taylortemplate}\(\meta{expression}\) or + \name{taylortemplate} \meta{simple_expression} + \end{Syntax} + + This returns a list of lists with the three elements + (VAR,VAR0,ORDER). An error is signalled if the argument is not a + Taylor kernel. + + \begin{Examples} + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + taylortemplate hugo; & \{\{X,0,2\}\} + \end{Examples} + +\end{Operator} + +\begin{Operator}{taylortostandard} + This operator converts all Taylor kernels in its argument into + standard form and resimplifies the result. + +\begin{Syntax} + \name{taylortostandard}\(\meta{expression}\) or + \name{taylortostandard} \meta{simple_expression} +\end{Syntax} + + \begin{Examples} + hugo := taylor(exp(x),x,0,2); & HUGO := 1 + X + \rfrac{1}{2}*X^{2} + O(X^{3})\\ + taylortostandard hugo; & \rfrac{X^{2} + 2*X + 2}{2} + \end{Examples} + +\end{Operator} + +\endinput + +\section{Warnings and error messages} +\index{errors ! TAYLOR package} +\begin{itemize} + +\item \name{Branch point detected in ...}\\ + This occurs if you take a rational power of a Taylor kernel + and raising the lowest order term of the kernel to this + power yields a non analytical term (i.e.\ a fractional power). + +\item \name{Cannot expand further... truncation done}\\ + You will get this warning if you try to expand a Taylor kernel to + a higher order. + +\item \name{Converting Taylor kernels to standard representation}\\ + This warning appears if you try to integrate an expression that + contains Taylor kernels. + +\item \name{Error during expansion (possible singularity)}\\ + The expression you are trying to expand caused an error. + As far as I know this can only happen if it contains a function + with a pole or an essential singularity at the expansion point. + (But one can never be sure.) + +\item \name{Essential singularity in ...}\\ + An essential singularity was detected while applying a + special function to a Taylor kernel. + This error occurs, for example, if you try to take + the logarithm of a Taylor kernel that starts with a negative + power in one of its variables, i.e.\ that has a pole + at the expansion point. + +\item \name{Expansion point lies on branch cut in ...}\\ + The only functions with branch cuts this package knows of are + (natural) logarithm, inverse circular and hyperbolic tangent and + cotangent. The branch cut of the logarithm is assumed to lie on + the negative real axis. Those of the arc tangent and arc + cotangent functions are chosen to be compatible with this: both + have essential singularities at the points $\pm i$. The branch + cut of arc tangent is the straight line along the imaginary axis + connecting $+1$ to $-1$ going through $\infty$ whereas that of arc + cotangent goes through the origin. Consequently, the branch cut + of the inverse hyperbolic tangent resp.\ cotangent lies on the + real axis and goes from $-1$ to $+1$, that of the latter across + $0$, the other across $\infty$. + + The error message can currently only appear when you try to + calculate the inverse tangent or cotangent of a Taylor + kernel that starts with a negative degree. + The case of a logarithm of a Taylor kernel whose constant term + is a negative real number is not caught since it is + difficult to detect this in general. + +\item \name{Not a unity in ...}\\ + This will happen if you try to divide by or take the logarithm of + a Taylor series whose constant term vanishes. + +\item \name{Not implemented yet (...)}\\ + Sorry, but I haven't had the time to implement this feature. + Tell me if you really need it, maybe I have already an improved + version of the package. + +\item \name{Reversion of Taylor series not possible: ...}\\ +\ttindex{TAYLORREVERT} + You tried to call the \name{TAYLORREVERT} operator with + inappropriate arguments. The second half of this error message + tells you why this operation is not possible. + +\item \name{Substitution of dependent variables ...}\\ + You tried to substitute a variable that is already present in the + Taylor kernel or on which one of the Taylor variables depend. + +\item \name{Taylor kernel doesn't have an original part}\\ +\ttindex{TAYLORORIGINAL} \ttindex{TAYLORKEEPORIGINAL} + The Taylor kernel upon which you try to use \name{TAYLORORIGINAL} + was created with the switch \name{TAYLORKEEPORIGINAL} + set to \name{OFF} + and does therefore not keep the original expression. + +\item \name{Wrong number of arguments to TAYLOR}\\ + You try to use the operator \name{TAYLOR} with a wrong number of + arguments. + +\item \name{Zero divisor in TAYLOREXPAND}\\ + A zero divisor was found while an expression was being expanded. + This should not normally occur. + +\item \name{Zero divisor in Taylor substitution}\\ + That's exactly what the message says. As an example consider the + case of a Taylor kernel containing the term \name{1/x} and you try + to substitute \name{x| by \verb|0}. + +\item \name{... invalid as kernel}\\ + You tried to expand with respect to an expression that is not a + kernel. + +\item \name{... invalid as order of Taylor expansion}\\ + The order parameter you gave to \name{TAYLOR} is not an integer. + +\item \name{... invalid as Taylor kernel}\\ +\ttindex{TAYLORORIGINAL} \ttindex{TAYLORTEMPLATE} + You tried to apply \name{TAYLORORIGINAL| or \verb|TAYLORTEMPLATE} + to an expression that is not a Taylor kernel. + +\item \name{... invalid as Taylor variable}\\ + You tried to substitute a Taylor variable by an expression that is + not a kernel. + +\item \name{... invalid as value of TaylorPrintTerms}\\ +\ttindex{TAYLORPRINTTERMS} + You have assigned an invalid value to \name{TAYLORPRINTTERMS}. + Allowed values are: an integer or the special identifier + \name{ALL}. + +\item \name{TAYLOR PACKAGE (...): this can't happen ...}\\ + This message shows that an internal inconsistency was detected. + This is not your fault, at least as long as you did not try to + work with the internal data structures of \REDUCE. Send input + and output to me, together with the version information that is + printed out. + +\end{itemize} + +\section{Comparison to other packages} + +At the moment there is only one \REDUCE{} package that I know of: +the truncated power series package by Alan Barnes and Julian Padget. +In my opinion there are two major differences: +\begin{itemize} + \item The interface. They use the domain mechanism for their power + series, I decided to invent a special kind of kernel. Both + approaches have advantages and disadvantages: with domain + modes, it is easier + to do certain things automatically, e.g., conversions. + \item The concept of a truncated series. Their idea is to remember + the original expression and to compute more coefficients when + more of them are needed. My approach is to truncate at a + certain order and forget how the unexpanded expression + looked like. I think that their method is more widely + usable, whereas mine is more efficient when you know in + advance exactly how many terms you need. +\end{itemize} + +\end{document} Index: r36/help/VARIABLE.TEX ================================================================== --- r36/help/VARIABLE.TEX +++ r36/help/VARIABLE.TEX @@ -1,233 +1,233 @@ -\section{Variables} - -\begin{Variable}{assumptions} -\index{solve} -After solving a linear or polynomial equation system -with parameters, the variable \name{assumptions} contains a list -of side relations for the parameters. The solution is valid only -as long as none of these expression is zero. -\begin{Examples} -solve({a*x-b*y+x,y-c},{x,y});& -\{\{x=\rfrac{b*c}{a + 1},y=c\}\} \\ -assumptions; & \{a + 1\} -\end{Examples} -\end{Variable} - -\begin{Variable}{CARD\_NO} -\index{FORTRAN}\index{output} -\name{card\_no} sets the total number of cards allowed in a Fortran -output statement when \name{fort} is on. Default is 20. - -\begin{Examples} -on fort; \\ -card_no := 4; & CARD\_NO=4. \\ -z := (x + y)**15; & -\begin{multilineoutput}{6cm} - ANS1=5005.*X**6*Y**9+3003.*X**5*Y**10+1365.*X**4*Y** - . 11+455.*X**3*Y**12+105.*X**2*Y**13+15.*X*Y**14+Y**15 - Z=X**15+15.*X**14*Y+105.*X**13*Y**2+455.*X**12*Y**3+ - . 1365.*X**11*Y**4+3003.*X**10*Y**5+5005.*X**9*Y**6+ - . 6435.*X**8*Y**7+6435.*X**7*Y**8+ANS1 -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -Twenty total cards means 19 continuation cards. You may set it for more -if your Fortran system allows more. Expressions are broken apart in a -Fortran-compatible way if they extend for more than \name{card\_no} -continuation cards. -\end{Comments} -\end{Variable} - - -\begin{Constant}{E} -The constant \name{e} is reserved for use as the base of the natural -logarithm. Its value is approximately 2.71828284590, which REDUCE gives -to the current decimal precision when the switch \nameref{rounded} is on. - -\begin{Comments} -\name{e} may be used as an iterative variable in a \nameref{for} statement, -or as a local variable or a \nameref{procedure}. If \name{e} is defined -as a local -variable inside the procedure, the normal definition as the base of the -natural logarithm would be suspended inside the procedure. -\end{Comments} -\end{Constant} - - -\begin{Variable}{EVAL\_MODE} -\index{algebraic}\index{symbolic} -The system variable \name{eval\_mode} contains the current mode, either -\nameref{algebraic} or \nameref{symbolic}. - -\begin{Examples} -EVAL\_MODE; & ALGEBRAIC -\end{Examples} - -\begin{Comments} -Some commands do not behave the same way in algebraic and symbolic modes. -%You can determine what mode you are in without using this command by noting -%that the numbered prompt in algebraic mode contains a colon (\name{:}), while -%the numbered prompt in symbolic mode contains an asterisk (\name{*}). -\end{Comments} -\end{Variable} - - -\begin{Variable}{FORT\_WIDTH} -\index{output}\index{FORTRAN} -The \name{fort\_width} variable sets the number of characters in a line of -Fortran-compatible output produced when the \nameref{fort} switch is on. -Default is 70. - -\begin{Examples} -fort_width := 30; & FORT\_WIDTH := 30 \\ -on fort; \\ -df(sin(x**3*y),x); & \begin{multilineoutput}{3cm} - ANS=3.*COS(X - . **3*Y)*X**2* - . Y -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -\name{fort\_width} includes the usually blank characters at the beginning -of the card. As you may notice above, it is conservative and makes the -lines even shorter than it was told. -\end{Comments} -\end{Variable} - - -\begin{Variable}{HIGH\_POW} -\index{polynomial}\index{degree} -The variable \name{high\_pow} is set by \nameref{coeff} to the highest power -of the variable of interest in the given expression. You can access this -variable for use in further computation or display. - -\begin{Examples} -coeff((x+1)^5*(x*(y+3)^2)^2,x); & -\begin{multilineoutput}{6cm} -\{0, - 0, - Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81, - 5*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), - 10*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), - 10*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), - 5*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), - Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81\} -\end{multilineoutput} \\ -high_pow; & 7 -\end{Examples} -\end{Variable} - - -\begin{Constant}{I} -\index{complex} -REDUCE knows \name{i} is the square root of -1, - and that \IFTEX{$i^2 = -1$}{i^2 = -1}. - -\begin{Examples} -(a + b*i)*(c + d*i); & A*C + A*D*I + B*C*I - B*D \\ -i**2; & -1 -\end{Examples} - -\begin{Comments} -\name{i} cannot be used as an identifier. It is all right to use \name{i} -as an index variable in a \name{for} loop, or as a local (\name{scalar}) -variable inside a \name{begin...end} block, but it loses its definition as -the square root of -1 inside the block in that case. - -Only the simplest properties of \IFTEX{$i$}{i} are known by REDUCE unless -the switch \nameref{complex} is turned on, which implements full complex -arithmetic in factoring, simplification, and functional values. -\name{complex} is ordinarily off. -\end{Comments} -\end{Constant} - - -\begin{Constant}{INFINITY} -The name \name{infinity} is used to represent the infinite positive number. -However, at the present time, arithmetic in terms of this operator reflects -finite arithmetic, rather than true operations on infinity. - -\end{Constant} - - -\begin{Variable}{LOW\_POW} -\index{degree}\index{polynomial} -The variable \name{low\_pow} is set by \nameref{coeff} to the lowest power -of the variable of interest in the given expression. You can access this -variable for use in further computation or display. - -\begin{Examples} -coeff((x+2*y)**6,y); & -\begin{multilineoutput}{6cm} -\{X^{6}, - 12*X^{5}, - 60*X^{4}, - 160*X^{3}, - 240*X^{2}, - 192*X, - 64\} -\end{multilineoutput}\\ -low_pow; & 0 \\ -coeff(x**2*(x*sin(y) + 1),x); - & \{0,0,1,SIN(Y)\} \\ -low_pow; & 2 -\end{Examples} - -\end{Variable} - - -\begin{Constant}{NIL} -\index{false} -\name{nil} represents the truth value {\it false} in symbolic mode, and is -a synonym for 0 in algebraic mode. It cannot be used for any other -purpose, even inside procedures or \nameref{for} loops. -\end{Constant} - - -\begin{Constant}{PI} -The identifier \name{pi} is reserved for use as the circular constant. -Its value is given by 3.14159265358..., which REDUCE gives to the current -decimal precision when REDUCE is in a floating-point mode. - -\begin{Comments} -\name{pi} may be used as a looping variable in a \nameref{for} statement, -or as a local variable in a \nameref{procedure}. Its value in such cases -will be taken from the local environment. -\end{Comments} -\end{Constant} - -\begin{Variable}{requirements} -\index{solve} -After an attempt to solve an inconsistent equation system -with parameters, the variable \name{requirements} contains a list -of expressions. These expressions define a set of conditions implicitly -equated with zero. Any solution to this system defines a setting for -the parameters sufficient to make the original system consistent. -\begin{Examples} -solve({x-a,x-y,y-1},{x,y}); & \{\}\\ -requirements;&\{a - 1\} -\end{Examples} -\end{Variable} - -\begin{Variable}{ROOT\_MULTIPLICITIES} -\index{root}\index{solve}\index{polynomial} -The \name{root\_multiplicities} variable is set to the list of the -multiplicities of the roots of an equation by the \nameref{solve} operator. - -\begin{Comments} -\nameref{solve} returns its solutions in a list. The multiplicities of -each solution are put in the corresponding locations of the list -\name{root\_multiplicities}. -\end{Comments} -\end{Variable} - - -\begin{Constant}{T} -The constant \name{t} stands for the truth value {\it true}. It cannot be used -as a scalar variable in a \nameref{block}, as a looping variable in a -\nameref{for} statement or as an \nameref{operator} name. - -\end{Constant} - +\section{Variables} + +\begin{Variable}{assumptions} +\index{solve} +After solving a linear or polynomial equation system +with parameters, the variable \name{assumptions} contains a list +of side relations for the parameters. The solution is valid only +as long as none of these expression is zero. +\begin{Examples} +solve({a*x-b*y+x,y-c},{x,y});& +\{\{x=\rfrac{b*c}{a + 1},y=c\}\} \\ +assumptions; & \{a + 1\} +\end{Examples} +\end{Variable} + +\begin{Variable}{CARD\_NO} +\index{FORTRAN}\index{output} +\name{card\_no} sets the total number of cards allowed in a Fortran +output statement when \name{fort} is on. Default is 20. + +\begin{Examples} +on fort; \\ +card_no := 4; & CARD\_NO=4. \\ +z := (x + y)**15; & +\begin{multilineoutput}{6cm} + ANS1=5005.*X**6*Y**9+3003.*X**5*Y**10+1365.*X**4*Y** + . 11+455.*X**3*Y**12+105.*X**2*Y**13+15.*X*Y**14+Y**15 + Z=X**15+15.*X**14*Y+105.*X**13*Y**2+455.*X**12*Y**3+ + . 1365.*X**11*Y**4+3003.*X**10*Y**5+5005.*X**9*Y**6+ + . 6435.*X**8*Y**7+6435.*X**7*Y**8+ANS1 +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +Twenty total cards means 19 continuation cards. You may set it for more +if your Fortran system allows more. Expressions are broken apart in a +Fortran-compatible way if they extend for more than \name{card\_no} +continuation cards. +\end{Comments} +\end{Variable} + + +\begin{Constant}{E} +The constant \name{e} is reserved for use as the base of the natural +logarithm. Its value is approximately 2.71828284590, which REDUCE gives +to the current decimal precision when the switch \nameref{rounded} is on. + +\begin{Comments} +\name{e} may be used as an iterative variable in a \nameref{for} statement, +or as a local variable or a \nameref{procedure}. If \name{e} is defined +as a local +variable inside the procedure, the normal definition as the base of the +natural logarithm would be suspended inside the procedure. +\end{Comments} +\end{Constant} + + +\begin{Variable}{EVAL\_MODE} +\index{algebraic}\index{symbolic} +The system variable \name{eval\_mode} contains the current mode, either +\nameref{algebraic} or \nameref{symbolic}. + +\begin{Examples} +EVAL\_MODE; & ALGEBRAIC +\end{Examples} + +\begin{Comments} +Some commands do not behave the same way in algebraic and symbolic modes. +%You can determine what mode you are in without using this command by noting +%that the numbered prompt in algebraic mode contains a colon (\name{:}), while +%the numbered prompt in symbolic mode contains an asterisk (\name{*}). +\end{Comments} +\end{Variable} + + +\begin{Variable}{FORT\_WIDTH} +\index{output}\index{FORTRAN} +The \name{fort\_width} variable sets the number of characters in a line of +Fortran-compatible output produced when the \nameref{fort} switch is on. +Default is 70. + +\begin{Examples} +fort_width := 30; & FORT\_WIDTH := 30 \\ +on fort; \\ +df(sin(x**3*y),x); & \begin{multilineoutput}{3cm} + ANS=3.*COS(X + . **3*Y)*X**2* + . Y +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +\name{fort\_width} includes the usually blank characters at the beginning +of the card. As you may notice above, it is conservative and makes the +lines even shorter than it was told. +\end{Comments} +\end{Variable} + + +\begin{Variable}{HIGH\_POW} +\index{polynomial}\index{degree} +The variable \name{high\_pow} is set by \nameref{coeff} to the highest power +of the variable of interest in the given expression. You can access this +variable for use in further computation or display. + +\begin{Examples} +coeff((x+1)^5*(x*(y+3)^2)^2,x); & +\begin{multilineoutput}{6cm} +\{0, + 0, + Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81, + 5*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), + 10*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), + 10*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), + 5*(Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81), + Y^{4} + 12*Y^{3} + 54*Y^{2} + 108*Y + 81\} +\end{multilineoutput} \\ +high_pow; & 7 +\end{Examples} +\end{Variable} + + +\begin{Constant}{I} +\index{complex} +REDUCE knows \name{i} is the square root of -1, + and that \IFTEX{$i^2 = -1$}{i^2 = -1}. + +\begin{Examples} +(a + b*i)*(c + d*i); & A*C + A*D*I + B*C*I - B*D \\ +i**2; & -1 +\end{Examples} + +\begin{Comments} +\name{i} cannot be used as an identifier. It is all right to use \name{i} +as an index variable in a \name{for} loop, or as a local (\name{scalar}) +variable inside a \name{begin...end} block, but it loses its definition as +the square root of -1 inside the block in that case. + +Only the simplest properties of \IFTEX{$i$}{i} are known by REDUCE unless +the switch \nameref{complex} is turned on, which implements full complex +arithmetic in factoring, simplification, and functional values. +\name{complex} is ordinarily off. +\end{Comments} +\end{Constant} + + +\begin{Constant}{INFINITY} +The name \name{infinity} is used to represent the infinite positive number. +However, at the present time, arithmetic in terms of this operator reflects +finite arithmetic, rather than true operations on infinity. + +\end{Constant} + + +\begin{Variable}{LOW\_POW} +\index{degree}\index{polynomial} +The variable \name{low\_pow} is set by \nameref{coeff} to the lowest power +of the variable of interest in the given expression. You can access this +variable for use in further computation or display. + +\begin{Examples} +coeff((x+2*y)**6,y); & +\begin{multilineoutput}{6cm} +\{X^{6}, + 12*X^{5}, + 60*X^{4}, + 160*X^{3}, + 240*X^{2}, + 192*X, + 64\} +\end{multilineoutput}\\ +low_pow; & 0 \\ +coeff(x**2*(x*sin(y) + 1),x); + & \{0,0,1,SIN(Y)\} \\ +low_pow; & 2 +\end{Examples} + +\end{Variable} + + +\begin{Constant}{NIL} +\index{false} +\name{nil} represents the truth value {\it false} in symbolic mode, and is +a synonym for 0 in algebraic mode. It cannot be used for any other +purpose, even inside procedures or \nameref{for} loops. +\end{Constant} + + +\begin{Constant}{PI} +The identifier \name{pi} is reserved for use as the circular constant. +Its value is given by 3.14159265358..., which REDUCE gives to the current +decimal precision when REDUCE is in a floating-point mode. + +\begin{Comments} +\name{pi} may be used as a looping variable in a \nameref{for} statement, +or as a local variable in a \nameref{procedure}. Its value in such cases +will be taken from the local environment. +\end{Comments} +\end{Constant} + +\begin{Variable}{requirements} +\index{solve} +After an attempt to solve an inconsistent equation system +with parameters, the variable \name{requirements} contains a list +of expressions. These expressions define a set of conditions implicitly +equated with zero. Any solution to this system defines a setting for +the parameters sufficient to make the original system consistent. +\begin{Examples} +solve({x-a,x-y,y-1},{x,y}); & \{\}\\ +requirements;&\{a - 1\} +\end{Examples} +\end{Variable} + +\begin{Variable}{ROOT\_MULTIPLICITIES} +\index{root}\index{solve}\index{polynomial} +The \name{root\_multiplicities} variable is set to the list of the +multiplicities of the roots of an equation by the \nameref{solve} operator. + +\begin{Comments} +\nameref{solve} returns its solutions in a list. The multiplicities of +each solution are put in the corresponding locations of the list +\name{root\_multiplicities}. +\end{Comments} +\end{Variable} + + +\begin{Constant}{T} +The constant \name{t} stands for the truth value {\it true}. It cannot be used +as a scalar variable in a \nameref{block}, as a looping variable in a +\nameref{for} statement or as an \nameref{operator} name. + +\end{Constant} + Index: r36/help/XREDHELP.TEX ================================================================== --- r36/help/XREDHELP.TEX +++ r36/help/XREDHELP.TEX @@ -1,36 +1,36 @@ -\documentstyle[redindex]{article} - -\makeindex - -\begin{document} - -%\setcounter{page}{63} - -%\tracingall - -\input{intro} -\input{concept} -\input{variable} -\input{syntax} -\input{arith} -\input{boolean} -\input{command} -\input{algebra} -\input{declare} -\input{io} -\input{elemfn} -\input{switch} -\input{matrix} -\input{pk-groeb} -\input{hephys} -\input{pk-numer} -\input{pk-roots} -\input{pk-specf} -\input{taylor} -\input{pk-gplot} -\input{linalg} -\input{normform} -\input{pk-misc} -%\input{symbolic} -\input{outmode} -\end{document} +\documentstyle[redindex]{article} + +\makeindex + +\begin{document} + +%\setcounter{page}{63} + +%\tracingall + +\input{intro} +\input{concept} +\input{variable} +\input{syntax} +\input{arith} +\input{boolean} +\input{command} +\input{algebra} +\input{declare} +\input{io} +\input{elemfn} +\input{switch} +\input{matrix} +\input{pk-groeb} +\input{hephys} +\input{pk-numer} +\input{pk-roots} +\input{pk-specf} +\input{taylor} +\input{pk-gplot} +\input{linalg} +\input{normform} +\input{pk-misc} +%\input{symbolic} +\input{outmode} +\end{document} Index: r36/help/algebra.tex ================================================================== --- r36/help/algebra.tex +++ r36/help/algebra.tex @@ -1,1713 +1,1713 @@ -\section{Algebraic Operators} - -\begin{Operator}{APPEND} -\index{list} -The \name{append} operator constructs a new \nameref{list} -from the elements of its two arguments (which must be lists). - -\begin{Syntax} -\name{append}\(\meta{list},\meta{list}\) -\end{Syntax} - -\meta{list} must be a list, though it may be the empty list (\name{\{\}}). -Any arguments beyond the first two are ignored. - -\begin{Examples} -alist := \{1,2,\{a,b\}\}; & ALIST := \{1,2,\{A,B\}\} \\ -blist := \{3,4,5,sin(y)\}; & BLIST := \{3,4,5,SIN(Y)\} \\ -append(alist,blist); & \{1,2,\{A,B\},3,4,5,SIN(Y)\} \\ -append(alist,\{\}); & \{1,2,\{A,B\}\} \\ -append(list z,blist); & \{Z,3,4,5,SIN(Y)\} -\end{Examples} - -\begin{Comments} -The new list consists of the elements of the second list appended to the -elements of the first list. You can \name{append} new elements to the -beginning or end of an existing list by putting the new element in a -list (use curly braces or the operator \name{list}). This is -particularly helpful in an iterative loop. -\end{Comments} -\end{Operator} - -\begin{Operator}{ARBINT} -\index{arbitrary value} -The operator \name{arbint} is used to express arbitrary integer parts -of an expression, e.g. in the result of \nameref{solve} when -\nameref{allbranch} is on. -\begin{Examples} - -solve(log(sin(x+3)),x); & -\begin{multilineoutput}{6cm} -\{X=2*ARBINT(1)*PI - ASIN(1) - 3, - X=2*ARBINT(1)*PI + ASIN(1) + PI - 3\} -\end{multilineoutput} -\end{Examples} -\end{Operator} - -\begin{Operator}{ARBCOMPLEX} -\index{arbitrary value} -The operator \name{arbcomplex} is used to express arbitrary scalar parts -of an expression, e.g. in the result of \nameref{solve} when -the solution is parametric in one of the variable. -\begin{Examples} - -solve({x+3=y-2z,y-3x=0},{x,y,z}); & -\begin{multilineoutput}{6cm} -\{X=\rfrac{2*ARBCOMPLEX(1) + 3}{2}, - Y=\rfrac{3*ARBCOMPLEX(1) + 3}{2}, - Z=ARBCOMPLEX(1)\} -\end{multilineoutput} -\end{Examples} -\end{Operator} - -\begin{Operator}{ARGLENGTH} -\index{argument} -The operator \name{arglength} returns the number of arguments of the top-level -operator in its argument. - -\begin{Syntax} -\name{arglength}\(\meta{expression}\) -\end{Syntax} - -\meta{expression} can be any valid REDUCE algebraic expression. - -\begin{Examples} -arglength(a + b + c + d); & 4 \\ -arglength(a/b/c); & 2 \\ -arglength(log(sin(df(r**3*x,x)))); & 1 -\end{Examples} - -\begin{Comments} -In the first example, \name{+} is an n-ary operator, so the number of terms -is returned. In the second example, since \name{/} is a binary operator, the -argument is actually (a/b)/c, so there are two terms at the top level. In -the last example, no matter how deeply the operators are nested, there is -still only one argument at the top level. -\end{Comments} -\end{Operator} - - -\begin{Operator}{COEFF} -\index{coefficient} -The \name{coeff} operator returns the coefficients of the powers of the -specified variable in the given expression, in a \nameref{list}. - -\begin{Syntax} -\name{coeff}\(\meta{expression}\name{,}\meta{variable}\) -\end{Syntax} - -\meta{expression} is expected to be a polynomial expression, not a rational -expression. Rational expressions are accepted when the switch -\nameref{ratarg} is on. \meta{variable} must be a kernel. The results are -returned in a list. - -\begin{Examples} -coeff((x+y)**3,x); & \{Y^{3} ,3*Y^{2} ,3*Y,1\} \\ -coeff((x+2)**4 + sin(x),x); & \{SIN(X) + 16,32,24,8,1\} \\ -high_pow; & 4 \\ -low_pow; & 0 \\ -ab := x**9 + sin(x)*x**7 + sqrt(y); - & AB := SQRT(Y) + SIN(X)*X^{7} + X^{9}\\ -coeff(ab,x); & \{SQRT(Y),0,0,0,0,0,0,SIN(X),0,1\} -\end{Examples} -\begin{Comments} -The variables \nameref{high\_pow} and \nameref{low\_pow} are set to the -highest and lowest powers of the variable, respectively, appearing in the -expression. - -The coefficients are put into a list, with the coefficient of the lowest -(constant) term first. You can use the usual list access methods -(\name{first}, \name{second}, \name{third}, \name{rest}, \name{length}, and -\name{part}) to extract them. If a power does not appear in the -expression, the corresponding element of the list is zero. Terms involving -functions of the specified variable but not including powers of it (for -example in the expression \name{x**4 + 3*x**2 + tan(x)}) are placed in the -constant term. - -Since the \name{coeff} command deals with the expanded form of the expression, -you may get unexpected results when \nameref{exp} is off, or when -\nameref{factor} or \nameref{ifactor} are on. - -If you want only a specific coefficient rather than all of them, use the -\nameref{coeffn} operator. - -\end{Comments} -\end{Operator} - - -\begin{Operator}{COEFFN} -\index{coefficient} -The \name{coeffn} operator takes three arguments: an expression, a kernel, and -a non-negative integer. It returns the coefficient of the kernel to that -integer power, appearing in the expression. - -\begin{Syntax} -\name{coeffn}\(\meta{expression},\meta{kernel},\meta{integer}\) -\end{Syntax} - -\meta{expression} must be a polynomial, unless \nameref{ratarg} is on which -allows rational expressions. \meta{kernel} must be a kernel, and -\meta{integer} must be a non-negative integer. - -\begin{Examples} - -ff := x**7 + sin(y)*x**5 + y**4 + x + 7; & - FF := SIN(Y)*X^{5} + X^{7} + X + Y^{4} + 7 \\ -coeffn(ff,x,5); & SIN(Y) \\ -coeffn(ff,z,3); & 0 \\ -coeffn(ff,y,0); & SIN(Y)*X^{5} + X^{7} + X + 7 \\ - -rr := 1/y**2+y**3+sin(y); & -RR := \rfrac{SIN(Y)*Y^{2} + Y^{5} + 1}{Y^{2}} \\ -on ratarg; \\ - -coeffn(rr,y,-2); & ***** -2 invalid as COEFFN index \\ - -coeffn(rr,y,5); & \rfrac{1}{Y^{2}}\\ - -\end{Examples} - -\begin{Comments} -If the given power of the kernel does not appear in the expression, -\name{coeffn} returns 0. Negative powers are never detected, even if -they appear in the expression and \nameref{ratarg} are on. \name{coeffn} -with an integer argument of 0 returns any terms in the expression that -do {\em not} contain the given kernel. -\end{Comments} -\end{Operator} - - -\begin{Operator}{CONJ} -\index{conjugate}\index{complex} - -\begin{Syntax} -\name{conj}\(\meta{expression}\) or \name{conj} \meta{simple\_expression} -\end{Syntax} -This operator returns the complex conjugate of an expression, if that -argument has an numerical value. A non-numerical argument is returned as -an expression in the operators \nameref{repart} and \nameref{impart}. - -\begin{Examples} -conj(1+i); & 1-I \\ -conj(a+i*b); & REPART(A) - REPART(B)*I - IMPART(A)*I - IMPART(B) -\end{Examples} - -\end{Operator} - -\begin{Operator}{CONTINUED_FRACTION} -\index{approximation}\index{rational numbers} - -\begin{Syntax} -\name{continued\_fraction}\(\meta{num}\) -or \name{continued\_fraction}\( \meta{num},\meta{size}\) -\end{Syntax} -This operator approximates the real number \meta{num} -( \nameref{rational} number, \nameref{rounded} number) -into a continued fraction. The result is a list of two elements: the -first one is the rational value of the approximation, the second one -is the list of terms of the continued fraction which represents the -same value according to the definition \name{t0 +1/(t1 + 1/(t2 + ...))}. -Precision: the second optional parameter \meta{size} is an upper bound -for the absolute value of the result denominator. If omitted, the -approximation is performed up to the current system precision. - - -\begin{Examples} -continued_fraction pi; - & \{\rfrac{1146408},{364913},\{3,7,15,1,292,1,1,1,2,1\}\} \\ -continued_fraction(pi,100); - & \{\rfrac{22},{7},\{3,7\}\} \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{DECOMPOSE} -\index{decomposition}\index{polynomial} -The \name{decompose} operator takes a multivariate polynomial as argument, -and returns an expression and a \nameref{list} of -\nameref{equation}s from which the -original polynomial can be found by composition. - -\begin{Syntax} -\name{decompose}\(\meta{expression}\) or \name{decompose} - \meta{simple\_expression} -\end{Syntax} - -\begin{Examples} -\begin{multilineinput} -decompose(x^8-88*x^7+2924*x^6-43912*x^5+263431*x^4- - 218900*x^3+65690*x^2-7700*x+234) -\end{multilineinput} - & {U^{2} + 35*U + 234, U=V^{2} + 10*V, V=X^{2} - 22*X} \\ - decompose(u^2+v^2+2u*v+1) & {W^{2} + 1, W=U + V} -\end{Examples} - -\begin{Comments} -Unlike factorization, this decomposition is not unique. Further -details can be found in V.S. Alagar, M.Tanh, \meta{Fast Polynomial -Decomposition}, Proc. EUROCAL 1985, pp 150-153 (Springer) and J. von zur -Gathen, \meta{Functional} -\meta{Decomposition of Polynomials: the Tame Case}, J. -Symbolic Computation (1990) 9, 281-299. -\end{Comments} -\end{Operator} - - -\begin{Operator}{DEG} -\index{degree}\index{polynomial} -The operator \name{deg} returns the highest degree of its variable argument -found in its expression argument. - -\begin{Syntax} -\name{deg}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} is expected to be a polynomial expression, not a rational -expression. Rational expressions are accepted when the switch -\nameref{ratarg} is on. \meta{variable} must be a \nameref{kernel}. The -results are returned in a list. - -\begin{Examples} - -deg((x+y)**5,x); & 5 \\ - -deg((a+b)*(c+2*d)**2,d); & 2 \\ - -deg(x**2 + cos(y),sin(x)); \\ - -deg((x**2 + sin(x))**5,sin(x)); & 5 -\end{Examples} -\end{Operator} - - -\begin{Operator}{DEN} -\index{denominator}\index{rational expression} -The \name{den} operator returns the denominator of its argument. - -\begin{Syntax} -\name{den}\(\meta{expression}\) -\end{Syntax} - -\meta{expression} is ordinarily a rational expression, but may be any valid -scalar REDUCE expression. - -\begin{Examples} - -a := x**3 + 3*x**2 + 12*x; & A := X*(X^{2} + 3*X + 12) \\ - -b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ - -den(a/b); & SIN(X) + 4*Y \\ - -den(aa/4 + bb/5); & 20 \\ - -den(100/6); & 3 \\ - -den(sin(x)); & 1 -\end{Examples} - -\begin{Comments} -\name{den} returns the denominator of the expression after it has been -simplified by REDUCE. As seen in the examples, this includes putting -sums of rational expressions over a common denominator, and reducing -common factors where possible. If the expression does not have any -other denominator, 1 is returned. - -Switch settings, such as \nameref{mcd} or \nameref{rational}, have an -effect on the denominator of an expression. -\end{Comments} -\end{Operator} - - -\begin{Operator}{DF} -\index{derivative}\index{partial derivative} -The \name{df} operator finds partial derivatives with respect to one or -more variables. - -\begin{TEX} -\begin{Syntax} - \name{df}\(\meta{expression}\name{,}\meta{var} - \&optional\(\name{,}\meta{number}\) - \{\name{,}\meta{var}\&option\(\name{,}\meta{number}\)\}\optional\) -\end{Syntax} -\end{TEX} -\begin{INFO}{ -\begin{Syntax} - \name{df}\(\meta{expression}\name{,}\meta{var} - [\name{,}\meta{number}\] - \{\name{,}\meta{var} [ \name{,}\meta{number}] \} \) -\end{Syntax} -}\end{INFO} - -\meta{expression} can be any valid REDUCE algebraic expression. \meta{var} -must be a \nameref{kernel}, and is the differentiation variable. -\meta{number} must be a non-negative integer. - -\begin{Examples} - -df(x**2,x); & 2*X \\ - -df(x**2*y + sin(y),y); & COS(Y) + X^{2} \\ - -df((x+y)**10,z); & 0 \\ - - -df(1/x**2,x,2); & \rfrac{6}{X^{4}}\\ - -df(x**4*y + sin(y),y,x,3); & 24*X \\ - -for all x let df(tan(x),x) = sec(x)**2; \\ - -df(tan(3*x),x); & 3*SEC(3*X)^{2} -\end{Examples} -\begin{Comments} -An error message results if a non-kernel is entered as a differentiation -operator. If the optional number is omitted, it is assumed to be 1. -See the declaration \nameref{depend} to establish dependencies for implicit -differentiation. - -You can define your own differentiation rules, expanding REDUCE's -capabilities, using the \nameref{let} command as shown in the last example -above. Note that once you add your own rule for differentiating a -function, it supersedes REDUCE's normal handling of that function for the -duration of the REDUCE session. If you clear the rule -(\nameref{clearrules}), you don't get back -to the previous rule. -\end{Comments} -\end{Operator} - -\begin{Operator}{EXPAND\_CASES} -\index{solve} -When a \nameref{root\_of} form in a result of \nameref{solve} -has been converted to a \nameref{one\_of} form, \name{expand\_cases} -can be used to convert this into form corresponding to the -normal explicit results of \nameref{solve}. See \nameref{root\_of}. -\end{Operator} - -\begin{Operator}{EXPREAD} -\index{input} -\begin{Syntax} -\name{expread}\(\) -\end{Syntax} - -\name{expread} reads one well-formed expression from the current input -buffer and returns its value. - -\begin{Examples} -expread(); a+b; & A + B -\end{Examples} - -\end{Operator} - - -\begin{Operator}{FACTORIZE} -\index{factorize}\index{polynomial} -The \name{factorize} operator factors a given expression. -\begin{Syntax} -\name{factorize}\(\meta{expression}\) -\end{Syntax} - -\meta{expression} should be a polynomial, otherwise an error will result. - -\begin{Examples} - -fff := factorize(x^3 - y^3); & - \{X - Y,X^{2} + X*Y + Y^{2}\} \\ -fac1 := first fff; & FAC1 := X - Y \\ -factorize(x^15 - 1); & -\begin{multilineoutput}{5cm} - \{X - 1, - X^{2} + X + 1, - X^{4} + X^{3} + X^{2} + X + 1, - X^{8} - X^{7} + X^{6} - X^{5} + X^{4} - X + 1\} -\end{multilineoutput}\\ -lastone := part(ws,length ws); & - LASTONE := X^{8} - X^{7} + X^{6} - X^{5} + X^{4} - X + 1 \\ -setmod 2; & 1 \\ -on modular; \\ -factorize(x^15 - 1); & -\begin{multilineoutput}{5cm} -\{X + 1, - X^{2} + X + 1, - X^{4} + X + 1, - X^{4} + X^{3} + 1, - X^{4} + X^{3} + X^{2} + X + 1\} -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -The \name{factorize} command returns the factors it finds as a \nameref{list}. -You can therefore use the usual list access methods (\nameref{first}, -\nameref{second}, \nameref{third}, \nameref{rest}, \nameref{length} and -\nameref{part}) to extract the factors. - -If the \meta{expression} given to \name{factorize} is an integer, it will be -factored into its prime components. To factor any integer factor of a -non-numerical expression, the switch \nameref{ifactor} should be turned on. -Its default is off. \nameref{ifactor} has effect only when factoring is -explicitly done by \name{factorize}, not when factoring is automatically -done with the \nameref{factor} switch. If full factorization is not -needed the switch \nameref{limitedfactors} allows you to reduce the -computing time of calls to \name{factorize}. - -Factoring can be done in a modular domain by calling \name{factorize} when -\nameref{modular} is on. You can set the modulus with the \nameref{setmod} -command. The last example above shows factoring modulo 2. - -For general comments on factoring, see comments under the switch -\nameref{factor}. -\end{Comments} -\end{Operator} - - -\begin{Operator}{HYPOT} - -\begin{Syntax} -hypot(\meta{expression},\meta{expression}) -\end{Syntax} - -If \name{rounded} is on, and the two arguments evaluate to numbers, this -operator returns the square root of the sums of the squares of the -arguments in a manner that avoids intermediate overflow. In other cases, -an expression in the original operator is returned. - -\begin{Examples} -hypot(3,4); & HYPOT(3,4) \\ -on rounded; \\ -ws; & 5.0 \\ -hypot(a,b); & HYPOT(A,B) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{IMPART} -\index{imaginary part}\index{complex} -\begin{Syntax} -\name{impart}\(\meta{expression}\) or \name{impart} \meta{simple\_expression} -\end{Syntax} -This operator returns the imaginary part of an expression, if that -argument has an numerical value. A non-numerical argument is returned as -an expression in the operators \nameref{repart} and \name{impart}. -\begin{Examples} -impart(1+i); & 1 \\ -impart(a+i*b); & REPART(B) + IMPART(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{INT} -\index{integration} -The \name{int} operator performs analytic integration on a variety of -functions. - -\begin{Syntax} -\name{int}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} can be any scalar expression. involving polynomials, log -functions, exponential functions, or tangent or arctangent expressions. -\name{int} attempts expressions involving error functions, dilogarithms -and other trigonometric expressions. Integrals involving algebraic -extensions (such as square roots) may not succeed. \meta{kernel} must be a -REDUCE \nameref{kernel}. - -\begin{Examples} -int(x**3 + 3,x); & \rfrac{X*(X^{3} + 12)}{4} \\\\ -int(sin(x)*exp(2*x),x); - & - \rfrac{E^{2*X}*(COS(X) - 2*SIN(X))}{5} \\ -int(1/(x^2-2),x); - & \rfrac{SQRT(2)*(LOG( - SQRT(2) + X) - LOG(SQRT(2) + X))}{4} \\ -int(sin(x)/(4 + cos(x)**2),x); - & - \rfrac{ATAN(\rfrac{COS(X)}{2})}{2} \\\\ -int(1/sqrt(x^2-x),x); & INT(\rfrac{SQRT(X)*SQRT(X - 1)}{X^{2}-X},X) -\end{Examples} - -\begin{Comments} -Note that REDUCE couldn't handle the last integral with its default -integrator, since the integrand involves a square root. However, -the integral can be found using the \nameref{algint} package. -Alternatively, you could add a rule using the \nameref{let} statement -to evaluate this integral. - -The arbitrary constant of integration is not shown. Definite integrals can -be found by evaluating the result at the limits of integration (use -\nameref{rounded}) and subtracting the lower from the higher. Evaluation can -be easily done by the \nameref{sub} operator. - -When \name{int} cannot find an integral it returns an expression -involving formal \name{int} expressions unless the switch -\nameref{failhard} has been set. If not all of the expression -can be integrated, the switch \nameref{nolnr} controls whether a partially -integrated result should be returned or not. - -\end{Comments} -\end{Operator} - - -\begin{Operator}{INTERPOL} -\index{interpolation}\index{polynomial}\index{approximation} -\name{interpol} generates an interpolation polynomial. -\begin{Syntax} - interpol(\meta{values},\meta{variable},\meta{points}) -\end{Syntax} - -\meta{values} and \meta{points} are \nameref{list}s of equal length and -\meta{variable} is an algebraic expression (preferably a \nameref{kernel}). -The interpolation polynomial is generated in the given variable of degree -length(\meta{values})-1. The unique polynomial \name{f} is defined by the -property that for corresponding elements \name{v} of \meta{values} and -\name{p} of \meta{points} the relation \name{f(p)=v} holds. - -\begin{Examples} -f := for i:=1:4 collect(i**3-1); & F := {0,7,26,63} \\ -p := {1,2,3,4}; & P := {1,2,3,4} \\ -interpol(f,x,p); & X^{3} - 1 -\end{Examples} - -\begin{Comments} -The Aitken-Neville interpolation algorithm is used which guarantees a -stable result even with rounded numbers and an ill-conditioned problem. -\end{Comments} -\end{Operator} - - -\begin{Operator}{LCOF} -\index{coefficient}\index{polynomial} -The \name{lcof} operator returns the leading coefficient of a given expression -with respect to a given variable. -\begin{Syntax} -\name{lcof}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, -a rational expression may also be used, otherwise an error results. -\meta{kernel} must be a \nameref{kernel}. - -\begin{Examples} -lcof((x+2*y)**5,y); & 32 \\ -lcof((x + y*sin(x))**2 + cos(x)*sin(x)**2,sin(x)); - & COS(X)^{2} + Y \\ -lcof(x**2 + 3*x + 17,y); & X^{2} + 3*X + 17 -\end{Examples} - -\begin{Comments} -If the kernel does not appear in the expression, \name{lcof} returns the -expression. -\end{Comments} -\end{Operator} - - -\begin{Operator}{LENGTH} -\index{list} -The \name{length} operator returns the number of items in a \nameref{list}, the -number of -terms in an expression, or the dimensions of an array or matrix. -\begin{Syntax} -\name{length}\(\meta{expr}\) or \name{length} \meta{expr} -\end{Syntax} - -\meta{expr} can be a list structure, an array, a matrix, or a scalar expression. - -\begin{Examples} -alist := \{a,b,\{ww,xx,yy,zz\}\}; & - ALIST := \{A,B,\{WW,XX,YY,ZZ\}\} \\ -length alist; & 3 \\ -length third alist; & 4 \\ -dlist := \{d\}; & DLIST := \{D\} \\ -length rest dlist; & 0 \\ -matrix mmm(4,5); \\ -length mmm; & \{4,5\} \\ -array aaa(5,3,2); \\ -length aaa; & \{6,4,3\} \\ -eex := (x+3)**2/(x-y); & EEX := \rfrac{X^{2} + 6*X + 9}{X - Y} \\ -length eex; & 5 -\end{Examples} - -\begin{Comments} -An item in a list that is itself a list only counts as one item. An error -message will be printed if \name{length} is called on a matrix which has -not had its dimensions set. The \name{length} of an array includes the -zeroth element of each dimension, showing the full number of elements -allocated. (Declaring an array \IFTEX{$A$}{A} with \IFTEX{$n$}{n} elements -allocates \IFTEX{$ A(0),A(1),\ldots,A(n)$}{A(0),A(1),...,A(n)}.) The -\name{length} of an expression is the total number of additive terms -appearing in the numerator and denominator of the expression. Note that -subtraction of a term is represented internally as addition of a negative -term. -\end{Comments} -\end{Operator} - - -\begin{Operator}{LHS} -\index{left-hand side}\index{equation} -The \name{lhs} operator returns the left-hand side of an \nameref{equation}, -such as those -returned in a list by \nameref{solve}. -\begin{Syntax} -\name{lhs}\(\meta{equation}\) or \name{lhs} \meta{equation} - -\end{Syntax} - -\meta{equation} must be an equation of the form \\ -\name{left-hand side} \name{=} \name{right-hand side}. - -\begin{Examples} -polly := (x+3)*(x^4+2x+1); & -POLLY := X^{5} + 3*X^{4} + 2*X^{2} + 7*X + 3 \\ -pollyroots := solve(polly,x); & -\begin{multilineoutput}{1cm} -POLLYROOTS := \{X=ROOT_OF(X_^{3} - X_^{2} + X_ + 1,X_), - X=-1, - X=-3\} -\end{multilineoutput} \\ -variable := lhs first pollyroots; & -VARIABLE := X -\end{Examples} -\end{Operator} - - -\begin{Operator}{LIMIT} -\index{limit}\index{l'Hopital's rule} -LIMITS is a fast limit package for REDUCE for functions which are -continuous except for computable poles and singularities, based on -some earlier work by Ian Cohen and John P. Fitch. The Truncated -Power Series package is used for non-critical points, at which -the value of the function is the constant term in the expansion -around that point. l'Hopital's rule is used in critical cases, -with preprocessing of 1-1 forms and reformatting of product forms -in order to apply l'Hopital's rule. A limited amount of bounded -arithmetic is also employed where applicable. - -\begin{Syntax} -\name{limit}\(\meta{expr},\meta{var},\meta{limpoint}\) or \\ -\name{limit!+}\(\meta{expr},\meta{var},\meta{limpoint}\) or \\ -\name{limit!-}\(\meta{expr},\meta{var},\meta{limpoint}\) -\end{Syntax} - -where \meta{expr} is an expression depending of the variable \meta{var} -(a \nameref{kernel}) and \meta{limpoint} is the limit point. -If the limit depends upon the direction of approach to the \meta{limpoint}, -the operators \name{limit!+} and \name{limit!-} may be used. - -\begin{Examples} -limit(x*cot(x),x,0);&0\\ -limit((2x+5)/(3x-2),x,infinity);&\rfrac{2}{3}\\ -\end{Examples} - -\end{Operator} - - -\begin{Operator}{LPOWER} -\index{leading power}\index{polynomial} -The \name{lpower} operator returns the leading power of an expression with -respect to a kernel. 1 is returned if the expression does not depend on -the kernel. -\begin{Syntax} -\name{lpower}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, -a rational expression may also be used, otherwise an error results. -\meta{kernel} must be a \nameref{kernel}. - -\begin{Examples} -lpower((x+2*y)**6,y); & Y^{6} \\ -lpower((x + cos(x))**8 + df(x**2,x),cos(x)); - & COS(X)^{8} \\ -lpower(x**3 + 3*x,y); & 1 -\end{Examples} -\end{Operator} - -\begin{Operator}{LTERM} -\index{leading term}\index{polynomial} -The \name{lterm} operator returns the leading term of an expression with -respect to a kernel. The expression is returned if it does not depend on -the kernel. -\begin{Syntax} -\name{lterm}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, -a rational expression may also be used, otherwise an error results. -\meta{kernel} must be a \nameref{kernel}. - -\begin{Examples} -lterm((x+2*y)**6,y); & 64*Y^{6} \\ -lterm((x + cos(x))**8 + df(x**2,x),cos(x)); - & COS(X)^{8} \\ -lterm(x**3 + 3*x,y); & X^{3} + 3X -\end{Examples} -\end{Operator} - - -\begin{Operator}{MAINVAR} -\index{main variable}\index{polynomial} -The \name{mainvar} operator returns the main variable (in the system's -internal representation) of its argument. -\begin{Syntax} -\name{mainvar}\(\meta{expression}\) - -\end{Syntax} - -\meta{expression} is usually a polynomial, but may be any valid REDUCE -scalar expression. In the case of a rational function, the main variable -of the numerator is returned. The main variable returned is a -\nameref{kernel}. - -\begin{Examples} -test := (a + b + c)**2; & - TEST := A^{2} + 2*A*B + 2*A*C + B^{2} + 2*B*C + C^{2} \\ -mainvar(test); & A \\ -korder c,b,a; \\ -mainvar(test); & C \\ -mainvar(2*cos(x)**2); & COS(X) \\ -mainvar(17); & 0 -\end{Examples} - -\begin{Comments} -The main variable is the first variable in the canonical ordering of -kernels. Generally, alphabetically ordered functions come first, then -alphabetically ordered identifiers (variables). Numbers come last, and as -far as \name{mainvar} is concerned belong in the family \name{0}. The -canonical ordering can be changed by the declaration \nameref{korder}, as -shown above. -\end{Comments} -\end{Operator} - - -\begin{Operator}{MAP} -\index{map}\index{composite structure} -The \name{map} operator applies a uniform evaluation pattern -to all members of a composite structure: a \nameref{matrix}, -a \nameref{list} or the arguments of an \nameref{operator} expression. -The evaluation pattern can be a -unary procedure, an operator, or an algebraic expression with -one free variable. -\begin{Syntax} - \name{map}\(\meta{function},\meta{object}\) -\end{Syntax} -\meta{object} is a list, a matrix or an operator expression. - -\meta{function} is -the name of an operator for a single argument: the operator - is evaluated once with each element of \meta{object} as its single argument, - -or an algebraic expression with exactly one \nameref{free variable}, that is -a variable preceded by the tilde symbol: the expression - is evaluated for each element of \meta{object} where the element is - substituted for the free variable, - -or a replacement \nameref{rule} of the form -\begin{Syntax} - \name{var} => \name{rep} -\end{Syntax} - where \meta{var} is a variable (a \meta{kernel} without subscript) - and \meta{rep} is an expression which contains \meta{var}. - Here \name{rep} is evaluated for each element of \meta{object} where - the element is substituted for \name{var}. \name{var} may be - optionally preceded by a tilde. - -The rule form for \meta{function} is needed when more than -one free variable occurs. - -\begin{Examples} -map(abs,{1,-2,a,-a}); & {1,2,abs(a),abs(a)} \\ -map(int(~w,x), mat((x^2,x^5),(x^4,x^5))); & -\begin{multilineoutput}{1cm} - [ 3 6 ] - [ x x ] - [---- ----] - [ 3 6 ] - [ ] - [ 5 6 ] - [ x x ] - [---- ----] - [ 5 6 ] -\end{multilineoutput}\\ -map(~w*6, x^2/3 = y^3/2 -1); & 2*x^2=3*(y^3-2)\\ -\end{Examples} - -\begin{Comments} -You can use \name{map} in nested expressions. It is not allowed to -apply \name{map} for a non-composed object, e.g. an identifier or a number. -\end{Comments} -\end{Operator} - - - -\begin{Command}{MKID} -\index{identifier} -The \name{mkid} command constructs an identifier, given a stem and an identifier -or an integer. -\begin{Syntax} -\name{mkid}\(\meta{stem},\meta{leaf}\) -\end{Syntax} - -\meta{stem} can be any valid REDUCE identifier that does not include escaped -special characters. \meta{leaf} may be an integer, including one given by a -local variable in a \nameref{for} loop, or any other legal group of -characters. - -\begin{Examples} -mkid(x,3); & X3 \\ -factorize(x^15 - 1); & \begin{multilineoutput}{6cm} -\{X - 1, - X^{2} + X + 1, - X^{4} + X^{3} + X^{2} + X + 1, - X^{8} - X^{7} + X^{5} - X^{4} + X^{3} - X + 1\} -\end{multilineoutput}\\ - -for i := 1:length ws do write set(mkid(f,i),part(ws,i)); - & \begin{multilineoutput}{6cm} -X^{8} - X^{7} + X^{5} - X^{4} + X^{3} - X + 1 -X^{4} + X^{3} + X^{2} + X + 1 -X^{2} + X + 1 -X - 1 -\end{multilineoutput} \\ -\end{Examples} - -\begin{Comments} -You can use \name{mkid} to construct identifiers from inside procedures. This -allows you to handle an unknown number of factors, or deal with variable -amounts of data. It is particularly helpful to attach identifiers to the -answers returned by \name{factorize} and \name{solve}. -\end{Comments} -\end{Command} - - -\begin{Operator}{NPRIMITIVE} -\index{primitive part}\index{polynomial} -\begin{Syntax} -\name{nprimitive}\(\meta{expression}\) or \name{nprimitive} - \meta{simple\_expression} -\end{Syntax} -This operator returns the numerically-primitive part of any scalar -expression. In other words, any overall integer factors in the expression -are removed. - -\begin{Examples} -nprimitive((2x+2y)^2); & X^{2} + 2*X*Y + Y^{2} \\ -nprimitive(3*a*b*c); & 3*A*B*C -\end{Examples} -\end{Operator} - - -\begin{Operator}{NUM} -\index{numerator}\index{rational expression} -The \name{num} operator returns the numerator of its argument. -\begin{Syntax} -\name{num}\(\meta{expression}\) or \name{num} \meta{simple\_expression} -\end{Syntax} - -\meta{expression} can be any valid REDUCE scalar expression. - -\begin{Examples} -num(100/6); & 50 \\ -num(a/5 + b/6); & 6*A + 5*B \\ -num(sin(x)); & SIN(X) -\end{Examples} - -\begin{Comments} -\name{num} returns the numerator of the expression after it has been simplified -by REDUCE. As seen in the examples, this includes putting sums of rational -expressions over a common denominator, and reducing common factors where -possible. If the expression is not a rational expression, it is returned -unchanged. -\end{Comments} -\end{Operator} - - -\begin{Operator}{ODESOLVE} -\index{differential equation}\index{solve} -The \name{odesolve} package is a solver for ordinary differential -equations. At the present time it has still limited capabilities: - - 1. it can handle only a single scalar equation presented as an - algebraic expression or equation, and - - 2. it can solve only first-order equations of simple types, linear - equations with constant coefficients and Euler equations. - -These solvable types are exactly those for which Lie symmetry -techniques give no useful information. - -\begin{Syntax} - -\name{odesolve}\(\meta{expr},\meta{var1},\meta{var2}\) - -\end{Syntax} - -\meta{expr} is a single scalar expression such that \meta{expr}=0 -is the ordinary differential equation (ODE for short) to be solved, or -is an equivalent \nameref{equation}. - -\meta{var1} is the name of the dependent variable, -\meta{var2} is the name of the independent variable. - -A differential in \meta{expr} is expressed using the \nameref{df} -operator. Note that in most cases you must declare explicitly -\meta{var1} to depend of \meta{var2} using a \nameref{depend} -declaration -- otherwise the derivative might be evaluated to -zero on input to \name{odesolve}. - -The returned value is a list containing the equation giving the general -solution of the ODE (for simultaneous equations this will be a -list of equations eventually). It will contain occurrences of -the operator \name{arbconst} for the arbitrary constants in the general -solution. The arguments of \name{arbconst} should be new. -A counter \name{!!arbconst} is used to arrange this. - -\begin{Examples} -depend y,x;\\ -\% A first-order linear equation, with an initial condition\\ -ode:=df(y,x) + y * sin x/cos x - 1/cos x$\\ -odesolve(ode,y,x); & \{y=arbconst(1)*cos(x) + sin(x)\} -\end{Examples} - -\end{Operator} - - -\begin{Type}{ONE\_OF} -The operator \name{one\_of} is used to represent an indefinite choice -of one element from a finite set of objects. -\begin{Examples} -x=one_of{1,2,5}\\ -\explanation{this equation encodes that x can take one of the values -1,2 or 5}\\ -\end{Examples} -REDUCE generates a \name{one\_of} form in cases when an implicit -\name{root\_of} expression could be converted to an explicit solution set. -A \name{one\_of} form can be converted to a \name{solve} solution using -\nameref{expand\_cases}. See \nameref{root\_of}. -\end{Type} - -\begin{Operator}{PART} -\index{decomposition} -The operator \name{part} permits the extraction of various parts or -operators of expressions and \nameref{list}\name{s}. -\begin{Syntax} -\name{part}\(\meta{expression,integer}\{,\meta{integer}\}\optional\) -\end{Syntax} - -\meta{expression} can be any valid REDUCE expression or a list, {\it -integer} may be an expression that evaluates to a positive or negative -integer or 0. A positive integer \meta{n} picks up the {\it n} th term, -counting from the first term toward the end. A negative integer {\it n} -picks up the {\it n} th term, counting from the back toward the front. The -integer 0 picks up the operator (which is \name{LIST} when the expression -is a \ref{list}). - -\begin{Examples} -part((x + y)**5,4); & 10*X^{2}*Y^{3} \\ -part((x + y)**5,4,2); & X^{2} \\ -part((x + y)**5,4,2,1); & X \\ -part((x + y)**5,0); & PLUS \\ -part((x + y)**5,-5); & 5*X *Y^{4} \\ -part((x + y)**5,4) := sin(x); & - X^{5} + 5*X^{4}*Y + 10*X^{3}*Y^{2} + SIN(X) + 5*X*Y^{4} + Y^{5} \\ -alist := \{x,y,\{aa,bb,cc\},x**2*sqrt(y)\}; & - ALIST := \{X,Y,\{AA,BB,CC\},SQRT(Y)*X^{2}\} \\ -part(alist,3,2); & BB \\ -part(alist,4,0); & TIMES -\end{Examples} - -\begin{Comments} -Additional integer arguments after the first one examine the -terms recursively, as shown above. In the third line, the fourth term -is picked from the original polynomial, \IFTEX{$10x^2y^3$}{10x^2y^3}, -then the second term from that, \IFTEX{$x^2$}{x^2}, and finally the first -component, \IFTEX{$x$}{x}. If an integer's absolute value is too large for -the appropriate expression, a message is given. - -\name{part} works on the form of the expression as printed, or as it would -have been printed at that point of the calculation, bearing in mind the -current switch settings. It is important to realize that the switch settings -change the operation of \name{part}. \nameref{pri} must be on when -\name{part} is used. - -When \name{part} is used on a polynomial expression that has minus signs, the -\name{+} is always returned as the top-level operator. The minus is found -as a unary operator attached to the negative term. - -\name{part} can also be used to change the relevant part of the expression or -list as shown in the sixth example line. The \name{part} operator returns the -changed expression, though original expression is not changed. You can -also use \name{part} to change the operator. -\end{Comments} -\end{Operator} - -\begin{Operator}{PF} -\index{partial fraction}\index{rational expression} -\begin{Syntax} -pf(\meta{expression},\meta{variable}) -\end{Syntax} - -\name{pf} transforms \meta{expression} into a \nameref{list} of partial fraction -s -with respect to the main variable, \meta{variable}. \name{pf} does a -complete partial fraction decomposition, and as the algorithms used are -fairly unsophisticated (factorization and the extended Euclidean -algorithm), the code may be unacceptably slow in complicated cases. -\begin{Examples} -pf(2/((x+1)^2*(x+2)),x); & - \{\rfrac{2}{X + 2},\rfrac{-2}{X + 1},\rfrac{2}{X^{2} + 2*X + 1}\} \\ -off exp; \\ -pf(2/((x+1)^2*(x+2)),x); - & \{\rfrac{2}{X + 2},\rfrac{- 2}{X + 1},\rfrac{2}{(X + 1)^{2}}\} \\ -for each j in ws sum j; & \rfrac{2}{( + 2)*(X + 1)^{2}} -\end{Examples} - -\begin{Comments} -If you want the denominators in factored form, turn \nameref{exp} off, as -shown in the second example above. As shown in the final example, the -\nameref{for} \name{each} construct can be used to recombine the terms. -Alternatively, one can use the operations on lists to extract any desired -term. -\end{Comments} - -\end{Operator} - - -\begin{Operator}{PROD} -\index{Gosper algorithm}\index{product} -The operator \name{prod} returns -the indefinite or definite product of a given expression. - -\begin{Syntax} - -\name{prod}\(\meta{expr},\meta{k}[,\meta{lolim} [,\meta{uplim} ]]\) - -\end{Syntax} - -where \meta{expr} is the expression to be multiplied, \meta{k} is the -control variable (a \nameref{kernel}), and \meta{lolim} and \meta{uplim} -uplim are the optional lower and upper limits. If \meta{uplim} is -not supplied the upper limit is taken as \meta{k}. The -Gosper algorithm is used. If there is no closed form solution, -the operator returns the input unchanged. - -\begin{Examples} -prod(k/(k-2),k);&k*( - k + 1)\\ -\end{Examples} -\end{Operator} - - -\begin{Operator}{REDUCT} -\index{reductum}\index{polynomial} -The \name{reduct} operator returns the remainder of its expression after the -leading term with respect to the kernel in the second argument is removed. -\begin{Syntax} -\name{reduct}\(\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, -a rational expression may also be used, otherwise an error results. -\meta{kernel} must be a \nameref{kernel}. - -\begin{Examples} -reduct((x+y)**3,x); & Y*(3*X^{2} + 3*X*Y + Y^{2}) \\ -reduct(x + sin(x)**3,sin(x)); & X \\ -reduct(x + sin(x)**3,y); & 0 -\end{Examples} - -\begin{Comments} -If the expression does not contain the kernel, \name{reduct} returns 0. -\end{Comments} -\end{Operator} - - -\begin{Operator}{REPART} -\index{real part}\index{complex} -\begin{Syntax} -\name{repart}\(\meta{expression}\) or \name{repart} \meta{simple\_expression} -\end{Syntax} - -This operator returns the real part of an expression, if that argument has an -numerical value. A non-numerical argument is returned as an expression in -the operators \name{repart} and \nameref{impart}. -\begin{Examples} -repart(1+i); & 1 \\ -repart(a+i*b); & REPART(A) - IMPART(B) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{RESULTANT} -\index{polynomial} -The \name{resultant} operator computes the resultant of two polynomials with -respect to a given variable. If the resultant is 0, the polynomials have -a root in common. -\begin{Syntax} - \name{resultant}\(\meta{expression},\meta{expression},\meta{kernel}\) -\end{Syntax} - -\meta{expression} must be a polynomial containing \meta{kernel} ; -\meta{kernel} must be a \nameref{kernel}. - -\begin{Examples} -resultant(x**2 + 2*x + 1,x+1,x); & 0 \\ -resultant(x**2 + 2*x + 1,x-3,x); & 16 \\ -\begin{multilineinput} -resultant(z**3 + z**2 + 5*z + 5, - z**4 - 6*z**3 + 16*z**2 - 30*z + 55, - z); -\end{multilineinput} & 0 \\ -resultant(x**3*y + 4*x*y + 10,y**2 + 6*y + 4,y); & - Y^{6} + 18*Y^{5} + 120*Y^{4} + 360*Y^{3} + 480*Y^{2} + 288*Y + 64 -\end{Examples} -\begin{Comments} -The resultant is the determinant of the Sylvester matrix, formed from the -coefficients of the two polynomials in the following way: - -Given two polynomials: - -\begin{TEX} -\begin{displaymath} -a_0x^n+a_1x^{n-1}+\cdots+a_n -\end{displaymath} -\end{TEX} -\begin{INFO} -{\begin{verbatim} - n n-1 - a x + a1 x + ... + an - -\end{verbatim}} -\end{INFO} -and -\begin{TEX} -\begin{displaymath} -b_0x^n+b_1x^{n-1}+\cdots+b_n -\end{displaymath} -\end{TEX} -\begin{INFO} -{\begin{verbatim} - m m-1 - b x + b1 x + ... + bm - -\end{verbatim}} -\end{INFO} -form the (m+n)x(m+n-1) Sylvester matrix by the following means: -\begin{TEX} -\begin{displaymath} - \left(\begin{array}{cccccccc} - 0&\ldots&0&0&a_0&a_1&\ldots&a_n\\ - 0&\ldots&0&a_0&a_1&\ldots&a_n&0\\ - \vdots&&&\vdots&&&\vdots\\ - a_0&a_1&\ldots&a_n&0&0&\ldots&0\\ - 0&\ldots&0&0&b_0&b_1&\ldots&b_n\\ - \vdots&&&\vdots&&&\vdots\\ - b_0&b_1&\ldots&b_n&0&0&\ldots&0 - \end{array}\right) -\end{displaymath} -\end{TEX} -\begin{INFO} -{\begin{verbatim} - 0.......0 a a1 .......... an - 0....0 a a1 .......... an 0 - . . . . - a0 a1 .......... an 0.......0 - 0.......0 b b1 .......... bm - 0....0 b b1 .......... bm 0 - . . . . - b b1 .......... bm 0.......0 - -\end{verbatim}} -\end{INFO} - -If the determinant of this matrix is 0, the two polynomials have a common -root. Finding the resultant of large expressions is time-consuming, due -to the time needed to find a large determinant. - -The sign conventions \name{resultant} uses are those given in the article, -``Computing in Algebraic Extensions,'' by R. Loos, appearing in -\meta{Computer Algebra--Symbolic and Algebraic Computation}, 2nd ed., -edited by B. Buchberger, G.E. Collins and R. Loos, and published by -Springer-Verlag, 1983. -These are: -\begin{TEX} -\begin{eqnarray*} - \mbox{resultant}(p(x),q(x),x) - &=& (-1)^{\deg p(x)*\deg q(x)}\cdot\mbox{resultant}(q(x),p(x),x),\\ - \mbox{resultant}(a,p(x),x) &=& a^{\deg p(x)},\\ - \mbox{resultant}(a,b,x) &=& 1 -\end{eqnarray*} -where $p(x)$ and $q(x)$ are polynomials which have $x$ as a variable, and -$a$ and $b$ are free of $x$. -\end{TEX} -\begin{INFO} -{ -\begin{verbatim} - resultant(p(x),q(x),x) = (-1)^{deg p(x)*deg q(x)} * resultant(q(x),p(x),x), - resultant(a,p(x),x) = a^{deg p(x)}, - resultant(a,b,x) = 1 -\end{verbatim} -where p(x) and q(x) are polynomials which have x as a variable, and -a and b are free of x. -} -\end{INFO} - -Error messages are given if \name{resultant} is given a non-polynomial -expression, or a non-kernel variable. -\end{Comments} -\end{Operator} - - -\begin{Operator}{RHS} -\index{right-hand side}\index{equation} -The \name{rhs} operator returns the right-hand side of an \nameref{equation}, -such as those returned in a \nameref{list} by \nameref{solve}. -\begin{Syntax} -\name{rhs}\(\meta{equation}\) or \name{rhs} \meta {equation} -\end{Syntax} - -\meta{equation} must be an equation of the form {\it left-hand side = right-hand -side}. - -\begin{Examples} -roots := solve(x**2 + 6*x*y + 5x + 3y**2,x); & -\begin{multilineoutput}{6cm} - ROOTS := \{X= - \rfrac{SQRT(24*Y^{2} + 60*Y + 25) + 6*Y + 5}{2}, - X= \rfrac{SQRT(24*Y^{2} + 60*Y + 25) - 6*Y - 5}{2}\} -\end{multilineoutput} \\ -root1 := rhs first roots; & - ROOT1 := - \rfrac{SQRT(24*Y^{2} + 60*Y + 25) + 6*Y + 5}{2} \\ -root2 := rhs second roots; & - ROOT2 := \rfrac{SQRT(24*Y^{2} + 60*Y + 25) - 6*Y - 5}{2} -\end{Examples} - -\begin{Comments} -An error message is given if \name{rhs} is applied to something other than an -equation. -\end{Comments} -\end{Operator} - -\begin{Operator}{ROOT\_OF} -\index{roots}\index{solve} -When the operator \nameref{solve} is unable to find an explicit solution -or if that solution would be too complicated, the result is presented -as formal root expression using the internal operator \name{root\_of} -and a new local variable. An expression with a top level \name{root\_of} -is implicitly a list with an unknown number of elements since we -can't always know how many solutions an equation has. If a -substitution is made into such an expression, closed form solutions -can emerge. If this occurs, the \name{root\_of} construct is -replaced by an operator \nameref{one\_of}. At this point it is -of course possible to transform the result if the original \name{solve} -operator expression into a standard \name{solve} solution. To -effect this, the operator \nameref{expand\_cases} can be used. - -\begin{Examples} -solve(a*x^7-x^2+1,x);& -\{x=root\_of(a*x\_^7 - x\_^2 + 1,x\_)\}\\ -sub(a=0,ws);& -\{x=one\_of(1,-1)\}\\ -expand_cases ws;& -{x=1,x=-1}\\ -\end{Examples} -The components of \name{root\_of} and \name{one\_of} expressions can be -processed as usual with operators \nameref{arglength} and \nameref{part}. -A higher power of a \name{root\_of} expression with a polynomial -as first argument is simplified by using the polynomial as a side relation. -\end{Operator} - -\begin{Operator}{SELECT} -\index{map}\index{list} - -The \name{select} operator extracts from a list -or from the arguments of an n--ary operator elements corresponding -to a boolean predicate. The predicate pattern can be a -unary procedure, an operator or an algebraic expression with -one \nameref{free variable}. -\begin{Syntax} - \name{select}\(\meta{function},\meta{object}\) -\end{Syntax} -\meta{object} is a \nameref{list}. - -\meta{function} is -the name of an operator for a single argument: the operator - is evaluated once with each element of \meta{object} as its single argument, - -or an algebraic expression with exactly one \nameref{free variable}, that is -a variable preceded by the tilde symbol: the expression - is evaluated for each element of \meta{object} where the element is - substituted for the free variable, - -or a replacement \nameref{rule} of the form -\begin{Syntax} - \name{var} => \name{rep} -\end{Syntax} - where \meta{var} is a variable (a \meta{kernel} without subscript) - and \meta{rep} is an expression which contains \meta{var}. - Here \name{rep} is evaluated for each element of \meta{object} where - the element is substituted for \name{var}. \name{var} may be - optionally preceded by a tilde. - -The rule form for \meta{function} is needed when more than -one free variable occurs. The evaluation result of \meta{function} is -interpreted as \nameref{boolean value} corresponding to the conventions of -REDUCE. The result value is built with the leading operator of the -input expression. -\begin{Examples} - select( ~w>0 , {1,-1,2,-3,3}) & \{1,2,3\} \\ - q:=(part((x+y)^5,0):=list)\\ - select(evenp deg(~w,y),q);& \{x^5 ,10*x^3 *y^2 ,5*x*y^4 \}\\ - select(evenp deg(~w,x),2x^2+3x^3+4x^4);& 2x^2+4x^4\\ -\end{Examples} -\end{Operator} - -\begin{Operator}{SHOWRULES} -\index{rule}\index{output} -\begin{Syntax} -\name{showrules}\(\meta{expression}\) or - \name{showrules} \meta{simple\_expression} -\end{Syntax} - -\name{showrules} returns in \nameref{rule}\name{-list} form any -\nameref{operator} rules associated with its argument. - -\begin{Examples} -showrules log; & -\begin{multilineoutput}{6cm} -\{LOG(E) => 1, - LOG(1) => 0, - LOG(E^{~X} ) => ~X, - DF(LOG(~X),~X) => \rfrac{1}{~X}\} -\end{multilineoutput} -\end{Examples} - -Such rules can then be manipulated further as with any \nameref{list}. For -example -\name{rhs first ws;} has the value {\em 1}. - -\begin{Comments} -An operator may have properties that cannot be displayed in such a form, -such as the fact it is an \ref{odd} function, or has a definition defined -as a procedure. -\end{Comments} -\end{Operator} - - -\begin{Operator}{SOLVE} -\index{equation}\index{equation solving} -\index{equation system}\index{root}\index{solve} -The \name{solve} operator solves a single algebraic \nameref{equation} or a -system of simultaneous equations. -\begin{TEX} -\begin{Syntax} -% \name{solve}\(\meta{expression} \&option(, \meta{kernel})\) or -% \name{solve}\(\name{\{}\meta{expression}\{,\meta{expression}\} -% \optional\name{\}} -% \&option(,\meta{kernel}\optional\) -\name{solve}\(\meta{expression}\&option(, \meta{kernel})\) or \\ - \name{solve}\(\name{\{}\meta{expression}\&option( ,\meta{expression}) - \optional\name{\}} - \&option(,\{\meta{kernel})\optional\name{\}\}}\) -\end{Syntax} -\end{TEX} -\begin{INFO} -{\begin{Syntax} -\name{solve}\(\meta{expression} [ , \meta{kernel}]\) or - -\name{solve}\(\{\meta{expression},...\} [ ,\{ \meta{kernel} ,...\}] \) -\end{Syntax} -}\end{INFO} - -If the number of equations equals the number of distinct kernels, the -optional kernel argument(s) may be omitted. \meta{expression} is either a -scalar expression or an \nameref{equation}. -When more than one expression is given, -the \nameref{list} of expressions is surrounded by curly braces. -The optional list -of \nameref{kernel}s follows, also in curly braces. - -\begin{Examples} -sss := solve(x^2 + 7); & -\begin{multilineoutput}{6cm} -Unknown: X -SSS := \{X= - SQRT(7)*I, - X=SQRT(7)*I\} -\end{multilineoutput}\\ -rhs first sss; & - SQRT(7)*I \\ -solve(sin(x^2*y),y); & -\begin{multilineoutput}{6cm} -\{Y=\rfrac{2*ARBINT(1)*PI}{X^{2}} - Y=\rfrac{PI*(2*ARBINT(1) + 1)}{X^{2}}\} -\end{multilineoutput}\\ -off allbranch; \\ -solve(sin(x**2*y),y); & \{Y=0\} \\ -solve({3x + 5y = -4,2*x + y = -10},{x,y}); - & \{\{X= - \rfrac{22}{7},Y=\rfrac{46}{7}\}\} \\ -solve({x + a*y + z,2x + 5},{x,y}); - & \{\{X= - \rfrac{5}{2},Y= - \rfrac{2*Z - 5}{2*A}\}\} \\ -% xval := rhs part(ws,1,1); & XVAL := - \rfrac{5}{2} \\ -ab := (x+2)^2*(x^6 + 17x + 1); - & AB := X^{8} + 4*X^{7} + 4*X^{6} + 17*X^{3} + 69*X^{2} + 72*X + 4 \\ -www := solve(ab,x); & \{X=ROOT_OF(X_^{6} + 17*X_ + 1),X=-2\} \\ -root_multiplicities; & \{1,2\} -\end{Examples} -\begin{Comments} -Results of the \name{solve} operator are returned as \nameref{equation}\name{s} -in a \nameref{list}. -You can use the usual list access methods (\nameref{first}, -\nameref{second}, \nameref{third}, \nameref{rest} and \nameref{part}) to -extract the desired equation, and then use the operators \nameref{rhs} and -\nameref{lhs} to access the right-hand or left-hand expression of the -equation. When \name{solve} is unable to solve an equation, it returns the -unsolved part as the argument of \name{root_of}, with the variable renamed -to avoid confusion, as shown in the last example above. - -For one equation, \name{solve} uses square-free factorization, roots of -unity, and the known inverses of the \nameref{log}, \nameref{sin}, -\nameref{cos}, \nameref{acos}, \nameref{asin}, and -exponentiation operators. The quadratic, cubic and quartic formulas are -used if necessary, but these are applied only when the switch -\nameref{fullroots} is set on; otherwise or when no closed form is available -the result is returned as -\nameref{root\_of} expression. The switch \nameref{trigform} -determines which type of cubic and quartic formula is used. -The multiplicity of each solution is given in a list as -the system variable \nameref{root\_multiplicities}. For systems of -simultaneous linear equations, matrix inversion is used. For nonlinear -systems, the Groebner basis method is used. - -%If kernels are given for linear equations, and there are an unequal number -%of kernels and equations, an error message is given. If no kernels are -%given, and there are more kernels in the equations than there are -%equations, an error message is given. -Linear equation system solving is influenced by the switch \nameref{cramer}. -%For nonlinear equations, it is -%possible to have a consistent set in which the number of variables does not -%match the number of equations. - -Singular systems can be solved when the switch \nameref{solvesingular} is -on, which is the default setting. An empty list is returned the system of -equations is inconsistent. For a linear inconsistent system with parameters -the variable \nameref{requirements} constraints -conditions for the system to become consistent. - -For a solvable linear and polynomial system with parameters -the variable \nameref{assumptions} -contains a list side relations for the parameters: the solution is -valid only as long as none of these expressions is zero. - -If the switch \nameref{varopt} is on (default), the system rearranges the -variable sequence for minimal computation time. Without \name{varopt} -the user supplied variable sequence is maintained. - -If the solution has free variables (dimension of the solution is greater -than zero), these are represented by \nameref{arbcomplex} expressions -as long as the switch \nameref{arbvars} is on (default). Without -\name{arbvars} no explicit equations are generated for free variables. -\end{Comments} - -\begin{Related} -\item[\nameref{allbranch} switch] -\item[\nameref{arbvars} switch] -\item[\nameref{assumptions} variable] -\item[\nameref{fullroots} switch] -\item[\nameref{requirements} variable] -\item[\nameref{roots} operator] -\item[\nameref{root\_of} operator] -\item[\nameref{trigform} switch] -\item[\nameref{varopt} switch] -\end{Related} - -\end{Operator} - -\begin{Operator}{SORT} -\index{sorting} -The \name{sort} operator sorts the elements of a list according to -an arbitrary comparison operator. -\begin{Syntax} -\name{sort}\(\meta{lst},\meta{comp}\) -\end{Syntax} -\meta{lst} is a \nameref{list} of algebraic expressions. -\meta{comp} is a comparison operator which defines a partial -ordering among the members of \meta{lst}. \meta{comp} may be -one of the builtin comparison operators like -\name{<}(\nameref{lessp}), \name{<=}(\nameref{leq}) -etc., or \meta{comp} may be the name of a comparison procedure. -Such a procedure has two arguments, and it returns -\nameref{true} if the first argument -ranges before the second one, and 0 or \nameref{nil} otherwise. -The result of \name{sort} is a new list which contains the -elements of \meta{lst} in a sequence corresponding to \meta{comp}. -\begin{Examples} - % Sort random integers\\ -procedure ce(a,b);\\ - if evenp a and not evenp b then 1 else 0;\\ -for i:=1:10 collect random(50)$\\ -sort(ws,>=); & \{41,38,33,30,28,25,20,17,8,5\}\\ -sort(ws,<); & \{5,8,17,20,25,28,30,33,38,41\}\\ -sort(ws,ce); &\{8,20,28,30,38,5,17,25,33,41\}\\ - % Sort a set of polynomials, first for degree of x\\ - % and second for degree of y.\\ -procedure cd(a,b);\\ - if deg(a,x)>deg(b,x) then 1 else\\ - if deg(a,x)deg(b,y) then 1 else 0;\\ -sort({x^2,y^2,x*y},cd);&\{x^2,x*y,y^2\} -\end{Examples} -\end{Operator} - -\begin{Operator}{STRUCTR} -\index{decomposition} -The \name{structr} operator breaks its argument expression into named -subexpressions. -\begin{TEX} -\begin{Syntax} -\name{structr}\(\meta{expression} \&option(,\meta{identifier} - \&option(,\meta{identifier}))\) -\end{Syntax} -\end{TEX} -\begin{Syntax} -\name{structr}\(\meta{expression} [,\meta{identifier}[,\meta{identifier} ...]]\) -\end{Syntax} -\begin{INFO} -\end{INFO} -\meta{expression} may be any valid REDUCE scalar expression. -\meta{identifier} may be any valid REDUCE \name{identifier}. The first -identifier -is the stem for subexpression names, the second is the name to be assigned -to the structured expression. - -\begin{Examples} -structr(sqrt(x**2 + 2*x) + sin(x**2*z)); & -\begin{multilineoutput}{6cm} -ANS1 + ANS2 - where - ANS2 := SIN(X^{2}*Z) - ANS1 := ((X + 2)*X)^{1/2} -\end{multilineoutput}\\ -ans3; & ANS3 \\ -on fort; \\ -structr((x+1)**5 + tan(x*y*z),var,aa); & -\begin{multilineoutput}{6cm} -VAR1=TAN(X*Y*Z) -AA=VAR1+X**5+5.*X**4+10.*X**3+10.X**2+5.*X+1 -\end{multilineoutput} -\end{Examples} -\begin{Comments} -The second argument to \name{structr} is optional. If it is not given, the -default stem \name{ANS} is used by REDUCE to construct names for the -subexpression. The names are only for display purposes: REDUCE does not -store the names and their values unless the switch \nameref{savestructr} is -on. - -If a third argument is given, the structured expression as a whole is named by -this argument, when \nameref{fort} is on. The expression is not stored -under this -name. You can send these structured Fortran expressions to a file with the -\name{out} command. -\end{Comments} -\end{Operator} - - -\begin{Operator}{SUB} -\index{substitution} -The \name{sub} operator substitutes a new expression for a kernel in an -expression. -\begin{Syntax} -%\name{sub}\(\meta{kernel}\name{=}\meta{expression}% -% \{,\meta{kernel}\name{=}\meta{expression}\}\optional,% -% \meta{expression}\) -\name{sub}\(\meta{kernel}\name{=}\meta{expression} - \{,\meta{kernel}\name{=}\meta{expression}\}\optional, - \meta{expression}\) or \\ -\name{sub}\(\{\meta{kernel}\name{=}\meta{expression}\optional, - \meta{kernel}\name{=}\name{expression}\},\meta{expression}\) -\end{Syntax} - -\meta{kernel} must be a \nameref{kernel}, \meta{expression} can be any REDUCE -scalar expression. - -\begin{Examples} -sub(x=3,y=4,(x+y)**3); & 343 \\ -x; & X \\ -sub({cos=sin,sin=cos},cos a+sin b} & COS(B) + SIN(A) -\end{Examples} -\begin{Comments} -Note in the second example that operators can be replaced using the -\name{sub} operator. -\end{Comments} -\end{Operator} - - -\begin{Operator}{SUM} -\index{Gosper algorithm}\index{summation} -The operator \name{sum} returns -the indefinite or definite summation of a given expression. - -\begin{Syntax} - -\name{sum}\(\meta{expr},\meta{k}[,\meta{lolim} [,\meta{uplim} ]]\) - -\end{Syntax} - -where \meta{expr} is the expression to be added, \meta{k} is the -control variable (a \nameref{kernel}), and \meta{lolim} and \meta{uplim} -are the optional lower and upper limits. If \meta{uplim} is -not supplied the upper limit is taken as \meta{k}. The Gosper -algorithm is used. If there is no closed form solution, the operator -returns the input unchanged. - -\begin{Examples} -sum(4n**3,n); &n^2 *(n^2 + 2*n + 1)\\ -sum(2a+2k*r,k,0,n-1);& n*(2*a + n*r - r)\\ -\end{Examples} -\end{Operator} - - -\begin{Operator}{WS} -\index{work space}\index{interactive} -The \name{ws} operator alone returns the last result; \name{ws} with a -number argument returns the results of the REDUCE statement executed after -that numbered prompt. -\begin{Syntax} -\name{ws} or \name{ws}\(\meta{number}\) -\end{Syntax} - - -\meta{number} must be an integer between 1 and the current REDUCE prompt number. - -\begin{Examples} - -\explanation{(In the following examples, unlike most others, the numbered -prompt is shown.)} \\ -1: df(sin y,y); & COS(Y) \\ -2: ws^2; & COS(Y)^{2} \\ -3: df(ws 1,y); & -SIN(Y) -\end{Examples} - -\begin{Comments} -\name{ws} and \name{ws}\name{(}\meta{number}\name{)} can be used anywhere the -expression they stand for can be used. Calling a number for which no -result was produced, such as a switch setting, will give an error message. - -The current workspace always contains the results of the last REDUCE -command that produced an expression, even if several input statements -that do not produce expressions have intervened. For example, if you do -a differentiation, producing a result expression, then change several -switches, the operator \name{ws;} returns the results of the differentiation. -The current workspace (\name{ws}) can also be used inside files, though the -numbered workspace contains only the \name{in} command that input the file. - -There are three history lists kept in your REDUCE session. The first -stores raw input, suitable for the statement editor. The second stores -parsed input, ready to execute and accessible by \nameref{input}. The -third stores results, when they are produced by statements, which are -accessible by the \name{ws}\meta{ n} operator. If your session is very -long, storage space begins to fill up with these expressions, so it is a -good idea to end the session once in a while, saving needed expressions to -files with the \nameref{saveas} and \nameref{out} commands. -% Or you could use the \name{forget} command to clear all history lists and -% reset the prompt number to 1, which doesn't change any switch settings or -% variable assignments. - -An error message is given if a reference number has not yet been used. -\end{Comments} -\end{Operator} - +\section{Algebraic Operators} + +\begin{Operator}{APPEND} +\index{list} +The \name{append} operator constructs a new \nameref{list} +from the elements of its two arguments (which must be lists). + +\begin{Syntax} +\name{append}\(\meta{list},\meta{list}\) +\end{Syntax} + +\meta{list} must be a list, though it may be the empty list (\name{\{\}}). +Any arguments beyond the first two are ignored. + +\begin{Examples} +alist := \{1,2,\{a,b\}\}; & ALIST := \{1,2,\{A,B\}\} \\ +blist := \{3,4,5,sin(y)\}; & BLIST := \{3,4,5,SIN(Y)\} \\ +append(alist,blist); & \{1,2,\{A,B\},3,4,5,SIN(Y)\} \\ +append(alist,\{\}); & \{1,2,\{A,B\}\} \\ +append(list z,blist); & \{Z,3,4,5,SIN(Y)\} +\end{Examples} + +\begin{Comments} +The new list consists of the elements of the second list appended to the +elements of the first list. You can \name{append} new elements to the +beginning or end of an existing list by putting the new element in a +list (use curly braces or the operator \name{list}). This is +particularly helpful in an iterative loop. +\end{Comments} +\end{Operator} + +\begin{Operator}{ARBINT} +\index{arbitrary value} +The operator \name{arbint} is used to express arbitrary integer parts +of an expression, e.g. in the result of \nameref{solve} when +\nameref{allbranch} is on. +\begin{Examples} + +solve(log(sin(x+3)),x); & +\begin{multilineoutput}{6cm} +\{X=2*ARBINT(1)*PI - ASIN(1) - 3, + X=2*ARBINT(1)*PI + ASIN(1) + PI - 3\} +\end{multilineoutput} +\end{Examples} +\end{Operator} + +\begin{Operator}{ARBCOMPLEX} +\index{arbitrary value} +The operator \name{arbcomplex} is used to express arbitrary scalar parts +of an expression, e.g. in the result of \nameref{solve} when +the solution is parametric in one of the variable. +\begin{Examples} + +solve({x+3=y-2z,y-3x=0},{x,y,z}); & +\begin{multilineoutput}{6cm} +\{X=\rfrac{2*ARBCOMPLEX(1) + 3}{2}, + Y=\rfrac{3*ARBCOMPLEX(1) + 3}{2}, + Z=ARBCOMPLEX(1)\} +\end{multilineoutput} +\end{Examples} +\end{Operator} + +\begin{Operator}{ARGLENGTH} +\index{argument} +The operator \name{arglength} returns the number of arguments of the top-level +operator in its argument. + +\begin{Syntax} +\name{arglength}\(\meta{expression}\) +\end{Syntax} + +\meta{expression} can be any valid REDUCE algebraic expression. + +\begin{Examples} +arglength(a + b + c + d); & 4 \\ +arglength(a/b/c); & 2 \\ +arglength(log(sin(df(r**3*x,x)))); & 1 +\end{Examples} + +\begin{Comments} +In the first example, \name{+} is an n-ary operator, so the number of terms +is returned. In the second example, since \name{/} is a binary operator, the +argument is actually (a/b)/c, so there are two terms at the top level. In +the last example, no matter how deeply the operators are nested, there is +still only one argument at the top level. +\end{Comments} +\end{Operator} + + +\begin{Operator}{COEFF} +\index{coefficient} +The \name{coeff} operator returns the coefficients of the powers of the +specified variable in the given expression, in a \nameref{list}. + +\begin{Syntax} +\name{coeff}\(\meta{expression}\name{,}\meta{variable}\) +\end{Syntax} + +\meta{expression} is expected to be a polynomial expression, not a rational +expression. Rational expressions are accepted when the switch +\nameref{ratarg} is on. \meta{variable} must be a kernel. The results are +returned in a list. + +\begin{Examples} +coeff((x+y)**3,x); & \{Y^{3} ,3*Y^{2} ,3*Y,1\} \\ +coeff((x+2)**4 + sin(x),x); & \{SIN(X) + 16,32,24,8,1\} \\ +high_pow; & 4 \\ +low_pow; & 0 \\ +ab := x**9 + sin(x)*x**7 + sqrt(y); + & AB := SQRT(Y) + SIN(X)*X^{7} + X^{9}\\ +coeff(ab,x); & \{SQRT(Y),0,0,0,0,0,0,SIN(X),0,1\} +\end{Examples} +\begin{Comments} +The variables \nameref{high\_pow} and \nameref{low\_pow} are set to the +highest and lowest powers of the variable, respectively, appearing in the +expression. + +The coefficients are put into a list, with the coefficient of the lowest +(constant) term first. You can use the usual list access methods +(\name{first}, \name{second}, \name{third}, \name{rest}, \name{length}, and +\name{part}) to extract them. If a power does not appear in the +expression, the corresponding element of the list is zero. Terms involving +functions of the specified variable but not including powers of it (for +example in the expression \name{x**4 + 3*x**2 + tan(x)}) are placed in the +constant term. + +Since the \name{coeff} command deals with the expanded form of the expression, +you may get unexpected results when \nameref{exp} is off, or when +\nameref{factor} or \nameref{ifactor} are on. + +If you want only a specific coefficient rather than all of them, use the +\nameref{coeffn} operator. + +\end{Comments} +\end{Operator} + + +\begin{Operator}{COEFFN} +\index{coefficient} +The \name{coeffn} operator takes three arguments: an expression, a kernel, and +a non-negative integer. It returns the coefficient of the kernel to that +integer power, appearing in the expression. + +\begin{Syntax} +\name{coeffn}\(\meta{expression},\meta{kernel},\meta{integer}\) +\end{Syntax} + +\meta{expression} must be a polynomial, unless \nameref{ratarg} is on which +allows rational expressions. \meta{kernel} must be a kernel, and +\meta{integer} must be a non-negative integer. + +\begin{Examples} + +ff := x**7 + sin(y)*x**5 + y**4 + x + 7; & + FF := SIN(Y)*X^{5} + X^{7} + X + Y^{4} + 7 \\ +coeffn(ff,x,5); & SIN(Y) \\ +coeffn(ff,z,3); & 0 \\ +coeffn(ff,y,0); & SIN(Y)*X^{5} + X^{7} + X + 7 \\ + +rr := 1/y**2+y**3+sin(y); & +RR := \rfrac{SIN(Y)*Y^{2} + Y^{5} + 1}{Y^{2}} \\ +on ratarg; \\ + +coeffn(rr,y,-2); & ***** -2 invalid as COEFFN index \\ + +coeffn(rr,y,5); & \rfrac{1}{Y^{2}}\\ + +\end{Examples} + +\begin{Comments} +If the given power of the kernel does not appear in the expression, +\name{coeffn} returns 0. Negative powers are never detected, even if +they appear in the expression and \nameref{ratarg} are on. \name{coeffn} +with an integer argument of 0 returns any terms in the expression that +do {\em not} contain the given kernel. +\end{Comments} +\end{Operator} + + +\begin{Operator}{CONJ} +\index{conjugate}\index{complex} + +\begin{Syntax} +\name{conj}\(\meta{expression}\) or \name{conj} \meta{simple\_expression} +\end{Syntax} +This operator returns the complex conjugate of an expression, if that +argument has an numerical value. A non-numerical argument is returned as +an expression in the operators \nameref{repart} and \nameref{impart}. + +\begin{Examples} +conj(1+i); & 1-I \\ +conj(a+i*b); & REPART(A) - REPART(B)*I - IMPART(A)*I - IMPART(B) +\end{Examples} + +\end{Operator} + +\begin{Operator}{CONTINUED_FRACTION} +\index{approximation}\index{rational numbers} + +\begin{Syntax} +\name{continued\_fraction}\(\meta{num}\) +or \name{continued\_fraction}\( \meta{num},\meta{size}\) +\end{Syntax} +This operator approximates the real number \meta{num} +( \nameref{rational} number, \nameref{rounded} number) +into a continued fraction. The result is a list of two elements: the +first one is the rational value of the approximation, the second one +is the list of terms of the continued fraction which represents the +same value according to the definition \name{t0 +1/(t1 + 1/(t2 + ...))}. +Precision: the second optional parameter \meta{size} is an upper bound +for the absolute value of the result denominator. If omitted, the +approximation is performed up to the current system precision. + + +\begin{Examples} +continued_fraction pi; + & \{\rfrac{1146408},{364913},\{3,7,15,1,292,1,1,1,2,1\}\} \\ +continued_fraction(pi,100); + & \{\rfrac{22},{7},\{3,7\}\} \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{DECOMPOSE} +\index{decomposition}\index{polynomial} +The \name{decompose} operator takes a multivariate polynomial as argument, +and returns an expression and a \nameref{list} of +\nameref{equation}s from which the +original polynomial can be found by composition. + +\begin{Syntax} +\name{decompose}\(\meta{expression}\) or \name{decompose} + \meta{simple\_expression} +\end{Syntax} + +\begin{Examples} +\begin{multilineinput} +decompose(x^8-88*x^7+2924*x^6-43912*x^5+263431*x^4- + 218900*x^3+65690*x^2-7700*x+234) +\end{multilineinput} + & {U^{2} + 35*U + 234, U=V^{2} + 10*V, V=X^{2} - 22*X} \\ + decompose(u^2+v^2+2u*v+1) & {W^{2} + 1, W=U + V} +\end{Examples} + +\begin{Comments} +Unlike factorization, this decomposition is not unique. Further +details can be found in V.S. Alagar, M.Tanh, \meta{Fast Polynomial +Decomposition}, Proc. EUROCAL 1985, pp 150-153 (Springer) and J. von zur +Gathen, \meta{Functional} +\meta{Decomposition of Polynomials: the Tame Case}, J. +Symbolic Computation (1990) 9, 281-299. +\end{Comments} +\end{Operator} + + +\begin{Operator}{DEG} +\index{degree}\index{polynomial} +The operator \name{deg} returns the highest degree of its variable argument +found in its expression argument. + +\begin{Syntax} +\name{deg}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} is expected to be a polynomial expression, not a rational +expression. Rational expressions are accepted when the switch +\nameref{ratarg} is on. \meta{variable} must be a \nameref{kernel}. The +results are returned in a list. + +\begin{Examples} + +deg((x+y)**5,x); & 5 \\ + +deg((a+b)*(c+2*d)**2,d); & 2 \\ + +deg(x**2 + cos(y),sin(x)); \\ + +deg((x**2 + sin(x))**5,sin(x)); & 5 +\end{Examples} +\end{Operator} + + +\begin{Operator}{DEN} +\index{denominator}\index{rational expression} +The \name{den} operator returns the denominator of its argument. + +\begin{Syntax} +\name{den}\(\meta{expression}\) +\end{Syntax} + +\meta{expression} is ordinarily a rational expression, but may be any valid +scalar REDUCE expression. + +\begin{Examples} + +a := x**3 + 3*x**2 + 12*x; & A := X*(X^{2} + 3*X + 12) \\ + +b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ + +den(a/b); & SIN(X) + 4*Y \\ + +den(aa/4 + bb/5); & 20 \\ + +den(100/6); & 3 \\ + +den(sin(x)); & 1 +\end{Examples} + +\begin{Comments} +\name{den} returns the denominator of the expression after it has been +simplified by REDUCE. As seen in the examples, this includes putting +sums of rational expressions over a common denominator, and reducing +common factors where possible. If the expression does not have any +other denominator, 1 is returned. + +Switch settings, such as \nameref{mcd} or \nameref{rational}, have an +effect on the denominator of an expression. +\end{Comments} +\end{Operator} + + +\begin{Operator}{DF} +\index{derivative}\index{partial derivative} +The \name{df} operator finds partial derivatives with respect to one or +more variables. + +\begin{TEX} +\begin{Syntax} + \name{df}\(\meta{expression}\name{,}\meta{var} + \&optional\(\name{,}\meta{number}\) + \{\name{,}\meta{var}\&option\(\name{,}\meta{number}\)\}\optional\) +\end{Syntax} +\end{TEX} +\begin{INFO}{ +\begin{Syntax} + \name{df}\(\meta{expression}\name{,}\meta{var} + [\name{,}\meta{number}\] + \{\name{,}\meta{var} [ \name{,}\meta{number}] \} \) +\end{Syntax} +}\end{INFO} + +\meta{expression} can be any valid REDUCE algebraic expression. \meta{var} +must be a \nameref{kernel}, and is the differentiation variable. +\meta{number} must be a non-negative integer. + +\begin{Examples} + +df(x**2,x); & 2*X \\ + +df(x**2*y + sin(y),y); & COS(Y) + X^{2} \\ + +df((x+y)**10,z); & 0 \\ + + +df(1/x**2,x,2); & \rfrac{6}{X^{4}}\\ + +df(x**4*y + sin(y),y,x,3); & 24*X \\ + +for all x let df(tan(x),x) = sec(x)**2; \\ + +df(tan(3*x),x); & 3*SEC(3*X)^{2} +\end{Examples} +\begin{Comments} +An error message results if a non-kernel is entered as a differentiation +operator. If the optional number is omitted, it is assumed to be 1. +See the declaration \nameref{depend} to establish dependencies for implicit +differentiation. + +You can define your own differentiation rules, expanding REDUCE's +capabilities, using the \nameref{let} command as shown in the last example +above. Note that once you add your own rule for differentiating a +function, it supersedes REDUCE's normal handling of that function for the +duration of the REDUCE session. If you clear the rule +(\nameref{clearrules}), you don't get back +to the previous rule. +\end{Comments} +\end{Operator} + +\begin{Operator}{EXPAND\_CASES} +\index{solve} +When a \nameref{root\_of} form in a result of \nameref{solve} +has been converted to a \nameref{one\_of} form, \name{expand\_cases} +can be used to convert this into form corresponding to the +normal explicit results of \nameref{solve}. See \nameref{root\_of}. +\end{Operator} + +\begin{Operator}{EXPREAD} +\index{input} +\begin{Syntax} +\name{expread}\(\) +\end{Syntax} + +\name{expread} reads one well-formed expression from the current input +buffer and returns its value. + +\begin{Examples} +expread(); a+b; & A + B +\end{Examples} + +\end{Operator} + + +\begin{Operator}{FACTORIZE} +\index{factorize}\index{polynomial} +The \name{factorize} operator factors a given expression. +\begin{Syntax} +\name{factorize}\(\meta{expression}\) +\end{Syntax} + +\meta{expression} should be a polynomial, otherwise an error will result. + +\begin{Examples} + +fff := factorize(x^3 - y^3); & + \{X - Y,X^{2} + X*Y + Y^{2}\} \\ +fac1 := first fff; & FAC1 := X - Y \\ +factorize(x^15 - 1); & +\begin{multilineoutput}{5cm} + \{X - 1, + X^{2} + X + 1, + X^{4} + X^{3} + X^{2} + X + 1, + X^{8} - X^{7} + X^{6} - X^{5} + X^{4} - X + 1\} +\end{multilineoutput}\\ +lastone := part(ws,length ws); & + LASTONE := X^{8} - X^{7} + X^{6} - X^{5} + X^{4} - X + 1 \\ +setmod 2; & 1 \\ +on modular; \\ +factorize(x^15 - 1); & +\begin{multilineoutput}{5cm} +\{X + 1, + X^{2} + X + 1, + X^{4} + X + 1, + X^{4} + X^{3} + 1, + X^{4} + X^{3} + X^{2} + X + 1\} +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +The \name{factorize} command returns the factors it finds as a \nameref{list}. +You can therefore use the usual list access methods (\nameref{first}, +\nameref{second}, \nameref{third}, \nameref{rest}, \nameref{length} and +\nameref{part}) to extract the factors. + +If the \meta{expression} given to \name{factorize} is an integer, it will be +factored into its prime components. To factor any integer factor of a +non-numerical expression, the switch \nameref{ifactor} should be turned on. +Its default is off. \nameref{ifactor} has effect only when factoring is +explicitly done by \name{factorize}, not when factoring is automatically +done with the \nameref{factor} switch. If full factorization is not +needed the switch \nameref{limitedfactors} allows you to reduce the +computing time of calls to \name{factorize}. + +Factoring can be done in a modular domain by calling \name{factorize} when +\nameref{modular} is on. You can set the modulus with the \nameref{setmod} +command. The last example above shows factoring modulo 2. + +For general comments on factoring, see comments under the switch +\nameref{factor}. +\end{Comments} +\end{Operator} + + +\begin{Operator}{HYPOT} + +\begin{Syntax} +hypot(\meta{expression},\meta{expression}) +\end{Syntax} + +If \name{rounded} is on, and the two arguments evaluate to numbers, this +operator returns the square root of the sums of the squares of the +arguments in a manner that avoids intermediate overflow. In other cases, +an expression in the original operator is returned. + +\begin{Examples} +hypot(3,4); & HYPOT(3,4) \\ +on rounded; \\ +ws; & 5.0 \\ +hypot(a,b); & HYPOT(A,B) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{IMPART} +\index{imaginary part}\index{complex} +\begin{Syntax} +\name{impart}\(\meta{expression}\) or \name{impart} \meta{simple\_expression} +\end{Syntax} +This operator returns the imaginary part of an expression, if that +argument has an numerical value. A non-numerical argument is returned as +an expression in the operators \nameref{repart} and \name{impart}. +\begin{Examples} +impart(1+i); & 1 \\ +impart(a+i*b); & REPART(B) + IMPART(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{INT} +\index{integration} +The \name{int} operator performs analytic integration on a variety of +functions. + +\begin{Syntax} +\name{int}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} can be any scalar expression. involving polynomials, log +functions, exponential functions, or tangent or arctangent expressions. +\name{int} attempts expressions involving error functions, dilogarithms +and other trigonometric expressions. Integrals involving algebraic +extensions (such as square roots) may not succeed. \meta{kernel} must be a +REDUCE \nameref{kernel}. + +\begin{Examples} +int(x**3 + 3,x); & \rfrac{X*(X^{3} + 12)}{4} \\\\ +int(sin(x)*exp(2*x),x); + & - \rfrac{E^{2*X}*(COS(X) - 2*SIN(X))}{5} \\ +int(1/(x^2-2),x); + & \rfrac{SQRT(2)*(LOG( - SQRT(2) + X) - LOG(SQRT(2) + X))}{4} \\ +int(sin(x)/(4 + cos(x)**2),x); + & - \rfrac{ATAN(\rfrac{COS(X)}{2})}{2} \\\\ +int(1/sqrt(x^2-x),x); & INT(\rfrac{SQRT(X)*SQRT(X - 1)}{X^{2}-X},X) +\end{Examples} + +\begin{Comments} +Note that REDUCE couldn't handle the last integral with its default +integrator, since the integrand involves a square root. However, +the integral can be found using the \nameref{algint} package. +Alternatively, you could add a rule using the \nameref{let} statement +to evaluate this integral. + +The arbitrary constant of integration is not shown. Definite integrals can +be found by evaluating the result at the limits of integration (use +\nameref{rounded}) and subtracting the lower from the higher. Evaluation can +be easily done by the \nameref{sub} operator. + +When \name{int} cannot find an integral it returns an expression +involving formal \name{int} expressions unless the switch +\nameref{failhard} has been set. If not all of the expression +can be integrated, the switch \nameref{nolnr} controls whether a partially +integrated result should be returned or not. + +\end{Comments} +\end{Operator} + + +\begin{Operator}{INTERPOL} +\index{interpolation}\index{polynomial}\index{approximation} +\name{interpol} generates an interpolation polynomial. +\begin{Syntax} + interpol(\meta{values},\meta{variable},\meta{points}) +\end{Syntax} + +\meta{values} and \meta{points} are \nameref{list}s of equal length and +\meta{variable} is an algebraic expression (preferably a \nameref{kernel}). +The interpolation polynomial is generated in the given variable of degree +length(\meta{values})-1. The unique polynomial \name{f} is defined by the +property that for corresponding elements \name{v} of \meta{values} and +\name{p} of \meta{points} the relation \name{f(p)=v} holds. + +\begin{Examples} +f := for i:=1:4 collect(i**3-1); & F := {0,7,26,63} \\ +p := {1,2,3,4}; & P := {1,2,3,4} \\ +interpol(f,x,p); & X^{3} - 1 +\end{Examples} + +\begin{Comments} +The Aitken-Neville interpolation algorithm is used which guarantees a +stable result even with rounded numbers and an ill-conditioned problem. +\end{Comments} +\end{Operator} + + +\begin{Operator}{LCOF} +\index{coefficient}\index{polynomial} +The \name{lcof} operator returns the leading coefficient of a given expression +with respect to a given variable. +\begin{Syntax} +\name{lcof}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, +a rational expression may also be used, otherwise an error results. +\meta{kernel} must be a \nameref{kernel}. + +\begin{Examples} +lcof((x+2*y)**5,y); & 32 \\ +lcof((x + y*sin(x))**2 + cos(x)*sin(x)**2,sin(x)); + & COS(X)^{2} + Y \\ +lcof(x**2 + 3*x + 17,y); & X^{2} + 3*X + 17 +\end{Examples} + +\begin{Comments} +If the kernel does not appear in the expression, \name{lcof} returns the +expression. +\end{Comments} +\end{Operator} + + +\begin{Operator}{LENGTH} +\index{list} +The \name{length} operator returns the number of items in a \nameref{list}, the +number of +terms in an expression, or the dimensions of an array or matrix. +\begin{Syntax} +\name{length}\(\meta{expr}\) or \name{length} \meta{expr} +\end{Syntax} + +\meta{expr} can be a list structure, an array, a matrix, or a scalar expression. + +\begin{Examples} +alist := \{a,b,\{ww,xx,yy,zz\}\}; & + ALIST := \{A,B,\{WW,XX,YY,ZZ\}\} \\ +length alist; & 3 \\ +length third alist; & 4 \\ +dlist := \{d\}; & DLIST := \{D\} \\ +length rest dlist; & 0 \\ +matrix mmm(4,5); \\ +length mmm; & \{4,5\} \\ +array aaa(5,3,2); \\ +length aaa; & \{6,4,3\} \\ +eex := (x+3)**2/(x-y); & EEX := \rfrac{X^{2} + 6*X + 9}{X - Y} \\ +length eex; & 5 +\end{Examples} + +\begin{Comments} +An item in a list that is itself a list only counts as one item. An error +message will be printed if \name{length} is called on a matrix which has +not had its dimensions set. The \name{length} of an array includes the +zeroth element of each dimension, showing the full number of elements +allocated. (Declaring an array \IFTEX{$A$}{A} with \IFTEX{$n$}{n} elements +allocates \IFTEX{$ A(0),A(1),\ldots,A(n)$}{A(0),A(1),...,A(n)}.) The +\name{length} of an expression is the total number of additive terms +appearing in the numerator and denominator of the expression. Note that +subtraction of a term is represented internally as addition of a negative +term. +\end{Comments} +\end{Operator} + + +\begin{Operator}{LHS} +\index{left-hand side}\index{equation} +The \name{lhs} operator returns the left-hand side of an \nameref{equation}, +such as those +returned in a list by \nameref{solve}. +\begin{Syntax} +\name{lhs}\(\meta{equation}\) or \name{lhs} \meta{equation} + +\end{Syntax} + +\meta{equation} must be an equation of the form \\ +\name{left-hand side} \name{=} \name{right-hand side}. + +\begin{Examples} +polly := (x+3)*(x^4+2x+1); & +POLLY := X^{5} + 3*X^{4} + 2*X^{2} + 7*X + 3 \\ +pollyroots := solve(polly,x); & +\begin{multilineoutput}{1cm} +POLLYROOTS := \{X=ROOT_OF(X_^{3} - X_^{2} + X_ + 1,X_), + X=-1, + X=-3\} +\end{multilineoutput} \\ +variable := lhs first pollyroots; & +VARIABLE := X +\end{Examples} +\end{Operator} + + +\begin{Operator}{LIMIT} +\index{limit}\index{l'Hopital's rule} +LIMITS is a fast limit package for REDUCE for functions which are +continuous except for computable poles and singularities, based on +some earlier work by Ian Cohen and John P. Fitch. The Truncated +Power Series package is used for non-critical points, at which +the value of the function is the constant term in the expansion +around that point. l'Hopital's rule is used in critical cases, +with preprocessing of 1-1 forms and reformatting of product forms +in order to apply l'Hopital's rule. A limited amount of bounded +arithmetic is also employed where applicable. + +\begin{Syntax} +\name{limit}\(\meta{expr},\meta{var},\meta{limpoint}\) or \\ +\name{limit!+}\(\meta{expr},\meta{var},\meta{limpoint}\) or \\ +\name{limit!-}\(\meta{expr},\meta{var},\meta{limpoint}\) +\end{Syntax} + +where \meta{expr} is an expression depending of the variable \meta{var} +(a \nameref{kernel}) and \meta{limpoint} is the limit point. +If the limit depends upon the direction of approach to the \meta{limpoint}, +the operators \name{limit!+} and \name{limit!-} may be used. + +\begin{Examples} +limit(x*cot(x),x,0);&0\\ +limit((2x+5)/(3x-2),x,infinity);&\rfrac{2}{3}\\ +\end{Examples} + +\end{Operator} + + +\begin{Operator}{LPOWER} +\index{leading power}\index{polynomial} +The \name{lpower} operator returns the leading power of an expression with +respect to a kernel. 1 is returned if the expression does not depend on +the kernel. +\begin{Syntax} +\name{lpower}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, +a rational expression may also be used, otherwise an error results. +\meta{kernel} must be a \nameref{kernel}. + +\begin{Examples} +lpower((x+2*y)**6,y); & Y^{6} \\ +lpower((x + cos(x))**8 + df(x**2,x),cos(x)); + & COS(X)^{8} \\ +lpower(x**3 + 3*x,y); & 1 +\end{Examples} +\end{Operator} + +\begin{Operator}{LTERM} +\index{leading term}\index{polynomial} +The \name{lterm} operator returns the leading term of an expression with +respect to a kernel. The expression is returned if it does not depend on +the kernel. +\begin{Syntax} +\name{lterm}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, +a rational expression may also be used, otherwise an error results. +\meta{kernel} must be a \nameref{kernel}. + +\begin{Examples} +lterm((x+2*y)**6,y); & 64*Y^{6} \\ +lterm((x + cos(x))**8 + df(x**2,x),cos(x)); + & COS(X)^{8} \\ +lterm(x**3 + 3*x,y); & X^{3} + 3X +\end{Examples} +\end{Operator} + + +\begin{Operator}{MAINVAR} +\index{main variable}\index{polynomial} +The \name{mainvar} operator returns the main variable (in the system's +internal representation) of its argument. +\begin{Syntax} +\name{mainvar}\(\meta{expression}\) + +\end{Syntax} + +\meta{expression} is usually a polynomial, but may be any valid REDUCE +scalar expression. In the case of a rational function, the main variable +of the numerator is returned. The main variable returned is a +\nameref{kernel}. + +\begin{Examples} +test := (a + b + c)**2; & + TEST := A^{2} + 2*A*B + 2*A*C + B^{2} + 2*B*C + C^{2} \\ +mainvar(test); & A \\ +korder c,b,a; \\ +mainvar(test); & C \\ +mainvar(2*cos(x)**2); & COS(X) \\ +mainvar(17); & 0 +\end{Examples} + +\begin{Comments} +The main variable is the first variable in the canonical ordering of +kernels. Generally, alphabetically ordered functions come first, then +alphabetically ordered identifiers (variables). Numbers come last, and as +far as \name{mainvar} is concerned belong in the family \name{0}. The +canonical ordering can be changed by the declaration \nameref{korder}, as +shown above. +\end{Comments} +\end{Operator} + + +\begin{Operator}{MAP} +\index{map}\index{composite structure} +The \name{map} operator applies a uniform evaluation pattern +to all members of a composite structure: a \nameref{matrix}, +a \nameref{list} or the arguments of an \nameref{operator} expression. +The evaluation pattern can be a +unary procedure, an operator, or an algebraic expression with +one free variable. +\begin{Syntax} + \name{map}\(\meta{function},\meta{object}\) +\end{Syntax} +\meta{object} is a list, a matrix or an operator expression. + +\meta{function} is +the name of an operator for a single argument: the operator + is evaluated once with each element of \meta{object} as its single argument, + +or an algebraic expression with exactly one \nameref{free variable}, that is +a variable preceded by the tilde symbol: the expression + is evaluated for each element of \meta{object} where the element is + substituted for the free variable, + +or a replacement \nameref{rule} of the form +\begin{Syntax} + \name{var} => \name{rep} +\end{Syntax} + where \meta{var} is a variable (a \meta{kernel} without subscript) + and \meta{rep} is an expression which contains \meta{var}. + Here \name{rep} is evaluated for each element of \meta{object} where + the element is substituted for \name{var}. \name{var} may be + optionally preceded by a tilde. + +The rule form for \meta{function} is needed when more than +one free variable occurs. + +\begin{Examples} +map(abs,{1,-2,a,-a}); & {1,2,abs(a),abs(a)} \\ +map(int(~w,x), mat((x^2,x^5),(x^4,x^5))); & +\begin{multilineoutput}{1cm} + [ 3 6 ] + [ x x ] + [---- ----] + [ 3 6 ] + [ ] + [ 5 6 ] + [ x x ] + [---- ----] + [ 5 6 ] +\end{multilineoutput}\\ +map(~w*6, x^2/3 = y^3/2 -1); & 2*x^2=3*(y^3-2)\\ +\end{Examples} + +\begin{Comments} +You can use \name{map} in nested expressions. It is not allowed to +apply \name{map} for a non-composed object, e.g. an identifier or a number. +\end{Comments} +\end{Operator} + + + +\begin{Command}{MKID} +\index{identifier} +The \name{mkid} command constructs an identifier, given a stem and an identifier +or an integer. +\begin{Syntax} +\name{mkid}\(\meta{stem},\meta{leaf}\) +\end{Syntax} + +\meta{stem} can be any valid REDUCE identifier that does not include escaped +special characters. \meta{leaf} may be an integer, including one given by a +local variable in a \nameref{for} loop, or any other legal group of +characters. + +\begin{Examples} +mkid(x,3); & X3 \\ +factorize(x^15 - 1); & \begin{multilineoutput}{6cm} +\{X - 1, + X^{2} + X + 1, + X^{4} + X^{3} + X^{2} + X + 1, + X^{8} - X^{7} + X^{5} - X^{4} + X^{3} - X + 1\} +\end{multilineoutput}\\ + +for i := 1:length ws do write set(mkid(f,i),part(ws,i)); + & \begin{multilineoutput}{6cm} +X^{8} - X^{7} + X^{5} - X^{4} + X^{3} - X + 1 +X^{4} + X^{3} + X^{2} + X + 1 +X^{2} + X + 1 +X - 1 +\end{multilineoutput} \\ +\end{Examples} + +\begin{Comments} +You can use \name{mkid} to construct identifiers from inside procedures. This +allows you to handle an unknown number of factors, or deal with variable +amounts of data. It is particularly helpful to attach identifiers to the +answers returned by \name{factorize} and \name{solve}. +\end{Comments} +\end{Command} + + +\begin{Operator}{NPRIMITIVE} +\index{primitive part}\index{polynomial} +\begin{Syntax} +\name{nprimitive}\(\meta{expression}\) or \name{nprimitive} + \meta{simple\_expression} +\end{Syntax} +This operator returns the numerically-primitive part of any scalar +expression. In other words, any overall integer factors in the expression +are removed. + +\begin{Examples} +nprimitive((2x+2y)^2); & X^{2} + 2*X*Y + Y^{2} \\ +nprimitive(3*a*b*c); & 3*A*B*C +\end{Examples} +\end{Operator} + + +\begin{Operator}{NUM} +\index{numerator}\index{rational expression} +The \name{num} operator returns the numerator of its argument. +\begin{Syntax} +\name{num}\(\meta{expression}\) or \name{num} \meta{simple\_expression} +\end{Syntax} + +\meta{expression} can be any valid REDUCE scalar expression. + +\begin{Examples} +num(100/6); & 50 \\ +num(a/5 + b/6); & 6*A + 5*B \\ +num(sin(x)); & SIN(X) +\end{Examples} + +\begin{Comments} +\name{num} returns the numerator of the expression after it has been simplified +by REDUCE. As seen in the examples, this includes putting sums of rational +expressions over a common denominator, and reducing common factors where +possible. If the expression is not a rational expression, it is returned +unchanged. +\end{Comments} +\end{Operator} + + +\begin{Operator}{ODESOLVE} +\index{differential equation}\index{solve} +The \name{odesolve} package is a solver for ordinary differential +equations. At the present time it has still limited capabilities: + + 1. it can handle only a single scalar equation presented as an + algebraic expression or equation, and + + 2. it can solve only first-order equations of simple types, linear + equations with constant coefficients and Euler equations. + +These solvable types are exactly those for which Lie symmetry +techniques give no useful information. + +\begin{Syntax} + +\name{odesolve}\(\meta{expr},\meta{var1},\meta{var2}\) + +\end{Syntax} + +\meta{expr} is a single scalar expression such that \meta{expr}=0 +is the ordinary differential equation (ODE for short) to be solved, or +is an equivalent \nameref{equation}. + +\meta{var1} is the name of the dependent variable, +\meta{var2} is the name of the independent variable. + +A differential in \meta{expr} is expressed using the \nameref{df} +operator. Note that in most cases you must declare explicitly +\meta{var1} to depend of \meta{var2} using a \nameref{depend} +declaration -- otherwise the derivative might be evaluated to +zero on input to \name{odesolve}. + +The returned value is a list containing the equation giving the general +solution of the ODE (for simultaneous equations this will be a +list of equations eventually). It will contain occurrences of +the operator \name{arbconst} for the arbitrary constants in the general +solution. The arguments of \name{arbconst} should be new. +A counter \name{!!arbconst} is used to arrange this. + +\begin{Examples} +depend y,x;\\ +\% A first-order linear equation, with an initial condition\\ +ode:=df(y,x) + y * sin x/cos x - 1/cos x$\\ +odesolve(ode,y,x); & \{y=arbconst(1)*cos(x) + sin(x)\} +\end{Examples} + +\end{Operator} + + +\begin{Type}{ONE\_OF} +The operator \name{one\_of} is used to represent an indefinite choice +of one element from a finite set of objects. +\begin{Examples} +x=one_of{1,2,5}\\ +\explanation{this equation encodes that x can take one of the values +1,2 or 5}\\ +\end{Examples} +REDUCE generates a \name{one\_of} form in cases when an implicit +\name{root\_of} expression could be converted to an explicit solution set. +A \name{one\_of} form can be converted to a \name{solve} solution using +\nameref{expand\_cases}. See \nameref{root\_of}. +\end{Type} + +\begin{Operator}{PART} +\index{decomposition} +The operator \name{part} permits the extraction of various parts or +operators of expressions and \nameref{list}\name{s}. +\begin{Syntax} +\name{part}\(\meta{expression,integer}\{,\meta{integer}\}\optional\) +\end{Syntax} + +\meta{expression} can be any valid REDUCE expression or a list, {\it +integer} may be an expression that evaluates to a positive or negative +integer or 0. A positive integer \meta{n} picks up the {\it n} th term, +counting from the first term toward the end. A negative integer {\it n} +picks up the {\it n} th term, counting from the back toward the front. The +integer 0 picks up the operator (which is \name{LIST} when the expression +is a \ref{list}). + +\begin{Examples} +part((x + y)**5,4); & 10*X^{2}*Y^{3} \\ +part((x + y)**5,4,2); & X^{2} \\ +part((x + y)**5,4,2,1); & X \\ +part((x + y)**5,0); & PLUS \\ +part((x + y)**5,-5); & 5*X *Y^{4} \\ +part((x + y)**5,4) := sin(x); & + X^{5} + 5*X^{4}*Y + 10*X^{3}*Y^{2} + SIN(X) + 5*X*Y^{4} + Y^{5} \\ +alist := \{x,y,\{aa,bb,cc\},x**2*sqrt(y)\}; & + ALIST := \{X,Y,\{AA,BB,CC\},SQRT(Y)*X^{2}\} \\ +part(alist,3,2); & BB \\ +part(alist,4,0); & TIMES +\end{Examples} + +\begin{Comments} +Additional integer arguments after the first one examine the +terms recursively, as shown above. In the third line, the fourth term +is picked from the original polynomial, \IFTEX{$10x^2y^3$}{10x^2y^3}, +then the second term from that, \IFTEX{$x^2$}{x^2}, and finally the first +component, \IFTEX{$x$}{x}. If an integer's absolute value is too large for +the appropriate expression, a message is given. + +\name{part} works on the form of the expression as printed, or as it would +have been printed at that point of the calculation, bearing in mind the +current switch settings. It is important to realize that the switch settings +change the operation of \name{part}. \nameref{pri} must be on when +\name{part} is used. + +When \name{part} is used on a polynomial expression that has minus signs, the +\name{+} is always returned as the top-level operator. The minus is found +as a unary operator attached to the negative term. + +\name{part} can also be used to change the relevant part of the expression or +list as shown in the sixth example line. The \name{part} operator returns the +changed expression, though original expression is not changed. You can +also use \name{part} to change the operator. +\end{Comments} +\end{Operator} + +\begin{Operator}{PF} +\index{partial fraction}\index{rational expression} +\begin{Syntax} +pf(\meta{expression},\meta{variable}) +\end{Syntax} + +\name{pf} transforms \meta{expression} into a \nameref{list} of partial fraction +s +with respect to the main variable, \meta{variable}. \name{pf} does a +complete partial fraction decomposition, and as the algorithms used are +fairly unsophisticated (factorization and the extended Euclidean +algorithm), the code may be unacceptably slow in complicated cases. +\begin{Examples} +pf(2/((x+1)^2*(x+2)),x); & + \{\rfrac{2}{X + 2},\rfrac{-2}{X + 1},\rfrac{2}{X^{2} + 2*X + 1}\} \\ +off exp; \\ +pf(2/((x+1)^2*(x+2)),x); + & \{\rfrac{2}{X + 2},\rfrac{- 2}{X + 1},\rfrac{2}{(X + 1)^{2}}\} \\ +for each j in ws sum j; & \rfrac{2}{( + 2)*(X + 1)^{2}} +\end{Examples} + +\begin{Comments} +If you want the denominators in factored form, turn \nameref{exp} off, as +shown in the second example above. As shown in the final example, the +\nameref{for} \name{each} construct can be used to recombine the terms. +Alternatively, one can use the operations on lists to extract any desired +term. +\end{Comments} + +\end{Operator} + + +\begin{Operator}{PROD} +\index{Gosper algorithm}\index{product} +The operator \name{prod} returns +the indefinite or definite product of a given expression. + +\begin{Syntax} + +\name{prod}\(\meta{expr},\meta{k}[,\meta{lolim} [,\meta{uplim} ]]\) + +\end{Syntax} + +where \meta{expr} is the expression to be multiplied, \meta{k} is the +control variable (a \nameref{kernel}), and \meta{lolim} and \meta{uplim} +uplim are the optional lower and upper limits. If \meta{uplim} is +not supplied the upper limit is taken as \meta{k}. The +Gosper algorithm is used. If there is no closed form solution, +the operator returns the input unchanged. + +\begin{Examples} +prod(k/(k-2),k);&k*( - k + 1)\\ +\end{Examples} +\end{Operator} + + +\begin{Operator}{REDUCT} +\index{reductum}\index{polynomial} +The \name{reduct} operator returns the remainder of its expression after the +leading term with respect to the kernel in the second argument is removed. +\begin{Syntax} +\name{reduct}\(\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} is ordinarily a polynomial. If \nameref{ratarg} is on, +a rational expression may also be used, otherwise an error results. +\meta{kernel} must be a \nameref{kernel}. + +\begin{Examples} +reduct((x+y)**3,x); & Y*(3*X^{2} + 3*X*Y + Y^{2}) \\ +reduct(x + sin(x)**3,sin(x)); & X \\ +reduct(x + sin(x)**3,y); & 0 +\end{Examples} + +\begin{Comments} +If the expression does not contain the kernel, \name{reduct} returns 0. +\end{Comments} +\end{Operator} + + +\begin{Operator}{REPART} +\index{real part}\index{complex} +\begin{Syntax} +\name{repart}\(\meta{expression}\) or \name{repart} \meta{simple\_expression} +\end{Syntax} + +This operator returns the real part of an expression, if that argument has an +numerical value. A non-numerical argument is returned as an expression in +the operators \name{repart} and \nameref{impart}. +\begin{Examples} +repart(1+i); & 1 \\ +repart(a+i*b); & REPART(A) - IMPART(B) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{RESULTANT} +\index{polynomial} +The \name{resultant} operator computes the resultant of two polynomials with +respect to a given variable. If the resultant is 0, the polynomials have +a root in common. +\begin{Syntax} + \name{resultant}\(\meta{expression},\meta{expression},\meta{kernel}\) +\end{Syntax} + +\meta{expression} must be a polynomial containing \meta{kernel} ; +\meta{kernel} must be a \nameref{kernel}. + +\begin{Examples} +resultant(x**2 + 2*x + 1,x+1,x); & 0 \\ +resultant(x**2 + 2*x + 1,x-3,x); & 16 \\ +\begin{multilineinput} +resultant(z**3 + z**2 + 5*z + 5, + z**4 - 6*z**3 + 16*z**2 - 30*z + 55, + z); +\end{multilineinput} & 0 \\ +resultant(x**3*y + 4*x*y + 10,y**2 + 6*y + 4,y); & + Y^{6} + 18*Y^{5} + 120*Y^{4} + 360*Y^{3} + 480*Y^{2} + 288*Y + 64 +\end{Examples} +\begin{Comments} +The resultant is the determinant of the Sylvester matrix, formed from the +coefficients of the two polynomials in the following way: + +Given two polynomials: + +\begin{TEX} +\begin{displaymath} +a_0x^n+a_1x^{n-1}+\cdots+a_n +\end{displaymath} +\end{TEX} +\begin{INFO} +{\begin{verbatim} + n n-1 + a x + a1 x + ... + an + +\end{verbatim}} +\end{INFO} +and +\begin{TEX} +\begin{displaymath} +b_0x^n+b_1x^{n-1}+\cdots+b_n +\end{displaymath} +\end{TEX} +\begin{INFO} +{\begin{verbatim} + m m-1 + b x + b1 x + ... + bm + +\end{verbatim}} +\end{INFO} +form the (m+n)x(m+n-1) Sylvester matrix by the following means: +\begin{TEX} +\begin{displaymath} + \left(\begin{array}{cccccccc} + 0&\ldots&0&0&a_0&a_1&\ldots&a_n\\ + 0&\ldots&0&a_0&a_1&\ldots&a_n&0\\ + \vdots&&&\vdots&&&\vdots\\ + a_0&a_1&\ldots&a_n&0&0&\ldots&0\\ + 0&\ldots&0&0&b_0&b_1&\ldots&b_n\\ + \vdots&&&\vdots&&&\vdots\\ + b_0&b_1&\ldots&b_n&0&0&\ldots&0 + \end{array}\right) +\end{displaymath} +\end{TEX} +\begin{INFO} +{\begin{verbatim} + 0.......0 a a1 .......... an + 0....0 a a1 .......... an 0 + . . . . + a0 a1 .......... an 0.......0 + 0.......0 b b1 .......... bm + 0....0 b b1 .......... bm 0 + . . . . + b b1 .......... bm 0.......0 + +\end{verbatim}} +\end{INFO} + +If the determinant of this matrix is 0, the two polynomials have a common +root. Finding the resultant of large expressions is time-consuming, due +to the time needed to find a large determinant. + +The sign conventions \name{resultant} uses are those given in the article, +``Computing in Algebraic Extensions,'' by R. Loos, appearing in +\meta{Computer Algebra--Symbolic and Algebraic Computation}, 2nd ed., +edited by B. Buchberger, G.E. Collins and R. Loos, and published by +Springer-Verlag, 1983. +These are: +\begin{TEX} +\begin{eqnarray*} + \mbox{resultant}(p(x),q(x),x) + &=& (-1)^{\deg p(x)*\deg q(x)}\cdot\mbox{resultant}(q(x),p(x),x),\\ + \mbox{resultant}(a,p(x),x) &=& a^{\deg p(x)},\\ + \mbox{resultant}(a,b,x) &=& 1 +\end{eqnarray*} +where $p(x)$ and $q(x)$ are polynomials which have $x$ as a variable, and +$a$ and $b$ are free of $x$. +\end{TEX} +\begin{INFO} +{ +\begin{verbatim} + resultant(p(x),q(x),x) = (-1)^{deg p(x)*deg q(x)} * resultant(q(x),p(x),x), + resultant(a,p(x),x) = a^{deg p(x)}, + resultant(a,b,x) = 1 +\end{verbatim} +where p(x) and q(x) are polynomials which have x as a variable, and +a and b are free of x. +} +\end{INFO} + +Error messages are given if \name{resultant} is given a non-polynomial +expression, or a non-kernel variable. +\end{Comments} +\end{Operator} + + +\begin{Operator}{RHS} +\index{right-hand side}\index{equation} +The \name{rhs} operator returns the right-hand side of an \nameref{equation}, +such as those returned in a \nameref{list} by \nameref{solve}. +\begin{Syntax} +\name{rhs}\(\meta{equation}\) or \name{rhs} \meta {equation} +\end{Syntax} + +\meta{equation} must be an equation of the form {\it left-hand side = right-hand +side}. + +\begin{Examples} +roots := solve(x**2 + 6*x*y + 5x + 3y**2,x); & +\begin{multilineoutput}{6cm} + ROOTS := \{X= - \rfrac{SQRT(24*Y^{2} + 60*Y + 25) + 6*Y + 5}{2}, + X= \rfrac{SQRT(24*Y^{2} + 60*Y + 25) - 6*Y - 5}{2}\} +\end{multilineoutput} \\ +root1 := rhs first roots; & + ROOT1 := - \rfrac{SQRT(24*Y^{2} + 60*Y + 25) + 6*Y + 5}{2} \\ +root2 := rhs second roots; & + ROOT2 := \rfrac{SQRT(24*Y^{2} + 60*Y + 25) - 6*Y - 5}{2} +\end{Examples} + +\begin{Comments} +An error message is given if \name{rhs} is applied to something other than an +equation. +\end{Comments} +\end{Operator} + +\begin{Operator}{ROOT\_OF} +\index{roots}\index{solve} +When the operator \nameref{solve} is unable to find an explicit solution +or if that solution would be too complicated, the result is presented +as formal root expression using the internal operator \name{root\_of} +and a new local variable. An expression with a top level \name{root\_of} +is implicitly a list with an unknown number of elements since we +can't always know how many solutions an equation has. If a +substitution is made into such an expression, closed form solutions +can emerge. If this occurs, the \name{root\_of} construct is +replaced by an operator \nameref{one\_of}. At this point it is +of course possible to transform the result if the original \name{solve} +operator expression into a standard \name{solve} solution. To +effect this, the operator \nameref{expand\_cases} can be used. + +\begin{Examples} +solve(a*x^7-x^2+1,x);& +\{x=root\_of(a*x\_^7 - x\_^2 + 1,x\_)\}\\ +sub(a=0,ws);& +\{x=one\_of(1,-1)\}\\ +expand_cases ws;& +{x=1,x=-1}\\ +\end{Examples} +The components of \name{root\_of} and \name{one\_of} expressions can be +processed as usual with operators \nameref{arglength} and \nameref{part}. +A higher power of a \name{root\_of} expression with a polynomial +as first argument is simplified by using the polynomial as a side relation. +\end{Operator} + +\begin{Operator}{SELECT} +\index{map}\index{list} + +The \name{select} operator extracts from a list +or from the arguments of an n--ary operator elements corresponding +to a boolean predicate. The predicate pattern can be a +unary procedure, an operator or an algebraic expression with +one \nameref{free variable}. +\begin{Syntax} + \name{select}\(\meta{function},\meta{object}\) +\end{Syntax} +\meta{object} is a \nameref{list}. + +\meta{function} is +the name of an operator for a single argument: the operator + is evaluated once with each element of \meta{object} as its single argument, + +or an algebraic expression with exactly one \nameref{free variable}, that is +a variable preceded by the tilde symbol: the expression + is evaluated for each element of \meta{object} where the element is + substituted for the free variable, + +or a replacement \nameref{rule} of the form +\begin{Syntax} + \name{var} => \name{rep} +\end{Syntax} + where \meta{var} is a variable (a \meta{kernel} without subscript) + and \meta{rep} is an expression which contains \meta{var}. + Here \name{rep} is evaluated for each element of \meta{object} where + the element is substituted for \name{var}. \name{var} may be + optionally preceded by a tilde. + +The rule form for \meta{function} is needed when more than +one free variable occurs. The evaluation result of \meta{function} is +interpreted as \nameref{boolean value} corresponding to the conventions of +REDUCE. The result value is built with the leading operator of the +input expression. +\begin{Examples} + select( ~w>0 , {1,-1,2,-3,3}) & \{1,2,3\} \\ + q:=(part((x+y)^5,0):=list)\\ + select(evenp deg(~w,y),q);& \{x^5 ,10*x^3 *y^2 ,5*x*y^4 \}\\ + select(evenp deg(~w,x),2x^2+3x^3+4x^4);& 2x^2+4x^4\\ +\end{Examples} +\end{Operator} + +\begin{Operator}{SHOWRULES} +\index{rule}\index{output} +\begin{Syntax} +\name{showrules}\(\meta{expression}\) or + \name{showrules} \meta{simple\_expression} +\end{Syntax} + +\name{showrules} returns in \nameref{rule}\name{-list} form any +\nameref{operator} rules associated with its argument. + +\begin{Examples} +showrules log; & +\begin{multilineoutput}{6cm} +\{LOG(E) => 1, + LOG(1) => 0, + LOG(E^{~X} ) => ~X, + DF(LOG(~X),~X) => \rfrac{1}{~X}\} +\end{multilineoutput} +\end{Examples} + +Such rules can then be manipulated further as with any \nameref{list}. For +example +\name{rhs first ws;} has the value {\em 1}. + +\begin{Comments} +An operator may have properties that cannot be displayed in such a form, +such as the fact it is an \ref{odd} function, or has a definition defined +as a procedure. +\end{Comments} +\end{Operator} + + +\begin{Operator}{SOLVE} +\index{equation}\index{equation solving} +\index{equation system}\index{root}\index{solve} +The \name{solve} operator solves a single algebraic \nameref{equation} or a +system of simultaneous equations. +\begin{TEX} +\begin{Syntax} +% \name{solve}\(\meta{expression} \&option(, \meta{kernel})\) or +% \name{solve}\(\name{\{}\meta{expression}\{,\meta{expression}\} +% \optional\name{\}} +% \&option(,\meta{kernel}\optional\) +\name{solve}\(\meta{expression}\&option(, \meta{kernel})\) or \\ + \name{solve}\(\name{\{}\meta{expression}\&option( ,\meta{expression}) + \optional\name{\}} + \&option(,\{\meta{kernel})\optional\name{\}\}}\) +\end{Syntax} +\end{TEX} +\begin{INFO} +{\begin{Syntax} +\name{solve}\(\meta{expression} [ , \meta{kernel}]\) or + +\name{solve}\(\{\meta{expression},...\} [ ,\{ \meta{kernel} ,...\}] \) +\end{Syntax} +}\end{INFO} + +If the number of equations equals the number of distinct kernels, the +optional kernel argument(s) may be omitted. \meta{expression} is either a +scalar expression or an \nameref{equation}. +When more than one expression is given, +the \nameref{list} of expressions is surrounded by curly braces. +The optional list +of \nameref{kernel}s follows, also in curly braces. + +\begin{Examples} +sss := solve(x^2 + 7); & +\begin{multilineoutput}{6cm} +Unknown: X +SSS := \{X= - SQRT(7)*I, + X=SQRT(7)*I\} +\end{multilineoutput}\\ +rhs first sss; & - SQRT(7)*I \\ +solve(sin(x^2*y),y); & +\begin{multilineoutput}{6cm} +\{Y=\rfrac{2*ARBINT(1)*PI}{X^{2}} + Y=\rfrac{PI*(2*ARBINT(1) + 1)}{X^{2}}\} +\end{multilineoutput}\\ +off allbranch; \\ +solve(sin(x**2*y),y); & \{Y=0\} \\ +solve({3x + 5y = -4,2*x + y = -10},{x,y}); + & \{\{X= - \rfrac{22}{7},Y=\rfrac{46}{7}\}\} \\ +solve({x + a*y + z,2x + 5},{x,y}); + & \{\{X= - \rfrac{5}{2},Y= - \rfrac{2*Z - 5}{2*A}\}\} \\ +% xval := rhs part(ws,1,1); & XVAL := - \rfrac{5}{2} \\ +ab := (x+2)^2*(x^6 + 17x + 1); + & AB := X^{8} + 4*X^{7} + 4*X^{6} + 17*X^{3} + 69*X^{2} + 72*X + 4 \\ +www := solve(ab,x); & \{X=ROOT_OF(X_^{6} + 17*X_ + 1),X=-2\} \\ +root_multiplicities; & \{1,2\} +\end{Examples} +\begin{Comments} +Results of the \name{solve} operator are returned as \nameref{equation}\name{s} +in a \nameref{list}. +You can use the usual list access methods (\nameref{first}, +\nameref{second}, \nameref{third}, \nameref{rest} and \nameref{part}) to +extract the desired equation, and then use the operators \nameref{rhs} and +\nameref{lhs} to access the right-hand or left-hand expression of the +equation. When \name{solve} is unable to solve an equation, it returns the +unsolved part as the argument of \name{root_of}, with the variable renamed +to avoid confusion, as shown in the last example above. + +For one equation, \name{solve} uses square-free factorization, roots of +unity, and the known inverses of the \nameref{log}, \nameref{sin}, +\nameref{cos}, \nameref{acos}, \nameref{asin}, and +exponentiation operators. The quadratic, cubic and quartic formulas are +used if necessary, but these are applied only when the switch +\nameref{fullroots} is set on; otherwise or when no closed form is available +the result is returned as +\nameref{root\_of} expression. The switch \nameref{trigform} +determines which type of cubic and quartic formula is used. +The multiplicity of each solution is given in a list as +the system variable \nameref{root\_multiplicities}. For systems of +simultaneous linear equations, matrix inversion is used. For nonlinear +systems, the Groebner basis method is used. + +%If kernels are given for linear equations, and there are an unequal number +%of kernels and equations, an error message is given. If no kernels are +%given, and there are more kernels in the equations than there are +%equations, an error message is given. +Linear equation system solving is influenced by the switch \nameref{cramer}. +%For nonlinear equations, it is +%possible to have a consistent set in which the number of variables does not +%match the number of equations. + +Singular systems can be solved when the switch \nameref{solvesingular} is +on, which is the default setting. An empty list is returned the system of +equations is inconsistent. For a linear inconsistent system with parameters +the variable \nameref{requirements} constraints +conditions for the system to become consistent. + +For a solvable linear and polynomial system with parameters +the variable \nameref{assumptions} +contains a list side relations for the parameters: the solution is +valid only as long as none of these expressions is zero. + +If the switch \nameref{varopt} is on (default), the system rearranges the +variable sequence for minimal computation time. Without \name{varopt} +the user supplied variable sequence is maintained. + +If the solution has free variables (dimension of the solution is greater +than zero), these are represented by \nameref{arbcomplex} expressions +as long as the switch \nameref{arbvars} is on (default). Without +\name{arbvars} no explicit equations are generated for free variables. +\end{Comments} + +\begin{Related} +\item[\nameref{allbranch} switch] +\item[\nameref{arbvars} switch] +\item[\nameref{assumptions} variable] +\item[\nameref{fullroots} switch] +\item[\nameref{requirements} variable] +\item[\nameref{roots} operator] +\item[\nameref{root\_of} operator] +\item[\nameref{trigform} switch] +\item[\nameref{varopt} switch] +\end{Related} + +\end{Operator} + +\begin{Operator}{SORT} +\index{sorting} +The \name{sort} operator sorts the elements of a list according to +an arbitrary comparison operator. +\begin{Syntax} +\name{sort}\(\meta{lst},\meta{comp}\) +\end{Syntax} +\meta{lst} is a \nameref{list} of algebraic expressions. +\meta{comp} is a comparison operator which defines a partial +ordering among the members of \meta{lst}. \meta{comp} may be +one of the builtin comparison operators like +\name{<}(\nameref{lessp}), \name{<=}(\nameref{leq}) +etc., or \meta{comp} may be the name of a comparison procedure. +Such a procedure has two arguments, and it returns +\nameref{true} if the first argument +ranges before the second one, and 0 or \nameref{nil} otherwise. +The result of \name{sort} is a new list which contains the +elements of \meta{lst} in a sequence corresponding to \meta{comp}. +\begin{Examples} + % Sort random integers\\ +procedure ce(a,b);\\ + if evenp a and not evenp b then 1 else 0;\\ +for i:=1:10 collect random(50)$\\ +sort(ws,>=); & \{41,38,33,30,28,25,20,17,8,5\}\\ +sort(ws,<); & \{5,8,17,20,25,28,30,33,38,41\}\\ +sort(ws,ce); &\{8,20,28,30,38,5,17,25,33,41\}\\ + % Sort a set of polynomials, first for degree of x\\ + % and second for degree of y.\\ +procedure cd(a,b);\\ + if deg(a,x)>deg(b,x) then 1 else\\ + if deg(a,x)deg(b,y) then 1 else 0;\\ +sort({x^2,y^2,x*y},cd);&\{x^2,x*y,y^2\} +\end{Examples} +\end{Operator} + +\begin{Operator}{STRUCTR} +\index{decomposition} +The \name{structr} operator breaks its argument expression into named +subexpressions. +\begin{TEX} +\begin{Syntax} +\name{structr}\(\meta{expression} \&option(,\meta{identifier} + \&option(,\meta{identifier}))\) +\end{Syntax} +\end{TEX} +\begin{Syntax} +\name{structr}\(\meta{expression} [,\meta{identifier}[,\meta{identifier} ...]]\) +\end{Syntax} +\begin{INFO} +\end{INFO} +\meta{expression} may be any valid REDUCE scalar expression. +\meta{identifier} may be any valid REDUCE \name{identifier}. The first +identifier +is the stem for subexpression names, the second is the name to be assigned +to the structured expression. + +\begin{Examples} +structr(sqrt(x**2 + 2*x) + sin(x**2*z)); & +\begin{multilineoutput}{6cm} +ANS1 + ANS2 + where + ANS2 := SIN(X^{2}*Z) + ANS1 := ((X + 2)*X)^{1/2} +\end{multilineoutput}\\ +ans3; & ANS3 \\ +on fort; \\ +structr((x+1)**5 + tan(x*y*z),var,aa); & +\begin{multilineoutput}{6cm} +VAR1=TAN(X*Y*Z) +AA=VAR1+X**5+5.*X**4+10.*X**3+10.X**2+5.*X+1 +\end{multilineoutput} +\end{Examples} +\begin{Comments} +The second argument to \name{structr} is optional. If it is not given, the +default stem \name{ANS} is used by REDUCE to construct names for the +subexpression. The names are only for display purposes: REDUCE does not +store the names and their values unless the switch \nameref{savestructr} is +on. + +If a third argument is given, the structured expression as a whole is named by +this argument, when \nameref{fort} is on. The expression is not stored +under this +name. You can send these structured Fortran expressions to a file with the +\name{out} command. +\end{Comments} +\end{Operator} + + +\begin{Operator}{SUB} +\index{substitution} +The \name{sub} operator substitutes a new expression for a kernel in an +expression. +\begin{Syntax} +%\name{sub}\(\meta{kernel}\name{=}\meta{expression}% +% \{,\meta{kernel}\name{=}\meta{expression}\}\optional,% +% \meta{expression}\) +\name{sub}\(\meta{kernel}\name{=}\meta{expression} + \{,\meta{kernel}\name{=}\meta{expression}\}\optional, + \meta{expression}\) or \\ +\name{sub}\(\{\meta{kernel}\name{=}\meta{expression}\optional, + \meta{kernel}\name{=}\name{expression}\},\meta{expression}\) +\end{Syntax} + +\meta{kernel} must be a \nameref{kernel}, \meta{expression} can be any REDUCE +scalar expression. + +\begin{Examples} +sub(x=3,y=4,(x+y)**3); & 343 \\ +x; & X \\ +sub({cos=sin,sin=cos},cos a+sin b} & COS(B) + SIN(A) +\end{Examples} +\begin{Comments} +Note in the second example that operators can be replaced using the +\name{sub} operator. +\end{Comments} +\end{Operator} + + +\begin{Operator}{SUM} +\index{Gosper algorithm}\index{summation} +The operator \name{sum} returns +the indefinite or definite summation of a given expression. + +\begin{Syntax} + +\name{sum}\(\meta{expr},\meta{k}[,\meta{lolim} [,\meta{uplim} ]]\) + +\end{Syntax} + +where \meta{expr} is the expression to be added, \meta{k} is the +control variable (a \nameref{kernel}), and \meta{lolim} and \meta{uplim} +are the optional lower and upper limits. If \meta{uplim} is +not supplied the upper limit is taken as \meta{k}. The Gosper +algorithm is used. If there is no closed form solution, the operator +returns the input unchanged. + +\begin{Examples} +sum(4n**3,n); &n^2 *(n^2 + 2*n + 1)\\ +sum(2a+2k*r,k,0,n-1);& n*(2*a + n*r - r)\\ +\end{Examples} +\end{Operator} + + +\begin{Operator}{WS} +\index{work space}\index{interactive} +The \name{ws} operator alone returns the last result; \name{ws} with a +number argument returns the results of the REDUCE statement executed after +that numbered prompt. +\begin{Syntax} +\name{ws} or \name{ws}\(\meta{number}\) +\end{Syntax} + + +\meta{number} must be an integer between 1 and the current REDUCE prompt number. + +\begin{Examples} + +\explanation{(In the following examples, unlike most others, the numbered +prompt is shown.)} \\ +1: df(sin y,y); & COS(Y) \\ +2: ws^2; & COS(Y)^{2} \\ +3: df(ws 1,y); & -SIN(Y) +\end{Examples} + +\begin{Comments} +\name{ws} and \name{ws}\name{(}\meta{number}\name{)} can be used anywhere the +expression they stand for can be used. Calling a number for which no +result was produced, such as a switch setting, will give an error message. + +The current workspace always contains the results of the last REDUCE +command that produced an expression, even if several input statements +that do not produce expressions have intervened. For example, if you do +a differentiation, producing a result expression, then change several +switches, the operator \name{ws;} returns the results of the differentiation. +The current workspace (\name{ws}) can also be used inside files, though the +numbered workspace contains only the \name{in} command that input the file. + +There are three history lists kept in your REDUCE session. The first +stores raw input, suitable for the statement editor. The second stores +parsed input, ready to execute and accessible by \nameref{input}. The +third stores results, when they are produced by statements, which are +accessible by the \name{ws}\meta{ n} operator. If your session is very +long, storage space begins to fill up with these expressions, so it is a +good idea to end the session once in a while, saving needed expressions to +files with the \nameref{saveas} and \nameref{out} commands. +% Or you could use the \name{forget} command to clear all history lists and +% reset the prompt number to 1, which doesn't change any switch settings or +% variable assignments. + +An error message is given if a reference number has not yet been used. +\end{Comments} +\end{Operator} + Index: r36/help/arith.tex ================================================================== --- r36/help/arith.tex +++ r36/help/arith.tex @@ -1,913 +1,913 @@ -\section{Arithmetic Operations} - -\begin{Introduction}{ARITHMETIC\_OPERATIONS} -This section considers operations defined in REDUCE that concern numbers, -or operators that can operate on numbers in addition, in most cases, to -more general expressions. -\end{Introduction} - -\begin{Operator}{ABS} -\index{absolute value} -The \name{abs} operator returns the absolute value of its argument. - -\begin{Syntax} -\name{abs}\(\meta{expression}\) -\end{Syntax} - -\meta{expression} can be any REDUCE scalar expression. - -\begin{Examples} -abs(-a); & ABS(A) \\ -abs(-5); & 5 \\ -a := -10; & A := -10 \\ -abs(a); & 10 \\ -abs(-a); & 10 -\end{Examples} -\begin{Comments} -If the argument has had no numeric value assigned to it, such as an -identifier or polynomial, \name{abs} returns an expression involving -\name{abs} of its argument, doing as much simplification of the argument -as it can, such as dropping any preceding minus sign. -\end{Comments} -\end{Operator} - - -\begin{Switch}{ADJPREC} -\index{input}\index{precision} -When a real number is input, it is normally truncated to the -\nameref{precision} in -effect at the time the number is read. If it is desired to keep the full -precision of all numbers input, the switch \name{adjprec} -(for \meta{adjust precision}) can be turned on. While on, \name{adjprec} -will automatically increase the precision, when necessary, to match that -of any integer or real input, and a message printed to inform the user of -the precision increase. - -\begin{Examples} -on rounded; \\ -1.23456789012345; & 1.23456789012 \\ -on adjprec; \\ -1.23456789012345; \\ -*** precision increased to 15 \\ -1.23456789012345 -\end{Examples} -\end{Switch} - - -\begin{Operator}{ARG} -\index{complex}\index{polar angle} -If \nameref{complex} and \nameref{rounded} are on, and {\em arg} -evaluates to a complex number, \name{arg} returns the polar angle of {\em -arg}, measured in radians. Otherwise an expression in {\em arg} is -returned. - -\begin{Examples} -arg(3+4i) & ARG(3 + 4*I) \\ -on rounded, complex; \\ -ws; & 0.927295218002 \\ -arg a; & ARG(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{CEILING} -\index{integer} - -\begin{Syntax} -\name{ceiling}\(\meta{expression}\) -\end{Syntax} - -This operator returns the ceiling (i.e., the least integer greater than or -equal to its argument) if its argument has a numerical value. For -negative numbers, this is equivalent to \nameref{fix}. For non-numeric -arguments, the value is an expression in the original operator. - -\begin{Examples} -ceiling 3.4; & 4 \\ -fix 3.4; & 3 \\ -ceiling(-5.2); & -5 \\ -fix(-5.2); & -5 \\ -ceiling a; & CEILING(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{CHOOSE} -\name{choose}(\meta{m},\meta{m}) returns the number of ways of choosing -\meta{m} objects from a collection of \meta{n} distinct objects --- in other -words the binomial coefficient. If \meta{m} and \meta{n} are not positive -integers, or $m > n$, the expression is returned unchanged. -than or equal to -\begin{Examples} -choose(2,3); & 3 \\ -choose(3,2); & CHOOSE(3,2) \\ -choose(a,b); & CHOOSE(A,B) -\end{Examples} -\end{Operator} - - -\begin{Operator}{DEG2DMS} -\index{degrees}\index{radians} -\begin{Syntax} -\name{deg2dms}\(\meta{expression}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{expression} is a real number, the -operator \name{deg2dms} will interpret it as degrees, and convert it to a -list containing the equivalent degrees, minutes and seconds. In all other -cases, an expression in terms of the original operator is returned. - -\begin{Examples} -deg2dms 60; & DEG2DMS(60) \\ -on rounded; \\ -ws; & \{60,0,0\} \\ -deg2dms 42.4; & \{42,23,60.0\} \\ -deg2dms a; & DEG2DMS(A) -\end{Examples} - -\end{Operator} - -\begin{Operator}{DEG2RAD} -\index{degrees}\index{radians} - -\begin{Syntax} -\name{deg2rad}\(\meta{expression}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{expression} is a real number, the -operator \name{deg2rad} will interpret it as degrees, and convert it to -the equivalent radians. In all other cases, an expression in terms of the -original operator is returned. - -\begin{Examples} -deg2rad 60; & DEG2RAD(60) \\ -on rounded; \\ -ws; & 1.0471975512 \\ -deg2rad a; & DEG2RAD(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{DIFFERENCE} -The \name{difference} operator may be used as either an infix or prefix binary -subtraction operator. It is identical to \name{-} as a binary operator. - -\begin{Syntax} -\name{difference}\(\meta{expression},\meta{expression}\) or - -\meta{expression} \name{difference} \meta{expression} - \{\name{difference} \meta{expression}\}\optional -\end{Syntax} - -\meta{expression} can be a number or any other valid REDUCE expression. Matrix -expressions are allowed if they are of the same dimensions. - -\begin{Examples} - -difference(10,4); & 6 \\ - -15 difference 5 difference 2; & 8 \\ - -a difference b; & A - B - -\end{Examples} - -\begin{Comments} -The \name{difference} operator is left associative, as shown in the second -example above. - -\end{Comments} -\end{Operator} - - -\begin{Operator}{DILOG} -\index{dilogarithm function} -The \name{dilog} operator is known to the differentiation and integration -operators, but has numeric value attached only at \name{dilog(0)}. Dilog is -defined by -\begin{TEX} -\begin{displaymath} - dilog(x) = -\int{{log(x)\,dx}\over{x-1}} -\end{displaymath} -\end{TEX} -\begin{INFO} - dilog(x) = -int(log(x),x)/(x-1) -\end{INFO} -\begin{Examples} -df(dilog(x**2),x); & - \rfrac{2*LOG(X^{2})*X}{X^{2} - 1}\\ - -int(dilog(x),x); & DILOG(X)*X - DILOG(X) + LOG(X)*X - X \\ - -dilog(0); & \rfrac{PI^{2}}{6} -\end{Examples} - -\end{Operator} - - -\begin{Operator}{DMS2DEG} -\index{degrees}\index{radians} - -\begin{Syntax} -\name{dms2deg}\(\meta{list}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{list} is a list of three real numbers, -the operator \name{dms2deg} will interpret the list as degrees, minutes -and seconds and convert it to the equivalent degrees. In all other cases, -an expression in terms of the original operator is returned. - -\begin{Examples} -dms2deg \{42,3,7\}; & DMS2DEG(\{42,3,7\}) \\ -on rounded; \\ -ws; & 42.0519444444 \\ -dms2deg a; & DMS2DEG(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{DMS2RAD} -\index{degrees}\index{radians} - -\begin{Syntax} -\name{dms2rad}\(\meta{list}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{list} is a list of three real numbers, -the operator \name{dms2rad} will interpret the list as degrees, minutes -and seconds and convert it to the equivalent radians. In all other cases, -an expression in terms of the original operator is returned. - -\begin{Examples} -dms2rad \{42,3,7\}; & DMS2RAD(\{42,3,7\}) \\ -on rounded; \\ -ws; & 0.733944887421 \\ -dms2rad a; & DMS2RAD(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{FACTORIAL} -\index{gamma} -\begin{Syntax} -\name{factorial}\(\meta{expression}\) -\end{Syntax} - -If the argument of \name{factorial} is a positive integer or zero, its -factorial is returned. Otherwise the result is expressed in terms of the -original operator. For more general operations, the \nameref{gamma} operator -is available in the \nameref{Special Function Package}. - -\begin{Examples} -factorial 4; & 24 \\ -factorial 30 ; & 265252859812191058636308480000000 \\ -factorial(a) ; FACTORIAL(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{FIX} -\index{integer} -\begin{Syntax} -\name{fix}\(\meta{expression}\) -\end{Syntax} - -The operator \name{fix} returns the integer part of its argument, if that -argument has a numerical value. For positive numbers, this is equivalent -to \nameref{floor}, and, for negative numbers, \nameref{ceiling}. For -non-numeric arguments, the value is an expression in the original operator. - -\begin{Examples} -fix 3.4; & 3 \\ -floor 3.4; & 3 \\ -ceiling 3.4; & 4 \\ -fix(-5.2); & -5 \\ -floor(-5.2); & -6 \\ -ceiling(-5.2); & -5 \\ -fix(a); & FIX(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{FIXP} -\index{integer} -The \name{fixp} logical operator returns true if its argument is an integer. -\begin{Syntax} -\name{fixp}\(\meta{expression}\) or \name{fixp} \meta{simple\_expression} -\end{Syntax} - -\meta{expression} can be any valid REDUCE expression, \meta{simple\_expression} -must be a single identifier or begin with a prefix operator. - -\begin{Examples} -if fixp 1.5 then write "ok" else write "not"; - & not \\ -if fixp(a) then write "ok" else write "not"; - & not \\ -a := 15; & A := 15 \\ -if fixp(a) then write "ok" else write "not"; - & ok -\end{Examples} - -\begin{Comments} -Logical operators can only be used inside conditional expressions such as -\name{if}\ldots\name{then} or \name{while}\ldots\name{do}. -\end{Comments} -\end{Operator} - - -\begin{Operator}{FLOOR} -\index{integer} - -\begin{Syntax} -\name{floor}\(\meta{expression}\) -\end{Syntax} - -This operator returns the floor (i.e., the greatest integer less than or -equal to its argument) if its argument has a numerical value. For -positive numbers, this is equivalent to \nameref{fix}. For non-numeric -arguments, the value is an expression in the original operator. - -\begin{Examples} -floor 3.4; & 3 \\ -fix 3.4; & 3 \\ -floor(-5.2); & -6 \\ -fix(-5.2); & -5 \\ -floor a; & FLOOR(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{EXPT} -The \name{expt} operator is both an infix and prefix binary exponentiation -operator. It is identical to \name{^} or \name{**}. -\begin{Syntax} -\name{expt}\(\meta{expression},\meta{expression}\) - or \meta{expression} \name{expt} \meta{expression} -\end{Syntax} -\begin{Examples} -a expt b; & A^{B} \\ -expt(a,b); & A^{B} \\ -(x+y) expt 4; & X^{4} + 4*X^{3}*Y + 6*X^{2}*Y^{2} + 4*X*Y^{3} + Y^{4} -\end{Examples} -\begin{Comments} -Scalar expressions may be raised to fractional and floating-point powers. -Square matrix expressions may be raised to positive powers, and also to -negative powers if non-singular. - -\name{expt} is left associative. In other words, \name{a expt b expt c} is -equivalent to \name{a expt (b*c)}, not \name{a expt (b expt c)}, which -would be right associative. -\end{Comments} -\end{Operator} - - -\begin{Operator}{GCD} -\index{greatest common divisor}\index{polynomial} -The \name{gcd} operator returns the greatest common divisor of two -polynomials. -\begin{Syntax} -\name{gcd}\(\meta{expression},\meta{expression}\) -\end{Syntax} -\meta{expression} must be a polynomial (or integer), otherwise an error -occurs. - -\begin{Examples} -gcd(2*x**2 - 2*y**2,4*x + 4*y); & 2*(X + Y) \\ -gcd(sin(x),x**2 + 1); & 1 \\ -gcd(765,68); & 17 -\end{Examples} - -\begin{Comments} -The operator \name{gcd} described here provides an explicit means to find the -gcd of two expressions. The switch \name{gcd} described below simplifies -expressions by finding and canceling gcd's at every opportunity. When -the switch \nameref{ezgcd} is also on, gcd's are figured using the EZ GCD -algorithm, which is usually faster. -%%% The \nameref{heugcd} switch is also available, providing -%%% gcd's by the Heuristic algorithm. -\end{Comments} -\end{Operator} - - -\begin{Operator}{LN} -\index{logarithm} -\begin{Syntax} -\name{ln}\(\meta{expression}\) -\end{Syntax} -\meta{expression} can be any valid scalar REDUCE expression. - -The \name{ln} operator returns the natural logarithm of its argument. -However, unlike \nameref{log}, there are no algebraic rules associated -with it; it will only evaluate when \nameref{rounded} is on, and the -argument is a real number. - -\begin{Examples} -ln(x); & LN(X) \\ -ln 4; & LN(4) \\ -ln(e); & LN(E) \\ -df(ln(x),x); & DF(LN(X),X) \\ -on rounded; \\ -ln 4; & 1.38629436112 \\ -ln e; & 1 -\end{Examples} - -\begin{Comments} -Because of the restricted algebraic properties of \name{ln}, users are -advised to use \nameref{log} whenever possible. -\end{Comments} - -\end{Operator} - - -\begin{Operator}{LOG} -\index{logarithm} -The \name{log} operator returns the natural logarithm of its argument. -\begin{Syntax} -\name{log}\(\meta{expression}\) or \name{log} \meta{expression} -\end{Syntax} - -\meta{expression} can be any valid scalar REDUCE expression. - -\begin{Examples} -log(x); & LOG(X) \\ -log 4; & LOG(4) \\ -log(e); & 1 \\ -on rounded; \\ -log 4; & 1.38629436112 -\end{Examples} - -\begin{Comments} -\name{log} returns a numeric value only when \nameref{rounded} is on. In that -case, use of a negative argument for \name{log} results in an error -message. No error is given on a negative argument when REDUCE is not in -that mode. -\end{Comments} -\end{Operator} - - -\begin{Operator}{LOGB} -\index{logarithm} -\begin{Syntax} -\name{logb}\(\meta{expression}\,\meta{integer}\) -\end{Syntax} -\meta{expression} can be any valid scalar REDUCE expression. - -The \name{logb} operator returns the logarithm of its first argument using -the second argument as base. However, unlike \nameref{log}, there are no -algebraic rules associated with it; it will only evaluate when -\nameref{rounded} is on, and the first argument is a real number. - -\begin{Examples} -logb(x,2); & LOGB(X,2) \\ -logb(4,3); & LOGB(4,3) \\ -logb(2,2); & LOGB(2,2) \\ -df(logb(x,3),x); & DF(LOGB(X,3),X) \\ -on rounded; \\ -logb(4,3); & 1.26185950714 \\ -logb(2,2); & 1 -\end{Examples} - -\end{Operator} - - -\begin{Operator}{MAX} -\index{maximum} -The operator \name{max} is an n-ary prefix operator, which returns the largest -value in its arguments. -\begin{Syntax} -\name{max}\(\meta{expression}\{,\meta{expression}\}\optional\) - -\end{Syntax} - -\meta{expression} must evaluate to a number. \name{max} of an empty list -returns 0. - -\begin{Examples} -max(4,6,10,-1); & 10 \\ -<>; - & 46 \\ -max(-5,-10,-a); & -5 -\end{Examples} - -\end{Operator} - - -\begin{Operator}{MIN} -\index{minimum} -The operator \name{min} is an n-ary prefix operator, which returns the -smallest value in its arguments. -\begin{Syntax} -\name{min}\(\meta{expression}\{,\meta{expression}\}\optional\) -\end{Syntax} - -\meta{expression} must evaluate to a number. \name{min} of an empty list -returns 0. -\begin{Examples} -min(-3,0,17,2); & -3 \\ -<>; - & 16 \\ -min(5,10,a); & 5 -\end{Examples} -\end{Operator} - - -\begin{Operator}{MINUS} -The \name{minus} operator is a unary minus, returning the negative of its -argument. It is equivalent to the unary \name{-}. -\begin{Syntax} -\name{minus}\(\meta{expression}\) - - -\end{Syntax} - -\meta{expression} may be any scalar REDUCE expression. - -\begin{Examples} -minus(a); & - A \\ -minus(-1); & 1 \\ -minus((x+1)**4); & - (X^{4} + 4*X^{3} + 6*X^{2} + 4*X + 1) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{NEXTPRIME} -\index{prime number} -\begin{Syntax} -\name{nextprime}\(\meta{expression}\) -\end{Syntax} - -If the argument of \name{nextprime} is an integer, the least prime greater -than that argument is returned. Otherwise, a type error results. - -\begin{Examples} -nextprime 5001; & 5003 \\ -nextprime(10^30); & 1000000000000000000000000000057 \\ -nextprime a; & ***** A invalid as integer -\end{Examples} - -\end{Operator} - - -\begin{Switch}{NOCONVERT} -Under normal circumstances when \name{rounded} is on, \REDUCE\ converts the -number 1.0 to the integer 1. If this is not desired, the switch -\name{noconvert} can be turned on. -\begin{Examples} -on rounded; \\ -1.0000000000001; & 1 \\ -on noconvert; \\ -1.0000000000001; & 1.0 \\ -\end{Examples} -\end{Switch} - -\begin{Operator}{NORM} -\index{complex} -\begin{Syntax} -\name{norm}\(\meta{expression}\) -\end{Syntax} - -If \name{rounded} is on, and the argument is a real number, \meta{norm} -returns its absolute value. If \name{complex} is also on, \meta{norm} -returns the square root of the sum of squares of the real and imaginary -parts of the argument. In all other cases, a result is returned in -terms of the original operator. - -\begin{Examples} -norm (-2); & NORM(-2) \\ -on rounded;\\ -ws; & 2.0 \\ -norm(3+4i); & NORM(4*I+3) \\ -on complex;\\ -ws; & 5.0\\ -\end{Examples} - -\end{Operator} - - -\begin{Operator}{PERM} -\index{permutation} -\begin{Syntax} -perm(\meta{expression1},\meta{expression2}) -\end{Syntax} - -If \meta{expression1} and \meta{expression2} evaluate to positive integers, -\name{perm} returns the number of permutations possible in selecting -\meta{expression1} objects from \meta{expression2} objects. -In other cases, an expression in the original operator is returned. - -\begin{Examples} -perm(1,1); & 1 \\ -perm(3,5); & 60 \\ -perm(-3,5); & PERM(-3,5) \\ -perm(a,b); & PERM(A,B) -\end{Examples} - -\end{Operator} - -\begin{Operator}{PLUS} -The \name{plus} operator is both an infix and prefix n-ary addition -operator. It exists because of the way in which {\REDUCE} handles such -operators internally, and is not recommended for use in algebraic mode -programming. \nameref{plussign}, which has the identical effect, should be -used instead. -\begin{Syntax} -\name{plus}\(\meta{expression},\meta{expression}\{,\meta{expression}\} -\optional\) or \\ - \meta{expression} \name{plus} \meta{expression} \{\name{plus} \meta{expression}\}\optional -\end{Syntax} - -\meta{expression} can be any valid REDUCE expression, including matrix -expressions of the same dimensions. - -\begin{Examples} -a plus b plus c plus d; & A + B + C + D \\ -4.5 plus 10; & \rfrac{29}{2} \\\\ -plus(x**2,y**2); & X^{2} + Y^{2} -\end{Examples} -\end{Operator} - - -\begin{Operator}{QUOTIENT} -The \name{quotient} operator is both an infix and prefix binary operator that -returns the quotient of its first argument divided by its second. It is -also a unary \nameref{recip}rocal operator. It is identical to \name{/} and -\nameref{slash}. -\begin{Syntax} -\name{quotient}\(\meta{expression},\meta{expression}\) or -\meta{expression} \name{quotient} \meta{expression} or -\name{quotient}\(\meta{expression}\) or -\name{quotient} \meta{expression} -\end{Syntax} - -\meta{expression} can be any valid REDUCE scalar expression. Matrix -expressions can also be used if the second expression is invertible and the -matrices are of the correct dimensions. -\begin{Examples} -quotient(a,x+1); & \rfrac{A}{X + 1} \\ -7 quotient 17; & \rfrac{7}{17} \\ -on rounded; \\ -4.5 quotient 2; & 2.25 \\ -quotient(x**2 + 3*x + 2,x+1); & X + 2 \\ -matrix m,inverse; \\ -m := mat((a,b),(c,d)); & \begin{multilineoutput}{6cm} -M(1,1) := A; -M(1,2) := B; -M(2,1) := C -M(2,2) := D -\end{multilineoutput}\\ - -inverse := quotient m; & \begin{multilineoutput}{8cm} -INVERSE(1,1) := \rfrac{D}{A*D - B*C} -INVERSE(1,2) := - \rfrac{B}{A*D - B*C} -INVERSE(2,1) := - \rfrac{C}{A*D - B*C} -INVERSE(2,2) := \rfrac{A}{A*D - B*C} -\end{multilineoutput} - -\end{Examples} - -\begin{Comments} -The \name{quotient} operator is left associative: \name{a quotient b quotient c} -is equivalent to \name{(a quotient b) quotient c}. - -If a matrix argument to the unary \name{quotient} is not invertible, or if the -second matrix argument to the binary quotient is not invertible, an error -message is given. -\end{Comments} -\end{Operator} - - -\begin{Operator}{RAD2DEG} -\index{degrees}\index{radians} -\begin{Syntax} -\name{rad2deg}\(\meta{expression}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{expression} is a real number, the -operator \name{rad2deg} will interpret it as radians, and convert it to -the equivalent degrees. In all other cases, an expression in terms of the -original operator is returned. - -\begin{Examples} -rad2deg 1; & RAD2DEG(1) \\ -on rounded; \\ -ws; & 57.2957795131 \\ -rad2deg a; & RAD2DEG(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{RAD2DMS} -\index{degrees}\index{radians} - -\begin{Syntax} -\name{rad2dms}\(\meta{expression}\) -\end{Syntax} - -In \nameref{rounded} mode, if \meta{expression} is a real number, the -operator \name{rad2dms} will interpret it as radians, and convert it to a -list containing the equivalent degrees, minutes and seconds. In all other -cases, an expression in terms of the original operator is returned. - -\begin{Examples} -rad2dms 1; & RAD2DMS(1) \\ -on rounded; \\ -ws; & \{57,17,44.8062470964\} \\ -rad2dms a; & RAD2DMS(A) -\end{Examples} - -\end{Operator} - - -\begin{Operator}{RECIP} -\name{recip} is the alphabetical name for the division operator \name{/} -or \nameref{slash} used as a unary operator. The use of \name{/} is preferred. - -\begin{Examples} -recip a; & \rfrac{1}{A} \\ -recip 2; & \rfrac{1}{2} -\end{Examples} - -\end{Operator} - - -\begin{Operator}{REMAINDER} -\index{polynomial} -The \name{remainder} operator returns the remainder after its first -argument is divided by its second argument. - -\begin{Syntax} -\name{remainder}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} can be any valid REDUCE polynomial, and is not limited -to numeric values. - -\begin{Examples} -remainder(13,6); & 1 \\ -remainder(x**2 + 3*x + 2,x+1); & 0 \\ -remainder(x**3 + 12*x + 4,x**2 + 1); & 11*X + 4 \\ -remainder(sin(2*x),x*y); & SIN(2*X) -\end{Examples} - -\begin{Comments} -In the default case, remainders are calculated over the integers. If you -need the remainder with respect to another domain, it must be declared -explicitly. - -If the first argument to \name{remainder} contains a denominator not equal to -1, an error occurs. -\end{Comments} -\end{Operator} - - -\begin{Operator}{ROUND} -\index{integer} - -\begin{Syntax} -\name{round}\(\meta{expression}\) -\end{Syntax} - -If its argument has a numerical value, \name{round} rounds it to the -nearest integer. For non-numeric arguments, the value is an expression in -the original operator. - -\begin{Examples} -round 3.4; & 3 \\ -round 3.5; & 4 \\ -round a; & ROUND(A) -\end{Examples} - -\end{Operator} - - -\begin{Command}{SETMOD} -\index{modular} -The \name{setmod} command sets the modulus value for subsequent \nameref{modular} -arithmetic. -\begin{Syntax} -\name{setmod} \meta{integer} -\end{Syntax} - -\meta{integer} must be positive, and greater than 1. It need not be a prime -number. - -\begin{Examples} -setmod 6; & 1 \\ -on modular; \\ -16; & 4 \\ -x^2 + 5x + 7; & X^{2} + 5*X + 1 \\ -x/3; & \rfrac{X}{3} \\ -setmod 2; & 6 \\ -(x+1)^4; & X^{4} + 1 \\ -x/3; & X -\end{Examples} -\begin{Comments} -\name{setmod} returns the previous modulus, or 1 if none has been set -before. \name{setmod} only has effect when \nameref{modular} is on. - -Modular operations are done only on numbers such as coefficients of -polynomials, not on the exponents. The modulus need not be prime. -Attempts to divide by a power of the modulus produces an error message, since the -operation is equivalent to dividing by 0. However, dividing by a factor -of a non-prime modulus does not produce an error message. -\end{Comments} -\end{Command} - - -\begin{Operator}{SIGN} - -\begin{Syntax} -\name{sign} \meta{expression} -\end{Syntax} - -\name{sign} tries to evaluate the sign of its argument. If this -is possible \name{sign} returns one of 1, 0 or -1. Otherwise, the result -is the original form or a simplified variant. - -\begin{Examples} - sign(-5) & -1\\ - sign(-a^2*b) & -SIGN(B)\\ -\end{Examples} - -\begin{Comments} -Even powers of formal expressions are assumed to be positive only as long -as the switch \nameref{complex} is off. -\end{Comments} -\end{Operator} - - -\begin{Operator}{SQRT} -\index{square root} -The \name{sqrt} operator returns the square root of its argument. -\begin{Syntax} -\name{sqrt}\(\meta{expression}\) -\end{Syntax} - -\meta{expression} can be any REDUCE scalar expression. - -\begin{Examples} -sqrt(16*a^3); & 4*SQRT(A)*A \\ -sqrt(17); & SQRT(17) \\ -on rounded; \\ -sqrt(17); & 4.12310562562 \\ -off rounded; \\ -sqrt(a*b*c^5*d^3*27); & - 3*SQRT(D)*SQRT(C)*SQRT(B)*SQRT(A)*SQRT(3)*C^{2}*D -\end{Examples} -\begin{Comments} -\name{sqrt} checks its argument for squared factors and removes them. -% If the \name{reduced} switch is on, square roots of a product become a -% product of square roots. - -Numeric values for square roots that are not exact integers are given only -when \nameref{rounded} is on. - -Please note that \name{sqrt(a**2)} is given as \name{a}, which may be -incorrect if \name{a} eventually has a negative value. If you are -programming a calculation in which this is a concern, you can turn on the -\nameref{precise} switch, which causes the absolute value of the square root -to be returned. -\end{Comments} -\end{Operator} - - -\begin{Operator}{TIMES} -The \name{times} operator is an infix or prefix n-ary multiplication -operator. It is identical to \name{*}. -\begin{Syntax} -\meta{expression} \name{times} \meta{expression} \{\name{times} \meta{expression}\}\optional - - or \name{times}\(\meta{expression},\meta{expression} \{,\meta{expression}\}\optional\) -\end{Syntax} - -\meta{expression} can be any valid REDUCE scalar or matrix expression. -Matrix expressions must be of the correct dimensions. Compatible scalar -and matrix expressions can be mixed. - -\begin{Examples} -var1 times var2; & VAR1*VAR2 \\ -times(6,5); & 30 \\ -matrix aa,bb; \\ -aa := mat((1),(2),(x))\$ \\ -bb := mat((0,3,1))\$ \\ -aa times bb times 5; & -\begin{multilineoutput}{6cm} -[0 15 5 ] -[ ] -[0 30 10 ] -[ ] -[0 15*X 5*X] -\end{multilineoutput} -\end{Examples} -\end{Operator} - +\section{Arithmetic Operations} + +\begin{Introduction}{ARITHMETIC\_OPERATIONS} +This section considers operations defined in REDUCE that concern numbers, +or operators that can operate on numbers in addition, in most cases, to +more general expressions. +\end{Introduction} + +\begin{Operator}{ABS} +\index{absolute value} +The \name{abs} operator returns the absolute value of its argument. + +\begin{Syntax} +\name{abs}\(\meta{expression}\) +\end{Syntax} + +\meta{expression} can be any REDUCE scalar expression. + +\begin{Examples} +abs(-a); & ABS(A) \\ +abs(-5); & 5 \\ +a := -10; & A := -10 \\ +abs(a); & 10 \\ +abs(-a); & 10 +\end{Examples} +\begin{Comments} +If the argument has had no numeric value assigned to it, such as an +identifier or polynomial, \name{abs} returns an expression involving +\name{abs} of its argument, doing as much simplification of the argument +as it can, such as dropping any preceding minus sign. +\end{Comments} +\end{Operator} + + +\begin{Switch}{ADJPREC} +\index{input}\index{precision} +When a real number is input, it is normally truncated to the +\nameref{precision} in +effect at the time the number is read. If it is desired to keep the full +precision of all numbers input, the switch \name{adjprec} +(for \meta{adjust precision}) can be turned on. While on, \name{adjprec} +will automatically increase the precision, when necessary, to match that +of any integer or real input, and a message printed to inform the user of +the precision increase. + +\begin{Examples} +on rounded; \\ +1.23456789012345; & 1.23456789012 \\ +on adjprec; \\ +1.23456789012345; \\ +*** precision increased to 15 \\ +1.23456789012345 +\end{Examples} +\end{Switch} + + +\begin{Operator}{ARG} +\index{complex}\index{polar angle} +If \nameref{complex} and \nameref{rounded} are on, and {\em arg} +evaluates to a complex number, \name{arg} returns the polar angle of {\em +arg}, measured in radians. Otherwise an expression in {\em arg} is +returned. + +\begin{Examples} +arg(3+4i) & ARG(3 + 4*I) \\ +on rounded, complex; \\ +ws; & 0.927295218002 \\ +arg a; & ARG(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{CEILING} +\index{integer} + +\begin{Syntax} +\name{ceiling}\(\meta{expression}\) +\end{Syntax} + +This operator returns the ceiling (i.e., the least integer greater than or +equal to its argument) if its argument has a numerical value. For +negative numbers, this is equivalent to \nameref{fix}. For non-numeric +arguments, the value is an expression in the original operator. + +\begin{Examples} +ceiling 3.4; & 4 \\ +fix 3.4; & 3 \\ +ceiling(-5.2); & -5 \\ +fix(-5.2); & -5 \\ +ceiling a; & CEILING(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{CHOOSE} +\name{choose}(\meta{m},\meta{m}) returns the number of ways of choosing +\meta{m} objects from a collection of \meta{n} distinct objects --- in other +words the binomial coefficient. If \meta{m} and \meta{n} are not positive +integers, or $m > n$, the expression is returned unchanged. +than or equal to +\begin{Examples} +choose(2,3); & 3 \\ +choose(3,2); & CHOOSE(3,2) \\ +choose(a,b); & CHOOSE(A,B) +\end{Examples} +\end{Operator} + + +\begin{Operator}{DEG2DMS} +\index{degrees}\index{radians} +\begin{Syntax} +\name{deg2dms}\(\meta{expression}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{expression} is a real number, the +operator \name{deg2dms} will interpret it as degrees, and convert it to a +list containing the equivalent degrees, minutes and seconds. In all other +cases, an expression in terms of the original operator is returned. + +\begin{Examples} +deg2dms 60; & DEG2DMS(60) \\ +on rounded; \\ +ws; & \{60,0,0\} \\ +deg2dms 42.4; & \{42,23,60.0\} \\ +deg2dms a; & DEG2DMS(A) +\end{Examples} + +\end{Operator} + +\begin{Operator}{DEG2RAD} +\index{degrees}\index{radians} + +\begin{Syntax} +\name{deg2rad}\(\meta{expression}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{expression} is a real number, the +operator \name{deg2rad} will interpret it as degrees, and convert it to +the equivalent radians. In all other cases, an expression in terms of the +original operator is returned. + +\begin{Examples} +deg2rad 60; & DEG2RAD(60) \\ +on rounded; \\ +ws; & 1.0471975512 \\ +deg2rad a; & DEG2RAD(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{DIFFERENCE} +The \name{difference} operator may be used as either an infix or prefix binary +subtraction operator. It is identical to \name{-} as a binary operator. + +\begin{Syntax} +\name{difference}\(\meta{expression},\meta{expression}\) or + +\meta{expression} \name{difference} \meta{expression} + \{\name{difference} \meta{expression}\}\optional +\end{Syntax} + +\meta{expression} can be a number or any other valid REDUCE expression. Matrix +expressions are allowed if they are of the same dimensions. + +\begin{Examples} + +difference(10,4); & 6 \\ + +15 difference 5 difference 2; & 8 \\ + +a difference b; & A - B + +\end{Examples} + +\begin{Comments} +The \name{difference} operator is left associative, as shown in the second +example above. + +\end{Comments} +\end{Operator} + + +\begin{Operator}{DILOG} +\index{dilogarithm function} +The \name{dilog} operator is known to the differentiation and integration +operators, but has numeric value attached only at \name{dilog(0)}. Dilog is +defined by +\begin{TEX} +\begin{displaymath} + dilog(x) = -\int{{log(x)\,dx}\over{x-1}} +\end{displaymath} +\end{TEX} +\begin{INFO} + dilog(x) = -int(log(x),x)/(x-1) +\end{INFO} +\begin{Examples} +df(dilog(x**2),x); & - \rfrac{2*LOG(X^{2})*X}{X^{2} - 1}\\ + +int(dilog(x),x); & DILOG(X)*X - DILOG(X) + LOG(X)*X - X \\ + +dilog(0); & \rfrac{PI^{2}}{6} +\end{Examples} + +\end{Operator} + + +\begin{Operator}{DMS2DEG} +\index{degrees}\index{radians} + +\begin{Syntax} +\name{dms2deg}\(\meta{list}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{list} is a list of three real numbers, +the operator \name{dms2deg} will interpret the list as degrees, minutes +and seconds and convert it to the equivalent degrees. In all other cases, +an expression in terms of the original operator is returned. + +\begin{Examples} +dms2deg \{42,3,7\}; & DMS2DEG(\{42,3,7\}) \\ +on rounded; \\ +ws; & 42.0519444444 \\ +dms2deg a; & DMS2DEG(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{DMS2RAD} +\index{degrees}\index{radians} + +\begin{Syntax} +\name{dms2rad}\(\meta{list}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{list} is a list of three real numbers, +the operator \name{dms2rad} will interpret the list as degrees, minutes +and seconds and convert it to the equivalent radians. In all other cases, +an expression in terms of the original operator is returned. + +\begin{Examples} +dms2rad \{42,3,7\}; & DMS2RAD(\{42,3,7\}) \\ +on rounded; \\ +ws; & 0.733944887421 \\ +dms2rad a; & DMS2RAD(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{FACTORIAL} +\index{gamma} +\begin{Syntax} +\name{factorial}\(\meta{expression}\) +\end{Syntax} + +If the argument of \name{factorial} is a positive integer or zero, its +factorial is returned. Otherwise the result is expressed in terms of the +original operator. For more general operations, the \nameref{gamma} operator +is available in the \nameref{Special Function Package}. + +\begin{Examples} +factorial 4; & 24 \\ +factorial 30 ; & 265252859812191058636308480000000 \\ +factorial(a) ; FACTORIAL(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{FIX} +\index{integer} +\begin{Syntax} +\name{fix}\(\meta{expression}\) +\end{Syntax} + +The operator \name{fix} returns the integer part of its argument, if that +argument has a numerical value. For positive numbers, this is equivalent +to \nameref{floor}, and, for negative numbers, \nameref{ceiling}. For +non-numeric arguments, the value is an expression in the original operator. + +\begin{Examples} +fix 3.4; & 3 \\ +floor 3.4; & 3 \\ +ceiling 3.4; & 4 \\ +fix(-5.2); & -5 \\ +floor(-5.2); & -6 \\ +ceiling(-5.2); & -5 \\ +fix(a); & FIX(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{FIXP} +\index{integer} +The \name{fixp} logical operator returns true if its argument is an integer. +\begin{Syntax} +\name{fixp}\(\meta{expression}\) or \name{fixp} \meta{simple\_expression} +\end{Syntax} + +\meta{expression} can be any valid REDUCE expression, \meta{simple\_expression} +must be a single identifier or begin with a prefix operator. + +\begin{Examples} +if fixp 1.5 then write "ok" else write "not"; + & not \\ +if fixp(a) then write "ok" else write "not"; + & not \\ +a := 15; & A := 15 \\ +if fixp(a) then write "ok" else write "not"; + & ok +\end{Examples} + +\begin{Comments} +Logical operators can only be used inside conditional expressions such as +\name{if}\ldots\name{then} or \name{while}\ldots\name{do}. +\end{Comments} +\end{Operator} + + +\begin{Operator}{FLOOR} +\index{integer} + +\begin{Syntax} +\name{floor}\(\meta{expression}\) +\end{Syntax} + +This operator returns the floor (i.e., the greatest integer less than or +equal to its argument) if its argument has a numerical value. For +positive numbers, this is equivalent to \nameref{fix}. For non-numeric +arguments, the value is an expression in the original operator. + +\begin{Examples} +floor 3.4; & 3 \\ +fix 3.4; & 3 \\ +floor(-5.2); & -6 \\ +fix(-5.2); & -5 \\ +floor a; & FLOOR(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{EXPT} +The \name{expt} operator is both an infix and prefix binary exponentiation +operator. It is identical to \name{^} or \name{**}. +\begin{Syntax} +\name{expt}\(\meta{expression},\meta{expression}\) + or \meta{expression} \name{expt} \meta{expression} +\end{Syntax} +\begin{Examples} +a expt b; & A^{B} \\ +expt(a,b); & A^{B} \\ +(x+y) expt 4; & X^{4} + 4*X^{3}*Y + 6*X^{2}*Y^{2} + 4*X*Y^{3} + Y^{4} +\end{Examples} +\begin{Comments} +Scalar expressions may be raised to fractional and floating-point powers. +Square matrix expressions may be raised to positive powers, and also to +negative powers if non-singular. + +\name{expt} is left associative. In other words, \name{a expt b expt c} is +equivalent to \name{a expt (b*c)}, not \name{a expt (b expt c)}, which +would be right associative. +\end{Comments} +\end{Operator} + + +\begin{Operator}{GCD} +\index{greatest common divisor}\index{polynomial} +The \name{gcd} operator returns the greatest common divisor of two +polynomials. +\begin{Syntax} +\name{gcd}\(\meta{expression},\meta{expression}\) +\end{Syntax} +\meta{expression} must be a polynomial (or integer), otherwise an error +occurs. + +\begin{Examples} +gcd(2*x**2 - 2*y**2,4*x + 4*y); & 2*(X + Y) \\ +gcd(sin(x),x**2 + 1); & 1 \\ +gcd(765,68); & 17 +\end{Examples} + +\begin{Comments} +The operator \name{gcd} described here provides an explicit means to find the +gcd of two expressions. The switch \name{gcd} described below simplifies +expressions by finding and canceling gcd's at every opportunity. When +the switch \nameref{ezgcd} is also on, gcd's are figured using the EZ GCD +algorithm, which is usually faster. +%%% The \nameref{heugcd} switch is also available, providing +%%% gcd's by the Heuristic algorithm. +\end{Comments} +\end{Operator} + + +\begin{Operator}{LN} +\index{logarithm} +\begin{Syntax} +\name{ln}\(\meta{expression}\) +\end{Syntax} +\meta{expression} can be any valid scalar REDUCE expression. + +The \name{ln} operator returns the natural logarithm of its argument. +However, unlike \nameref{log}, there are no algebraic rules associated +with it; it will only evaluate when \nameref{rounded} is on, and the +argument is a real number. + +\begin{Examples} +ln(x); & LN(X) \\ +ln 4; & LN(4) \\ +ln(e); & LN(E) \\ +df(ln(x),x); & DF(LN(X),X) \\ +on rounded; \\ +ln 4; & 1.38629436112 \\ +ln e; & 1 +\end{Examples} + +\begin{Comments} +Because of the restricted algebraic properties of \name{ln}, users are +advised to use \nameref{log} whenever possible. +\end{Comments} + +\end{Operator} + + +\begin{Operator}{LOG} +\index{logarithm} +The \name{log} operator returns the natural logarithm of its argument. +\begin{Syntax} +\name{log}\(\meta{expression}\) or \name{log} \meta{expression} +\end{Syntax} + +\meta{expression} can be any valid scalar REDUCE expression. + +\begin{Examples} +log(x); & LOG(X) \\ +log 4; & LOG(4) \\ +log(e); & 1 \\ +on rounded; \\ +log 4; & 1.38629436112 +\end{Examples} + +\begin{Comments} +\name{log} returns a numeric value only when \nameref{rounded} is on. In that +case, use of a negative argument for \name{log} results in an error +message. No error is given on a negative argument when REDUCE is not in +that mode. +\end{Comments} +\end{Operator} + + +\begin{Operator}{LOGB} +\index{logarithm} +\begin{Syntax} +\name{logb}\(\meta{expression}\,\meta{integer}\) +\end{Syntax} +\meta{expression} can be any valid scalar REDUCE expression. + +The \name{logb} operator returns the logarithm of its first argument using +the second argument as base. However, unlike \nameref{log}, there are no +algebraic rules associated with it; it will only evaluate when +\nameref{rounded} is on, and the first argument is a real number. + +\begin{Examples} +logb(x,2); & LOGB(X,2) \\ +logb(4,3); & LOGB(4,3) \\ +logb(2,2); & LOGB(2,2) \\ +df(logb(x,3),x); & DF(LOGB(X,3),X) \\ +on rounded; \\ +logb(4,3); & 1.26185950714 \\ +logb(2,2); & 1 +\end{Examples} + +\end{Operator} + + +\begin{Operator}{MAX} +\index{maximum} +The operator \name{max} is an n-ary prefix operator, which returns the largest +value in its arguments. +\begin{Syntax} +\name{max}\(\meta{expression}\{,\meta{expression}\}\optional\) + +\end{Syntax} + +\meta{expression} must evaluate to a number. \name{max} of an empty list +returns 0. + +\begin{Examples} +max(4,6,10,-1); & 10 \\ +<>; + & 46 \\ +max(-5,-10,-a); & -5 +\end{Examples} + +\end{Operator} + + +\begin{Operator}{MIN} +\index{minimum} +The operator \name{min} is an n-ary prefix operator, which returns the +smallest value in its arguments. +\begin{Syntax} +\name{min}\(\meta{expression}\{,\meta{expression}\}\optional\) +\end{Syntax} + +\meta{expression} must evaluate to a number. \name{min} of an empty list +returns 0. +\begin{Examples} +min(-3,0,17,2); & -3 \\ +<>; + & 16 \\ +min(5,10,a); & 5 +\end{Examples} +\end{Operator} + + +\begin{Operator}{MINUS} +The \name{minus} operator is a unary minus, returning the negative of its +argument. It is equivalent to the unary \name{-}. +\begin{Syntax} +\name{minus}\(\meta{expression}\) + + +\end{Syntax} + +\meta{expression} may be any scalar REDUCE expression. + +\begin{Examples} +minus(a); & - A \\ +minus(-1); & 1 \\ +minus((x+1)**4); & - (X^{4} + 4*X^{3} + 6*X^{2} + 4*X + 1) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{NEXTPRIME} +\index{prime number} +\begin{Syntax} +\name{nextprime}\(\meta{expression}\) +\end{Syntax} + +If the argument of \name{nextprime} is an integer, the least prime greater +than that argument is returned. Otherwise, a type error results. + +\begin{Examples} +nextprime 5001; & 5003 \\ +nextprime(10^30); & 1000000000000000000000000000057 \\ +nextprime a; & ***** A invalid as integer +\end{Examples} + +\end{Operator} + + +\begin{Switch}{NOCONVERT} +Under normal circumstances when \name{rounded} is on, \REDUCE\ converts the +number 1.0 to the integer 1. If this is not desired, the switch +\name{noconvert} can be turned on. +\begin{Examples} +on rounded; \\ +1.0000000000001; & 1 \\ +on noconvert; \\ +1.0000000000001; & 1.0 \\ +\end{Examples} +\end{Switch} + +\begin{Operator}{NORM} +\index{complex} +\begin{Syntax} +\name{norm}\(\meta{expression}\) +\end{Syntax} + +If \name{rounded} is on, and the argument is a real number, \meta{norm} +returns its absolute value. If \name{complex} is also on, \meta{norm} +returns the square root of the sum of squares of the real and imaginary +parts of the argument. In all other cases, a result is returned in +terms of the original operator. + +\begin{Examples} +norm (-2); & NORM(-2) \\ +on rounded;\\ +ws; & 2.0 \\ +norm(3+4i); & NORM(4*I+3) \\ +on complex;\\ +ws; & 5.0\\ +\end{Examples} + +\end{Operator} + + +\begin{Operator}{PERM} +\index{permutation} +\begin{Syntax} +perm(\meta{expression1},\meta{expression2}) +\end{Syntax} + +If \meta{expression1} and \meta{expression2} evaluate to positive integers, +\name{perm} returns the number of permutations possible in selecting +\meta{expression1} objects from \meta{expression2} objects. +In other cases, an expression in the original operator is returned. + +\begin{Examples} +perm(1,1); & 1 \\ +perm(3,5); & 60 \\ +perm(-3,5); & PERM(-3,5) \\ +perm(a,b); & PERM(A,B) +\end{Examples} + +\end{Operator} + +\begin{Operator}{PLUS} +The \name{plus} operator is both an infix and prefix n-ary addition +operator. It exists because of the way in which {\REDUCE} handles such +operators internally, and is not recommended for use in algebraic mode +programming. \nameref{plussign}, which has the identical effect, should be +used instead. +\begin{Syntax} +\name{plus}\(\meta{expression},\meta{expression}\{,\meta{expression}\} +\optional\) or \\ + \meta{expression} \name{plus} \meta{expression} \{\name{plus} \meta{expression}\}\optional +\end{Syntax} + +\meta{expression} can be any valid REDUCE expression, including matrix +expressions of the same dimensions. + +\begin{Examples} +a plus b plus c plus d; & A + B + C + D \\ +4.5 plus 10; & \rfrac{29}{2} \\\\ +plus(x**2,y**2); & X^{2} + Y^{2} +\end{Examples} +\end{Operator} + + +\begin{Operator}{QUOTIENT} +The \name{quotient} operator is both an infix and prefix binary operator that +returns the quotient of its first argument divided by its second. It is +also a unary \nameref{recip}rocal operator. It is identical to \name{/} and +\nameref{slash}. +\begin{Syntax} +\name{quotient}\(\meta{expression},\meta{expression}\) or +\meta{expression} \name{quotient} \meta{expression} or +\name{quotient}\(\meta{expression}\) or +\name{quotient} \meta{expression} +\end{Syntax} + +\meta{expression} can be any valid REDUCE scalar expression. Matrix +expressions can also be used if the second expression is invertible and the +matrices are of the correct dimensions. +\begin{Examples} +quotient(a,x+1); & \rfrac{A}{X + 1} \\ +7 quotient 17; & \rfrac{7}{17} \\ +on rounded; \\ +4.5 quotient 2; & 2.25 \\ +quotient(x**2 + 3*x + 2,x+1); & X + 2 \\ +matrix m,inverse; \\ +m := mat((a,b),(c,d)); & \begin{multilineoutput}{6cm} +M(1,1) := A; +M(1,2) := B; +M(2,1) := C +M(2,2) := D +\end{multilineoutput}\\ + +inverse := quotient m; & \begin{multilineoutput}{8cm} +INVERSE(1,1) := \rfrac{D}{A*D - B*C} +INVERSE(1,2) := - \rfrac{B}{A*D - B*C} +INVERSE(2,1) := - \rfrac{C}{A*D - B*C} +INVERSE(2,2) := \rfrac{A}{A*D - B*C} +\end{multilineoutput} + +\end{Examples} + +\begin{Comments} +The \name{quotient} operator is left associative: \name{a quotient b quotient c} +is equivalent to \name{(a quotient b) quotient c}. + +If a matrix argument to the unary \name{quotient} is not invertible, or if the +second matrix argument to the binary quotient is not invertible, an error +message is given. +\end{Comments} +\end{Operator} + + +\begin{Operator}{RAD2DEG} +\index{degrees}\index{radians} +\begin{Syntax} +\name{rad2deg}\(\meta{expression}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{expression} is a real number, the +operator \name{rad2deg} will interpret it as radians, and convert it to +the equivalent degrees. In all other cases, an expression in terms of the +original operator is returned. + +\begin{Examples} +rad2deg 1; & RAD2DEG(1) \\ +on rounded; \\ +ws; & 57.2957795131 \\ +rad2deg a; & RAD2DEG(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{RAD2DMS} +\index{degrees}\index{radians} + +\begin{Syntax} +\name{rad2dms}\(\meta{expression}\) +\end{Syntax} + +In \nameref{rounded} mode, if \meta{expression} is a real number, the +operator \name{rad2dms} will interpret it as radians, and convert it to a +list containing the equivalent degrees, minutes and seconds. In all other +cases, an expression in terms of the original operator is returned. + +\begin{Examples} +rad2dms 1; & RAD2DMS(1) \\ +on rounded; \\ +ws; & \{57,17,44.8062470964\} \\ +rad2dms a; & RAD2DMS(A) +\end{Examples} + +\end{Operator} + + +\begin{Operator}{RECIP} +\name{recip} is the alphabetical name for the division operator \name{/} +or \nameref{slash} used as a unary operator. The use of \name{/} is preferred. + +\begin{Examples} +recip a; & \rfrac{1}{A} \\ +recip 2; & \rfrac{1}{2} +\end{Examples} + +\end{Operator} + + +\begin{Operator}{REMAINDER} +\index{polynomial} +The \name{remainder} operator returns the remainder after its first +argument is divided by its second argument. + +\begin{Syntax} +\name{remainder}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} can be any valid REDUCE polynomial, and is not limited +to numeric values. + +\begin{Examples} +remainder(13,6); & 1 \\ +remainder(x**2 + 3*x + 2,x+1); & 0 \\ +remainder(x**3 + 12*x + 4,x**2 + 1); & 11*X + 4 \\ +remainder(sin(2*x),x*y); & SIN(2*X) +\end{Examples} + +\begin{Comments} +In the default case, remainders are calculated over the integers. If you +need the remainder with respect to another domain, it must be declared +explicitly. + +If the first argument to \name{remainder} contains a denominator not equal to +1, an error occurs. +\end{Comments} +\end{Operator} + + +\begin{Operator}{ROUND} +\index{integer} + +\begin{Syntax} +\name{round}\(\meta{expression}\) +\end{Syntax} + +If its argument has a numerical value, \name{round} rounds it to the +nearest integer. For non-numeric arguments, the value is an expression in +the original operator. + +\begin{Examples} +round 3.4; & 3 \\ +round 3.5; & 4 \\ +round a; & ROUND(A) +\end{Examples} + +\end{Operator} + + +\begin{Command}{SETMOD} +\index{modular} +The \name{setmod} command sets the modulus value for subsequent \nameref{modular} +arithmetic. +\begin{Syntax} +\name{setmod} \meta{integer} +\end{Syntax} + +\meta{integer} must be positive, and greater than 1. It need not be a prime +number. + +\begin{Examples} +setmod 6; & 1 \\ +on modular; \\ +16; & 4 \\ +x^2 + 5x + 7; & X^{2} + 5*X + 1 \\ +x/3; & \rfrac{X}{3} \\ +setmod 2; & 6 \\ +(x+1)^4; & X^{4} + 1 \\ +x/3; & X +\end{Examples} +\begin{Comments} +\name{setmod} returns the previous modulus, or 1 if none has been set +before. \name{setmod} only has effect when \nameref{modular} is on. + +Modular operations are done only on numbers such as coefficients of +polynomials, not on the exponents. The modulus need not be prime. +Attempts to divide by a power of the modulus produces an error message, since the +operation is equivalent to dividing by 0. However, dividing by a factor +of a non-prime modulus does not produce an error message. +\end{Comments} +\end{Command} + + +\begin{Operator}{SIGN} + +\begin{Syntax} +\name{sign} \meta{expression} +\end{Syntax} + +\name{sign} tries to evaluate the sign of its argument. If this +is possible \name{sign} returns one of 1, 0 or -1. Otherwise, the result +is the original form or a simplified variant. + +\begin{Examples} + sign(-5) & -1\\ + sign(-a^2*b) & -SIGN(B)\\ +\end{Examples} + +\begin{Comments} +Even powers of formal expressions are assumed to be positive only as long +as the switch \nameref{complex} is off. +\end{Comments} +\end{Operator} + + +\begin{Operator}{SQRT} +\index{square root} +The \name{sqrt} operator returns the square root of its argument. +\begin{Syntax} +\name{sqrt}\(\meta{expression}\) +\end{Syntax} + +\meta{expression} can be any REDUCE scalar expression. + +\begin{Examples} +sqrt(16*a^3); & 4*SQRT(A)*A \\ +sqrt(17); & SQRT(17) \\ +on rounded; \\ +sqrt(17); & 4.12310562562 \\ +off rounded; \\ +sqrt(a*b*c^5*d^3*27); & + 3*SQRT(D)*SQRT(C)*SQRT(B)*SQRT(A)*SQRT(3)*C^{2}*D +\end{Examples} +\begin{Comments} +\name{sqrt} checks its argument for squared factors and removes them. +% If the \name{reduced} switch is on, square roots of a product become a +% product of square roots. + +Numeric values for square roots that are not exact integers are given only +when \nameref{rounded} is on. + +Please note that \name{sqrt(a**2)} is given as \name{a}, which may be +incorrect if \name{a} eventually has a negative value. If you are +programming a calculation in which this is a concern, you can turn on the +\nameref{precise} switch, which causes the absolute value of the square root +to be returned. +\end{Comments} +\end{Operator} + + +\begin{Operator}{TIMES} +The \name{times} operator is an infix or prefix n-ary multiplication +operator. It is identical to \name{*}. +\begin{Syntax} +\meta{expression} \name{times} \meta{expression} \{\name{times} \meta{expression}\}\optional + + or \name{times}\(\meta{expression},\meta{expression} \{,\meta{expression}\}\optional\) +\end{Syntax} + +\meta{expression} can be any valid REDUCE scalar or matrix expression. +Matrix expressions must be of the correct dimensions. Compatible scalar +and matrix expressions can be mixed. + +\begin{Examples} +var1 times var2; & VAR1*VAR2 \\ +times(6,5); & 30 \\ +matrix aa,bb; \\ +aa := mat((1),(2),(x))\$ \\ +bb := mat((0,3,1))\$ \\ +aa times bb times 5; & +\begin{multilineoutput}{6cm} +[0 15 5 ] +[ ] +[0 30 10 ] +[ ] +[0 15*X 5*X] +\end{multilineoutput} +\end{Examples} +\end{Operator} + Index: r36/help/linalg.tex ================================================================== --- r36/help/linalg.tex +++ r36/help/linalg.tex @@ -1,2081 +1,2081 @@ -\section{Linear Algebra package} - -\begin{Introduction}{Linear Algebra package} - -This section briefly describes what's available in the Linear Algebra -package. - -Note on examples: In the examples throughout this -document, the matrix A will be -\begin{verbatim} - [1 2 3] - [4 5 6] - [7 8 9]. -\end{verbatim} - -The functions can be divided into four categories: - -{\bf Basic matrix handling} - -\nameref{add\_columns}, - -\nameref{add\_rows}, - -\nameref{add\_to\_columns}, - -\nameref{add\_to\_rows}, - -\nameref{augment\_columns}, - -\nameref{char\_poly}, - -\nameref{column\_dim}, - -\nameref{copy\_into}, - -\nameref{diagonal}, - -\nameref{extend}, - -\nameref{find\_companion}, - -\nameref{get\_columns}, - -\nameref{get\_rows}, - -\nameref{hermitian\_tp}, - -\nameref{matrix\_augment}, - -\nameref{matrix\_stack} , - -\nameref{minor}, - -\nameref{mult\_columns}, - -\nameref{mult\_rows}, - -\nameref{pivot}, - -\nameref{remove\_columns}, - -\nameref{remove\_rows}, - -\nameref{row\_dim}, - -\nameref{rows\_pivot}, - -\nameref{stack\_rows}, - -\nameref{sub\_matrix}, - -\nameref{swap\_columns}, - -\nameref{swap\_entries}, - -\nameref{swap\_rows}. - -{\bf Constructors -- functions that create matrices} - -\nameref{band\_matrix}, - -\nameref{block\_matrix}, - -\nameref{char\_matrix}, - -\nameref{coeff\_matrix}, - -\nameref{companion}, - -\nameref{hessian}, - -\nameref{hilbert}, - -\nameref{jacobian}, - -\nameref{jordan\_block}, - -\nameref{make\_identity}, - -\nameref{random\_matrix}, - -\nameref{toeplitz}, - -\nameref{vandermonde}. - -{\bf High level algorithms} - -\nameref{char\_poly}, - -\nameref{cholesky}, - -\nameref{gram\_schmidt}, - -\nameref{lu\_decom}, - -\nameref{pseudo\_inverse}, - -\nameref{simplex}, - -\nameref{svd}. - -{\bf Normal Forms} - -There is a separate package, NORMFORM, for computing -the following matrix normal forms in \REDUCE: - -\nameref{smithex}, - -\nameref{smithex\_int}, - -\nameref{frobenius}, - -\nameref{ratjordan}, - -\nameref{jordansymbolic}, - -\nameref{jordan}. - - -{\bf Predicates} - -\nameref{matrixp}, - -\nameref{squarep}, - -\nameref{symmetricp}. - -\end{Introduction} - - -\begin{Switch}{fast_la} - -By turning the \name{fast\_la} switch on, the speed of the following -functions will be increased: - - -\nameref{add\_columns}, - -\nameref{add\_rows}, - -\nameref{augment\_columns}, - -\nameref{column\_dim}, - -\nameref{copy\_into}, - -\nameref{make\_identity}, - -\nameref{matrix\_augment}, - -\nameref{matrix\_stack}, - -\nameref{minor}, - -\nameref{mult\_columns}, - -\nameref{mult\_rows}, - -\nameref{pivot}, - -\nameref{remove\_columns}, - -\nameref{remove\_rows}, - -\nameref{rows\_pivot}, - -\nameref{squarep}, - -\nameref{stack\_rows}, - -\nameref{sub\_matrix}, - -\nameref{swap\_columns}, - -\nameref{swap\_entries}, - -\nameref{swap\_rows}, - -\nameref{symmetricp}. - - -The increase in speed will be negligible unless you are making a -significant number (i.e. thousands) of calls. When using this switch, -error checking is minimized. This means that illegal input may give -strange error messages. Beware. -\end{Switch} - -\begin{Operator}{add_columns} -Add columns, add rows: -\begin{Syntax} -\name{add\_columns}\(\meta{matrix},\meta{c1},\meta{c2},\meta{expr}\) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{c1},\meta{c2} :- positive integers. - -\meta{expr} :- a scalar expression. - -The Operator \name{add\_columns} replaces column \meta{\meta{c2}} of -\meta{matrix} by \meta{expr} * column(\meta{matrix},\meta{c1}) + -column(\meta{matrix},\meta{c2}). - -\name{add\_rows} performs the equivalent task on the rows of -\meta{matrix}. - -\begin{Examples} - -add_columns(A,1,2,x); & -\begin{multilineoutput}{6cm} -[1 x + 2 3] -[ ] -[4 4*x + 5 6] -[ ] -[7 7*x + 8 9] -\end{multilineoutput} \\ - -add_rows(A,2,3,5); & -\begin{multilineoutput}{6cm} -[1 2 3 ] -[ ] -[4 5 6 ] -[ ] -[27 33 39] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: \nameref{add\_to\_columns}, -\nameref{add\_to\_rows}, \nameref{mult\_columns}, -\nameref{mult\_rows}. - -\end{Operator} - - -\begin{Operator}{add_rows} - see: \nameref{add\_columns}. -\end{Operator} - - -\begin{Operator}{add_to_columns} -Add to columns, add to rows: - -\begin{Syntax} -\name{add\_to\_columns}\(\meta{matrix},\meta{column\_list},\meta{expr}\) -\end{Syntax} - -\meta{matrix} :- a matrix. - -\meta{column\_list} :- a positive integer or a list of positive - integers. - -\meta{expr} :- a scalar expression. - -\name{add\_to\_columns} adds \meta{expr} to each column specified in -\meta{column\_list} of \meta{matrix}. - -\name{add\_to\_rows} performs the equivalent task on the rows of -\meta{matrix}. - -\begin{Examples} - -add_to_columns(A,\{1,2\},10); & -\begin{multilineoutput}{6cm} -[11 12 3] -[ ] -[14 15 6] -[ ] -[17 18 9] -\end{multilineoutput}\\ - -add_to_rows(A,2,-x) & -\begin{multilineoutput}{6cm} -[ 1 2 3 ] -[ ] -[ - x + 4 - x + 5 - x + 6] -[ ] -[ 7 8 9 ] -\end{multilineoutput} \\ -\end{Examples} - -Related functions: -\nameref{add\_columns}, \nameref{add\_rows}, \nameref{mult\_rows}, -\nameref{mult\_columns}. - -\end{Operator} - - -\begin{Operator}{add_to_rows} - see: \nameref{add\_to\_columns}. -\end{Operator} - - -\begin{Operator}{augment_columns} -Augment columns, stack rows: - -\begin{Syntax} -\name{augment\_columns}(\meta{matrix},\meta{column\_list}) -\end{Syntax} - -\meta{matrix} :- a matrix. - -\meta{column\_list} :- either a positive integer or a list of positive - integers. - -\name{augment\_columns} gets hold of the columns of \meta{matrix} -specified in \name{column\_list} and sticks them together. - -\name{stack\_rows} performs the same task on rows of \meta{matrix}. - -\begin{Examples} - -augment_columns(A,\{1,2\}) & -\begin{multilineoutput}{6cm} -[1 2] -[ ] -[4 5] -[ ] -[7 8] -\end{multilineoutput} \\ - -stack_rows(A,\{1,3\}) & -\begin{multilineoutput}{6cm} -[1 2 3] -[ ] -[7 8 9] -\end{multilineoutput} \\ -\end{Examples} - -Related functions: -\nameref{get\_columns}, \nameref{get\_rows}, \nameref{sub\_matrix}. - -\end{Operator} - - -\begin{Operator}{band_matrix} - -\begin{Syntax} -\name{band\_matrix}(\meta{expr\_list},\meta{square\_size}) -\end{Syntax} - -\meta{expr\_list} :- either a single scalar expression or a list of - an odd number of scalar expressions. - -\meta{square\_size} :- a positive integer. - -\name{band\_matrix} creates a square matrix of dimension -\meta{square\_size}. The diagonal consists of the middle expression -of the \meta{expr\_list}. The expressions to the left of this fill -the required number of sub\_diagonals and the expressions to the right -the super\_diagonals. - -\begin{Examples} - -band_matrix(\{x,y,z\},6) & -\begin{multilineoutput}{6cm} -[y z 0 0 0 0] -[ ] -[x y z 0 0 0] -[ ] -[0 x y z 0 0] -[ ] -[0 0 x y z 0] -[ ] -[0 0 0 x y z] -[ ] -[0 0 0 0 x y] -\end{multilineoutput} \\ -\end{Examples} - -Related functions: \nameref{diagonal}. - -\end{Operator} - - -\begin{Operator}{block_matrix} - -\begin{Syntax} -\name{block\_matrix}(\meta{r},\meta{c},\meta{matrix\_list}) -\end{Syntax} - -\meta{r},\meta{c} :- positive integers. - -\meta{matrix\_list} :- a list of matrices. - -\name{block\_matrix} creates a matrix that consists of \meta{r} by -\meta{c} matrices filled from the \meta{matrix\_list} row wise. - -\begin{Examples} -B := make_identity(2); & -\begin{multilineoutput}{6cm} - [1 0] -b := [ ] - [0 1] -\end{multilineoutput} \\ - -C := mat((5),(5)); & -\begin{multilineoutput}{6cm} - [5] -c := [ ] - [5] -\end{multilineoutput} \\ - -D := mat((22,33),(44,55)); & -\begin{multilineoutput}{6cm} - [22 33] -d := [ ] - [44 55] -\end{multilineoutput} \\ - -block_matrix(2,3,\{B,C,D,D,C,B\}); & -\begin{multilineoutput}{6cm} -[1 0 5 22 33] -[ ] -[0 1 5 44 55] -[ ] -[22 33 5 1 0 ] -[ ] -[44 55 5 0 1 ] -\end{multilineoutput} \\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{char_matrix} - -\begin{Syntax} -\name{char\_matrix}(\meta{matrix},\meta{lambda}) -\end{Syntax} - -\meta{matrix} :- a square matrix. -\meta{lambda} :- a symbol or algebraic expression. - -\meta{char\_matrix} creates the characteristic matrix C of -\meta{matrix}. - -This is C = \meta{lambda} * Id - A. -Id is the identity matrix. - -\begin{Examples} - -char_matrix(A,x); & -\begin{multilineoutput}{6cm} -[x - 1 -2 -3 ] -[ ] -[ -4 x - 5 -6 ] -[ ] -[ -7 -8 x - 9] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: \nameref{char\_poly}. - -\end{Operator} - - -\begin{Operator}{char_poly} - -\begin{Syntax} -\name{char\_poly}(\meta{matrix},\meta{lambda}) -\end{Syntax} - -\meta{matrix} :- a square matrix. - -\meta{lambda} :- a symbol or algebraic expression. - -\name{char\_poly} finds the characteristic polynomial of \meta{matrix}. -This is the determinant of \meta{lambda} * Id - A. -Id is the identity matrix. - -\begin{Examples} -char_poly(A,x); & -x^3-15*x^2-18*x -\end{Examples} - -Related functions: \nameref{char\_matrix}. - -\end{Operator} - - -\begin{Operator}{cholesky} - -\begin{Syntax} -\name{cholesky}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a positive definite matrix containing numeric entries. - -\name{cholesky} computes the cholesky decomposition of \meta{matrix}. - -It returns \{L,U\} where L is a lower matrix, U is an upper matrix, -A = LU, and U = $L^T$. - -\begin{Examples} -F := mat((1,1,0),(1,3,1),(0,1,1)); & -\begin{multilineoutput}{6cm} - [1 1 0] - [ ] -f := [1 3 1] - [ ] - [0 1 1] -\end{multilineoutput} \\ - -on rounded; \\ -cholesky(F); & -\begin{multilineoutput}{6cm} -\{ - - [1 0 0 ] - [ ] - [1 1.41421356237 0 ] - [ ] - [0 0.707106781187 0.707106781187] - - , - - - [1 1 0 ] - [ ] - [0 1.41421356237 0.707106781187] - [ ] - [0 0 0.707106781187] - -\} -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: \nameref{lu\_decom}. - -\end{Operator} - - -\begin{Operator}{coeff_matrix} - -\begin{Syntax} -\name{coeff\_matrix}(\{\meta{lineq\_list}\}) -\end{Syntax} - -(If you are feeling lazy then the braces can be omitted.) - -\meta{lineq\_list} :- linear equations. Can be of the form equation = number -or just equation. - -\name{coeff\_matrix} creates the coefficient matrix C of the linear -equations. - -It returns \{C,X,B\} such that CX = B. - -\begin{Examples} - -coeff_matrix(\{x+y+4*z=10,y+x-z=20,x+y+4\}); & -\begin{multilineoutput}{6cm} -\{ - - [4 1 1] - [ ] - [-1 1 1] - [ ] - [0 1 1] - - , - - [z] - [ ] - [y] - [ ] - [x] - - , - - [10] - [ ] - [20] - [ ] - [-4] - -\} -\end{multilineoutput} \\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{column_dim} -Column dimension, row dimension: - -\begin{Syntax} -\name{column\_dim}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a matrix. - -\name{column\_dim} finds the column dimension of \meta{matrix}. - -\name{row\_dim} finds the row dimension of \meta{matrix}. - - -\begin{Examples} - -column_dim(A); & -3 \\ -row_dim(A); & -3 \\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{companion} - -\begin{Syntax} -\name{companion}(\meta{poly},\meta{x}) -\end{Syntax} - -\meta{poly} :- a monic univariate polynomial in \meta{x}. - -\meta{x} :- the variable. - - -\name{companion} creates the companion matrix C of \meta{poly}. - -This is the square matrix of dimension n, where n is the degree of -\meta{poly} w.r.t. \meta{x}. - -The entries of C are: - - C(i,n) = -coeffn(\meta{poly},\meta{x},i-1) for i = 1 - \ldots n, C(i,i-1) = 1 for i = 2 \ldots n and - the rest are 0. - -\begin{Examples} - -companion(x^4+17*x^3-9*x^2+11,x); & -\begin{multilineoutput}{6cm} -[0 0 0 -11] -[ ] -[1 0 0 0 ] -[ ] -[0 1 0 9 ] -[ ] -[0 0 1 -17] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{find\_companion}. - -\end{Operator} - - -\begin{Operator}{copy_into} - -\begin{Syntax} -\name{copy\_into}(\meta{A},\meta{B},\meta{r},\meta{c}) -\end{Syntax} - -\meta{A},\meta{B} :- matrices. - -\meta{r},\meta{c} :- positive integers. - - -\name{copy\_into} copies matrix \meta{matrix} into \meta{B} with -\meta{matrix}(1,1) at \meta{B}(\meta{r},\meta{c}). - -\begin{Examples} - -G := mat((0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0)); & -\begin{multilineoutput}{6cm} - [0 0 0 0 0] - [ ] - [0 0 0 0 0] - [ ] -g := [0 0 0 0 0] - [ ] - [0 0 0 0 0] - [ ] - [0 0 0 0 0] -\end{multilineoutput} \\ - -copy_into(A,G,1,2); & -\begin{multilineoutput}{6cm} -[0 1 2 3 0] -[ ] -[0 4 5 6 0] -[ ] -[0 7 8 9 0] -[ ] -[0 0 0 0 0] -[ ] -[0 0 0 0 0] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{augment\_columns}, \nameref{extend}, \nameref{matrix\_augment}, -\nameref{matrix\_stack}, \nameref{stack\_rows}, \nameref{sub\_matrix}. - -\end{Operator} - - -\begin{Operator}{diagonal} - -\begin{Syntax} -\name{diagonal}(\{\meta{mat\_list}\}) -\end{Syntax} -(If you are feeling lazy then the braces can be omitted.) - -\meta{mat\_list} :- each can be either a scalar expression or a -square \nameref{matrix}. - -\name{diagonal} creates a matrix that contains the input on the -diagonal. - -\begin{Examples} - -H := mat((66,77),(88,99)); & -\begin{multilineoutput}{6cm} - [66 77] -h := [ ] - [88 99] -\end{multilineoutput} \\ - -diagonal(\{A,x,H\}); & -\begin{multilineoutput}{6cm} -[1 2 3 0 0 0 ] -[ ] -[4 5 6 0 0 0 ] -[ ] -[7 8 9 0 0 0 ] -[ ] -[0 0 0 x 0 0 ] -[ ] -[0 0 0 0 66 77] -[ ] -[0 0 0 0 88 99] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{jordan\_block}. - -\end{Operator} - - -\begin{Operator}{extend} - -\begin{Syntax} -\name{extend}(\meta{matrix},\meta{r},\meta{c},\meta{expr}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{r},\meta{c} :- positive integers. - -\meta{expr} :- algebraic expression or symbol. - -\name{extend} returns a copy of \meta{matrix} that has been extended by -\meta{r} rows and \meta{c} columns. The new entries are made equal to -\meta{expr}. - -\begin{Examples} - -extend(A,1,2,x); & -\begin{multilineoutput}{6cm} -[1 2 3 x x] -[ ] -[4 5 6 x x] -[ ] -[7 8 9 x x] -[ ] -[x x x x x] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{copy\_into}, \nameref{matrix\_augment}, \nameref{matrix\_stack}, -\nameref{remove\_columns}, \nameref{remove\_rows}. - -\end{Operator} - - -\begin{Operator}{find_companion} - -\begin{Syntax} -\name{find\_companion}(\meta{matrix},\meta{x}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{x} :- the variable. - -Given a companion matrix, \name{find\_companion} finds the polynomial -from which it was made. - -\begin{Examples} - -C := companion(x^4+17*x^3-9*x^2+11,x); & -\begin{multilineoutput}{6cm} - [0 0 0 -11] - [ ] - [1 0 0 0 ] -c := [ ] - [0 1 0 9 ] - [ ] - [0 0 1 -17] -\end{multilineoutput}\\ - -find_companion(C,x); & -x^4+17*x^3-9*x^2+11 - -\end{Examples} - -Related functions: -\nameref{companion}. - -\end{Operator} - - -\begin{Operator}{get_columns} -Get columns, get rows: - -\begin{Syntax} -\name{get\_columns}(\meta{matrix},\meta{column\_list}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{c} :- either a positive integer or a list of positive - integers. - -\name{get\_columns} removes the columns of \meta{matrix} specified in -\meta{column\_list} and returns them as a list of column matrices. - -\name{get\_rows} performs the same task on the rows of \meta{matrix}. - -\begin{Examples} - -get_columns(A,\{1,3\}); & -\begin{multilineoutput}{6cm} -\{ - - [1] - [ ] - [4] - [ ] - [7] - - , - - [3] - [ ] - [6] - [ ] - [9] - -\} -\end{multilineoutput} \\ - -get_rows(A,2); & -\begin{multilineoutput}{6cm} -\{ - - [4 5 6] - -\} -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{augment\_columns}, \nameref{stack\_rows}, \nameref{sub\_matrix}. - -\end{Operator} - - -\begin{Operator}{get_rows} -see: \nameref{get\_columns}. -\end{Operator} - - -\begin{Operator}{gram_schmidt} - -\begin{Syntax} -\name{gram\_schmidt}(\{\meta{vec\_list}\}) -\end{Syntax} - -(If you are feeling lazy then the braces can be omitted.) - -\meta{vec\_list} :- linearly independent vectors. Each vector must be -written as a list, eg:\{1,0,0\}. - -\name{gram\_schmidt} performs the gram\_schmidt orthonormalization on -the input vectors. - -It returns a list of orthogonal normalized vectors. - -\begin{Examples} - -gram_schmidt(\{\{1,0,0\},\{1,1,0\},\{1,1,1\}\}); & -\{\{1,0,0\},\{0,1,0\},\{0,0,1\}\} \\ - -gram_schmidt(\{\{1,2\},\{3,4\}\}); & -\{\{ \rfrac{1}{{sqrt(5)}} , \rfrac{2}{sqrt(5)} \}, -\{ \rfrac{2*sqrt(5)}{5} , \rfrac{-sqrt(5)}{5} \}\} - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{hermitian_tp} - -\begin{Syntax} -\name{ hermitian\_tp}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\name{hermitian\_tp} computes the hermitian transpose of \meta{matrix}. - -This is a \nameref{matrix} in which the (i,j)'th entry is the conjugate -of the (j,i)'th entry of \meta{matrix}. - -\begin{Examples} - -J := mat((i+1,i+2,i+3),(4,5,2),(1,i,0)); & -\begin{multilineoutput}{6cm} - [i + 1 i + 2 i + 3] - [ ] -j := [ 4 5 2 ] - [ ] - [ 1 i 0 ] -\end{multilineoutput} \\ - -hermitian_tp(j); & -\begin{multilineoutput}{6cm} -[ - i + 1 4 1 ] -[ ] -[ - i + 2 5 - i] -[ ] -[ - i + 3 2 0 ] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{tp}. - -\end{Operator} - - -\begin{Operator}{hessian} - -\begin{Syntax} -\name{hessian}(\meta{expr},\meta{variable\_list}) -\end{Syntax} - -\meta{expr} :- a scalar expression. - -\meta{variable\_list} :- either a single variable or a list of - variables. - -\name{hessian} computes the hessian matrix of \meta{expr} w.r.t. the -variables in \meta{variable\_list}. - -% Does df exist in the help pages? -This is an n by n matrix where n is the number of variables and the -(i,j)'th entry is \nameref{df}(\meta{expr},\meta{variable\_list}(i), -\meta{variable\_list}(j)). - -\begin{Examples} - -hessian(x*y*z+x^2,\{w,x,y,z\}); & -\begin{multilineoutput}{6cm} -[0 0 0 0] -[ ] -[0 2 z y] -[ ] -[0 z 0 x] -[ ] -[0 y x 0] -\end{multilineoutput}{6cm} - -\end{Examples} - -Related functions: \nameref{df}. - -\end{Operator} - - -\begin{Operator}{hilbert} - -\begin{Syntax} -\name{hilbert}(\meta{square\_size},\meta{expr}) -\end{Syntax} - -\meta{square\_size} :- a positive integer. - -\meta{expr} :- an algebraic expression. - -\name{hilbert} computes the square hilbert matrix of dimension -\meta{square\_size}. - -This is the symmetric matrix in which the (i,j)'th entry is -1/(i+j-\meta{expr}). - -\begin{Examples} - -hilbert(3,y+x); & -\begin{multilineoutput}{6cm} -[ - 1 - 1 - 1 ] -[----------- ----------- -----------] -[ x + y - 2 x + y - 3 x + y - 4 ] -[ ] -[ - 1 - 1 - 1 ] -[----------- ----------- -----------] -[ x + y - 3 x + y - 4 x + y - 5 ] -[ ] -[ - 1 - 1 - 1 ] -[----------- ----------- -----------] -[ x + y - 4 x + y - 5 x + y - 6 ] -\end{multilineoutput} - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{jacobian} - -\begin{Syntax} -\name{jacobian}(\meta{expr\_list},\meta{variable\_list}) -\end{Syntax} - -\meta{expr\_list} :- either a single algebraic expression or a list - of algebraic expressions. - -\meta{variable\_list} :- either a single variable or a list of - variables. - -\name{jacobian} computes the jacobian matrix of \meta{expr\_list} -w.r.t. \meta{variable\_list}. - -This is a matrix whose (i,j)'th entry is \nameref{df}(\meta{expr\_list} -(i),\meta{variable\_list}(j)). - -The matrix is n by m where n is the number of variables and m the number -of expressions. - -\begin{Examples} - -jacobian(\{x^4,x*y^2,x*y*z^3\},\{w,x,y,z\}); & -\begin{multilineoutput}{6cm} -[ 3 ] -[0 4*x 0 0 ] -[ ] -[ 2 ] -[0 y 2*x*y 0 ] -[ ] -[ 3 3 2] -[0 y*z x*z 3*x*y*z ] -\end{multilineoutput} - -\end{Examples} - -Related functions: -\nameref{hessian}, \nameref{df}. - -\end{Operator} - - -\begin{Operator}{jordan_block} - -\begin{Syntax} -\name{jordan\_block}(\meta{expr},\meta{square\_size}) -\end{Syntax} - -\meta{expr} :- an algebraic expression or symbol. - -\meta{square\_size} :- a positive integer. - -\name{jordan\_block} computes the square jordan block matrix J of -dimension \meta{square\_size}. - -The entries of J are: - - J(i,i) = \meta{expr} for i=1 - \ldots n, J(i,i+1) = 1 for i=1 - \ldots n-1, and all other entries are 0. - -\begin{Examples} - -jordan\_block(x,5); & -\begin{multilineoutput}{6cm} -[x 1 0 0 0] -[ ] -[0 x 1 0 0] -[ ] -[0 0 x 1 0] -[ ] -[0 0 0 x 1] -[ ] -[0 0 0 0 x] -\end{multilineoutput} - -\end{Examples} - -Related functions: \nameref{diagonal}, \nameref{companion}. - -\end{Operator} - - -\begin{Operator}{lu_decom} - -\begin{Syntax} -\name{lu\_decom}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix} containing either numeric entries - or imaginary entries with numeric coefficients. - -\name{lu\_decom} performs LU decomposition on \meta{matrix}, ie: it -returns \{L,U\} where L is a lower diagonal \nameref{matrix}, U an -upper diagonal \nameref{matrix} and A = LU. - -Caution: - -The algorithm used can swap the rows of \meta{matrix} during the -calculation. This means that LU does not equal \meta{matrix} but a row -equivalent of it. Due to this, \name{lu\_decom} returns \{L,U,vec\}. -The call \name{convert(\meta{matrix},vec)} will return the matrix that has -been decomposed, i.e: LU = convert(\meta{matrix},vec). - - -\begin{Examples} - -K := mat((1,3,5),(-4,3,7),(8,6,4)); & -\begin{multilineoutput}{6cm} - [1 3 5] - [ ] -k := [-4 3 7] - [ ] - [8 6 4] -\end{multilineoutput}\\ - -on rounded;\\ -lu := lu_decom(K); & -\begin{multilineoutput}{6cm} -lu := \{ - - [8 0 0 ] - [ ] - [-4 6.0 0 ] - [ ] - [1 2.25 1.125] - - , - - - [1 0.75 0.5] - [ ] - [0 1 1.5] - [ ] - [0 0 1 ] - - , - - [3 2 3]\} -\end{multilineoutput} \\ - -first lu * second lu; & -\begin{multilineoutput}{6cm} -[8 6.0 4.0] -[ ] -[-4 3.0 7.0] -[ ] -[1 3.0 5.0] -\end{multilineoutput}\\ - -convert(K,third lu); & -\begin{multilineoutput} -[8 6 4] -[ ] -[-4 3 7] -[ ] -[1 3 5] -\end{multilineoutput}\\ - -P := mat((i+1,i+2,i+3),(4,5,2),(1,i,0)); & -\begin{multilineoutput}{6cm} - [i + 1 i + 2 i + 3] - [ ] -p := [ 4 5 2 ] - [ ] - [ 1 i 0 ] -\end{multilineoutput}\\ - -lu := lu_decom(P); & -\begin{multilineoutput}{6cm} -lu := \{ - - [ 1 0 0 ] - [ ] - [ 4 - 4*i + 5 0 ] - [ ] - [i + 1 3 0.414634146341*i + 2.26829268293] - - , - - - [1 i 0 ] - [ ] - [0 1 0.19512195122*i + 0.243902439024] - [ ] - [0 0 1 ] - - , - - [3 2 3]\} -\end{multilineoutput}\\ - -first lu * second lu; & -\begin{multilineoutput}{6cm} -[ 1 i 0 ] -[ ] -[ 4 5 2.0 ] -[ ] -[i + 1 i + 2 i + 3.0] -\end{multilineoutput}\\ - -convert(P,third lu); & -\begin{multilineoutput}{6cm} -[ 1 i 0 ] -[ ] -[ 4 5 2 ] -[ ] -[i + 1 i + 2 i + 3] -\end{multilineoutput}\\ - -\end{Examples} - -Related functions: \nameref{cholesky}. - -\end{Operator} - - -\begin{Operator}{make_identity} - -\begin{Syntax} -\name{make\_identity}(\meta{square\_size}) -\end{Syntax} - -\meta{square\_size} :- a positive integer. - -\name{make\_identity} creates the identity matrix of dimension -\meta{square\_size}. - -\begin{Examples} - -make_identity(4); & -\begin{multilineoutput}{6cm} -[1 0 0 0] -[ ] -[0 1 0 0] -[ ] -[0 0 1 0] -[ ] -[0 0 0 1] -\end{multilineoutput} - -\end{Examples} - -Related functions: \nameref{diagonal}. - -\end{Operator} - - -\begin{Operator}{matrix_augment} -Matrix augment, matrix stack: - -\begin{Syntax} -\name{matrix\_augment} \{\meta{matrix\_list}\} -\end{Syntax} - -(If you are feeling lazy then the braces can be omitted.) - -\meta{matrix\_list} :- matrices. - -\name{matrix\_augment} sticks the matrices in \meta{matrix\_list} -together horizontally. - -\name{matrix\_stack} sticks the matrices in \meta{matrix\_list} -together vertically. - - -\begin{Examples} - -matrix_augment(\{A,A\}); & -\begin{multilineoutput}{6cm} -[1 2 3 1 2 3] -[ ] -[4 5 6 4 5 6] -[ ] -[7 8 9 7 8 9] -\end{multilineoutput}\\ - -matrix_stack(A,A); & -\begin{multilineoutput}{6cm} -[1 2 3] -[ ] -[4 5 6] -[ ] -[7 8 9] -[ ] -[1 2 3] -[ ] -[4 5 6] -[ ] -[7 8 9] -\end{multilineoutput} \\ - -\end{Examples} - -Related functions: -\nameref{augment\_columns}, \nameref{stack\_rows}, \nameref{sub\_matrix}. - -\end{Operator} - - -\begin{Operator}{matrixp} - -\begin{Syntax} -\name{matrixp}(\meta{test\_input}) -\end{Syntax} - -\meta{test\_input} :- anything you like. - -\name{matrixp} is a boolean function that returns t if the input is a -matrix and nil otherwise. - - -\begin{Examples} - -matrixp A; & -t \\ -matrixp(doodlesackbanana);& -nil - -\end{Examples} - -Related functions: \nameref{squarep}, \nameref{symmetricp}. - -\end{Operator} - - -\begin{Operator}{matrix_stack} -see: \nameref{matrix\_augment}. -\end{Operator} - - -\begin{Operator}{minor} - -\begin{Syntax} -\name{minor}(\meta{matrix},\meta{r},\meta{c}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. -\meta{r},\meta{c} :- positive integers. - -\name{minor} computes the (\meta{r},\meta{c})'th minor of \meta{matrix}. -This is created by removing the \meta{r}'th row and the \meta{c}'th -column from \meta{matrix}. - - -\begin{Examples} - -minor(A,1,3); & -\begin{multilineoutput}{6cm} -[4 5] -[ ] -[7 8] -\end{multilineoutput} - -\end{Examples} - -Related functions: -\nameref{remove\_columns}, \nameref{remove\_rows}. - -\end{Operator} - - -\begin{Operator}{mult_columns} -Mult columns, mult rows: - -\begin{Syntax} -\name{mult\_columns}(\meta{matrix},\meta{column\_list},\meta{expr}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{column\_list} :- a positive integer or a list of positive - integers. - -\meta{expr} :- an algebraic expression. - -\name{mult\_columns} returns a copy of \meta{matrix} in which the -columns specified in \meta{column\_list} have been multiplied by -\meta{expr}. - -\name{mult\_rows} performs the same task on the rows of \meta{matrix}. - -\begin{Examples} - -mult_columns(A,\{1,3\},x); & -\begin{multilineoutput}{6cm} -[ x 2 3*x] -[ ] -[4*x 5 6*x] -[ ] -[7*x 8 9*x] -\end{multilineoutput}\\ - -mult_rows(A,2,10); & -\begin{multilineoutput}{6cm} -[1 2 3 ] -[ ] -[40 50 60] -[ ] -[7 8 9 ] -\end{multilineoutput} - -\end{Examples} - -Related functions: \nameref{add\_to\_columns}, \nameref{add\_to\_rows}. - -\end{Operator} - - -\begin{Operator}{mult_rows} -see: \nameref{mult\_columns}. -\end{Operator} - - -\begin{Operator}{pivot} - -\begin{Syntax} -\name{pivot}(\meta{matrix},\meta{r},\meta{c}) -\end{Syntax} - -\meta{matrix} :- a matrix. - -\meta{r},\meta{c} :- positive integers such that \meta{matrix}(\meta{r}, - \meta{c}) neq 0. - -\name{pivot} pivots \meta{matrix} about it's (\meta{r},\meta{c})'th -entry. - -To do this, multiples of the \meta{r}'th row are added to every other -row in the matrix. - -This means that the \meta{c}'th column will be 0 except for the -(\meta{r},\meta{c})'th entry. - - -\begin{Examples} - -pivot(A,2,3); & -\begin{multilineoutput}{6cm} -[ - 1 ] -[-1 ------ 0] -[ 2 ] -[ ] -[4 5 6] -[ ] -[ 1 ] -[1 --- 0] -[ 2 ] -\end{multilineoutput} - -\end{Examples} - -Related functions: -\nameref{rows\_pivot}. - -\end{Operator} - -\begin{Operator}{pseudo_inverse} - -\begin{Syntax} -\name{pseudo\_inverse}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\name{pseudo\_inverse}, also known as the Moore-Penrose inverse, -computes the pseudo inverse of \meta{matrix}. - -Given the singular value decomposition of \meta{matrix}, i.e: -A = $U*P*V^T$, then the pseudo inverse $A^{-1}$ is defined by -$A^{-1} = V^T*P^{-1}*U$. - -Thus \meta{matrix} * pseudo\_inverse(A) = Id. -(Id is the identity matrix). - - -\begin{Examples} - -R := mat((1,2,3,4),(9,8,7,6)); & -\begin{multilineoutput}{6cm} - [1 2 3 4] -r := [ ] - [9 8 7 6] -\end{multilineoutput}\\ - -on rounded; \\ -pseudo_inverse(R); & -\begin{multilineoutput}{6cm} -[ - 0.199999999996 0.100000000013 ] -[ ] -[ - 0.0499999999988 0.0500000000037 ] -[ ] -[ 0.0999999999982 - 5.57825497203e-12] -[ ] -[ 0.249999999995 - 0.0500000000148 ] -\end{multilineoutput} - -\end{Examples} - - -Related functions: \nameref{svd}. - -\end{Operator} - - -\begin{Operator}{random_matrix} - -\begin{Syntax} -\name{random\_matrix}(\meta{r},\meta{c},\meta{limit}) -\end{Syntax} - -\meta{r},\meta{c},\meta{limit} :- positive integers. - -\name{random\_matrix} creates an \meta{r} by \meta{c} matrix with random -entries in the range -limit < entry < limit. - - -Switches: - -\name{imaginary} :- if on then matrix entries are x+i*y where -limit < x,y - < \meta{limit}. - -\name{not\_negative} :- if on then 0 < entry < \meta{limit}. In the imaginary - case we have 0 < x,y < \meta{limit}. - -\name{only\_integer} :- if on then each entry is an integer. In the imaginary - case x and y are integers. - -\name{symmetric} :- if on then the matrix is symmetric. - -\name{upper\_matrix} :- if on then the matrix is upper triangular. - -\name{lower\_matrix} :- if on then the matrix is lower triangular. - - - -\begin{Examples} - -on rounded; \\ -random_matrix(3,3,10); & -\begin{multilineoutput}{6cm} -[ - 8.11911717343 - 5.71677292768 0.620580830035 ] -[ ] -[ - 0.032596262422 7.1655452861 5.86742633837 ] -[ ] -[ - 9.37155438255 - 7.55636708637 - 8.88618627557] -\end{multilineoutput}\\ - -on only_integer, not_negative, upper_matrix, imaginary; \\ -random_matrix(4,4,10); & -\begin{multilineoutput}{6cm} -[70*i + 15 28*i + 8 2*i + 79 27*i + 44] -[ ] -[ 0 46*i + 95 9*i + 63 95*i + 50] -[ ] -[ 0 0 31*i + 75 14*i + 65] -[ ] -[ 0 0 0 5*i + 52 ] -\end{multilineoutput}\\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{remove_columns} -Remove columns, remove rows: - -\begin{Syntax} -\name{remove\_columns}(\meta{matrix},\meta{column\_list}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. -\meta{column\_list} :- either a positive integer or a list of positive - integers. - -\name{remove\_columns} removes the columns specified in -\meta{column\_list} from \meta{matrix}. - -\name{remove\_rows} performs the same task on the rows of \meta{matrix}. - -\begin{Examples} - -remove_columns(A,2); & -\begin{multilineoutput}{6cm} -[1 3] -[ ] -[4 6] -[ ] -[7 9] -\end{multilineoutput}\\ - -remove_rows(A,\{1,3\}); & -\begin{multilineoutput}{6cm} -[4 5 6] -\end{multilineoutput}\\ - - -\end{Examples} - -Related functions: \nameref{minor}. - -\end{Operator} - - -\begin{Operator}{remove_rows} -see: \nameref{remove\_columns}. -\end{Operator} - - -\begin{Operator}{row_dim} -see: \nameref{column\_dim}. -\end{Operator} - - -\begin{Operator}{rows_pivot} - -\begin{Syntax} -\name{rows\_pivot}(\meta{matrix},\meta{r},\meta{c},\{\meta{row\_list}\}) -\end{Syntax} - -\meta{matrix} :- a nameref{matrix}. - -\meta{r},\meta{c} :- positive integers such that \meta{matrix}(\meta{r}, - \meta{c}) neq 0. - -\meta{row\_list} :- positive integer or a list of positive integers. - -\name{rows\_pivot} performs the same task as \name{pivot} but applies -the pivot only to the rows specified in \meta{row\_list}. - - -\begin{Examples} - -N := mat((1,2,3),(4,5,6),(7,8,9),(1,2,3),(4,5,6)); & -\begin{multilineoutput}{6cm} - [1 2 3] - [ ] - [4 5 6] - [ ] -n := [7 8 9] - [ ] - [1 2 3] - [ ] - [4 5 6] -\end{multilineoutput}\\ - -rows_pivot(N,2,3,{4,5}); & -\begin{multilineoutput}{6cm} -[1 2 3] -[ ] -[4 5 6] -[ ] -[7 8 9] -[ ] -[ - 1 ] -[-1 ------ 0] -[ 2 ] -[ ] -[0 0 0] -\end{multilineoutput}\\ - -\end{Examples} - -Related functions: \nameref{pivot}. - -\end{Operator} - - -\begin{Operator}{simplex} - -\begin{Syntax} -\name{simplex}(\meta{max/min},\meta{objective function}, -\{\meta{linear inequalities}\}) -\end{Syntax} - -\meta{max/min} :- either max or min (signifying maximize and - minimize). - -\meta{objective function} :- the function you are maximizing or - minimizing. - -\meta{linear inequalities} :- the constraint inequalities. Each one must - be of the form {\it sum of variables ( - <=,=,>=) number}. - -\name{simplex} applies the revised simplex algorithm to find the -optimal(either maximum or minimum) value of the -\meta{objective function} under the linear inequality constraints. - -It returns \{optimal value,\{ values of variables at this optimal\}\}. - -The algorithm implies that all the variables are non-negative. - -\begin{Examples} - - simplex(max,x+y,\{x>=10,y>=20,x+y<=25\}); & - - ***** Error in simplex: Problem has no feasible solution\\ - -simplex(max,10x+5y+5.5z,\{5x+3z<=200,x+0.1y+0.5z<=12, -0.1x+0.2y+0.3z<=9, 30x+10y+50z<=1500\}); & - -\{525.0,\{x=40.0,y=25.0,z=0\}\}\\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{squarep} - -\begin{Syntax} -\name{squarep}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\name{squarep} is a predicate that returns t if the \meta{matrix} is -square and nil otherwise. - -\begin{Examples} - -squarep(mat((1,3,5))); & -nil \\ -squarep(A); -t\\ - -\end{Examples} - -Related functions: \nameref{matrixp}, \nameref{symmetricp}. - -\end{Operator} - - -\begin{Operator}{stack_rows} -see: \nameref{augment\_columns}. -\end{Operator} - - -\begin{Operator}{sub_matrix} - -\begin{Syntax} -\name{sub\_matrix}(\meta{matrix},\meta{row\_list},\meta{column\_list}) -\end{Syntax} - -\meta{matrix} :- a matrix. -\meta{row\_list}, \meta{column\_list} :- either a positive integer or a - list of positive integers. - -name{sub\_matrix} produces the matrix consisting of the intersection of -the rows specified in \meta{row\_list} and the columns specified in -\meta{column\_list}. - - -\begin{Examples} - -sub_matrix(A,\{1,3\},\{2,3\}); & -\begin{multilineoutput}{6cm} -[2 3] -[ ] -[8 9] -\end{multilineoutput} - -\end{Examples} - -Related functions: -\nameref{augment\_columns}, \nameref{stack\_rows}. - -\end{Operator} - - -\begin{Operator}{svd} -\index{singular value decomposition} -Singular value decomposition: - -\begin{Syntax} -\name{svd}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix} containing only numeric entries. - - -\name{svd} computes the singular value decomposition of \meta{matrix}. - -It returns - -\{U,P,V\} - -where A = $U*P*V^T$ - -and P = diag(sigma(1) ... sigma(n)). - -sigma(i) for i= 1 ... n are the singular values of -\meta{matrix}. - -n is the column dimension of \meta{matrix}. - -The singular values of \meta{matrix} are the non-negative square roots -of the eigenvalues of $A^T*A$. - -U and V are such that $U*U^T = V*V^T = V^T*V$ = Id. -Id is the identity matrix. - - -\begin{Examples} - -Q := mat((1,3),(-4,3)); & -\begin{multilineoutput}{6cm} - [1 3] -q := [ ] - [-4 3] -\end{multilineoutput}\\ - -on rounded; \\ -svd(Q); & -\begin{multilineoutput}{6cm} -\{ - - [ 0.289784137735 0.957092029805] - [ ] - [ - 0.957092029805 0.289784137735] - - , - - - [5.1491628629 0 ] - [ ] - [ 0 2.9130948854] - - , - - - [ - 0.687215403194 0.726453707825 ] - [ ] - [ - 0.726453707825 - 0.687215403194] - -\} -\end{multilineoutput}\\ - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{swap_columns} -Swap columns, swap rows: - -\begin{Syntax} -\name{swap\_columns} (\meta{matrix},\meta{c1},\meta{c2}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{c1},\meta{c1} :- positive integers. - -\name{swap\_columns} swaps column \meta{c1} of \meta{matrix} with -column \meta{c2}. - -\name{swap\_rows} performs the same task on two rows of \meta{matrix}. - -\begin{Examples} - -swap_columns(A,2,3); & -\begin{multilineoutput}{6cm} -[1 3 2] -[ ] -[4 6 5] -[ ] -[7 9 8] -\end{multilineoutput}\\ - -swap_rows(A,1,3); & -\begin{multilineoutput}{6cm} -[7 8 9] -[ ] -[4 5 6] -[ ] -[1 2 3] -\end{multilineoutput} - -\end{Examples} - -Related functions: \nameref{swap\_entries}. - -\end{Operator} - - -\begin{Operator}{swap_entries} - -\begin{Syntax} -\name{swap\_entries}(\meta{matrix},\{\meta{r1},\meta{c1}\},\{\meta{r2}, -\meta{c2}\}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\meta{r1},\meta{c1},\meta{r2},\meta{c2} :- positive integers. - -\name{swap\_entries} swaps \meta{matrix}(\meta{r1},\meta{c1}) with -\meta{matrix}(\meta{r2},\meta{c2}). - -\begin{Examples} - -swap_entries(A,\{1,1\},\{3,3\}); & -\begin{multilineoutput}{6cm} -[9 2 3] -[ ] -[4 5 6] -[ ] -[7 8 1] -\end{multilineoutput} - -\end{Examples} - -Related functions: \nameref{swap\_columns}, \nameref{swap\_rows}. - -\end{Operator} - - -\begin{Operator}{swap_rows} -see: \nameref{swap\_columns}. -\end{Operator} - - -\begin{Operator}{symmetricp} - -\begin{Syntax} -\name{symmetricp}(\meta{matrix}) -\end{Syntax} - -\meta{matrix} :- a \nameref{matrix}. - -\name{symmetricp} is a predicate that returns t if the matrix is symmetric -and nil otherwise. - - -\begin{Examples} - -symmetricp(make_identity(11)); & -t \\ -symmetricp(A); & -nil\\ - -\end{Examples} - -Related functions: \nameref{matrixp}, \nameref{squarep}. - -\end{Operator} - - -\begin{Operator}{toeplitz} - -\begin{Syntax} -\name{toeplitz}(\meta{expr\_list}) -\end{Syntax} -(If you are feeling lazy then the braces can be omitted.) - -\meta{expr\_list} :- list of algebraic expressions. - -\name{toeplitz} creates the toeplitz matrix from the \meta{expr\_list}. - -This is a square symmetric matrix in which the first expression is -placed on the diagonal and the i'th expression is placed on the (i-1)'th -sub and super diagonals. - -It has dimension n where n is the number of expressions. - - -\begin{Examples} - -toeplitz({w,x,y,z}); & -\begin{multilineoutput}{6cm} -[w x y z] -[ ] -[x w x y] -[ ] -[y x w x] -[ ] -[z y x w] -\end{multilineoutput} - -\end{Examples} - -\end{Operator} - - -\begin{Operator}{vandermonde} - -\begin{Syntax} -\name{vandermonde}(\{\meta{expr\_list}\}) -\end{Syntax} -(If you are feeling lazy then the braces can be omitted.) - -\meta{expr\_list} :- list of algebraic expressions. - -\name{vandermonde} creates the vandermonde matrix from the -\meta{expr\_list}. - -This is the square matrix in which the (i,j)'th entry is -\meta{expr\_list}$(i)^(j-1)$. - -It has dimension n where n is the number of expressions. - - -\begin{Examples} -vandermonde({x,2*y,3*z}); & -\begin{multilineoutput}{6cm} -[ 2 ] -[1 x x ] -[ ] -[ 2] -[1 2*y 4*y ] -[ ] -[ 2] -[1 3*z 9*z ] -\end{multilineoutput} - -\end{Examples} - -\end{Operator} - +\section{Linear Algebra package} + +\begin{Introduction}{Linear Algebra package} + +This section briefly describes what's available in the Linear Algebra +package. + +Note on examples: In the examples throughout this +document, the matrix A will be +\begin{verbatim} + [1 2 3] + [4 5 6] + [7 8 9]. +\end{verbatim} + +The functions can be divided into four categories: + +{\bf Basic matrix handling} + +\nameref{add\_columns}, + +\nameref{add\_rows}, + +\nameref{add\_to\_columns}, + +\nameref{add\_to\_rows}, + +\nameref{augment\_columns}, + +\nameref{char\_poly}, + +\nameref{column\_dim}, + +\nameref{copy\_into}, + +\nameref{diagonal}, + +\nameref{extend}, + +\nameref{find\_companion}, + +\nameref{get\_columns}, + +\nameref{get\_rows}, + +\nameref{hermitian\_tp}, + +\nameref{matrix\_augment}, + +\nameref{matrix\_stack} , + +\nameref{minor}, + +\nameref{mult\_columns}, + +\nameref{mult\_rows}, + +\nameref{pivot}, + +\nameref{remove\_columns}, + +\nameref{remove\_rows}, + +\nameref{row\_dim}, + +\nameref{rows\_pivot}, + +\nameref{stack\_rows}, + +\nameref{sub\_matrix}, + +\nameref{swap\_columns}, + +\nameref{swap\_entries}, + +\nameref{swap\_rows}. + +{\bf Constructors -- functions that create matrices} + +\nameref{band\_matrix}, + +\nameref{block\_matrix}, + +\nameref{char\_matrix}, + +\nameref{coeff\_matrix}, + +\nameref{companion}, + +\nameref{hessian}, + +\nameref{hilbert}, + +\nameref{jacobian}, + +\nameref{jordan\_block}, + +\nameref{make\_identity}, + +\nameref{random\_matrix}, + +\nameref{toeplitz}, + +\nameref{vandermonde}. + +{\bf High level algorithms} + +\nameref{char\_poly}, + +\nameref{cholesky}, + +\nameref{gram\_schmidt}, + +\nameref{lu\_decom}, + +\nameref{pseudo\_inverse}, + +\nameref{simplex}, + +\nameref{svd}. + +{\bf Normal Forms} + +There is a separate package, NORMFORM, for computing +the following matrix normal forms in \REDUCE: + +\nameref{smithex}, + +\nameref{smithex\_int}, + +\nameref{frobenius}, + +\nameref{ratjordan}, + +\nameref{jordansymbolic}, + +\nameref{jordan}. + + +{\bf Predicates} + +\nameref{matrixp}, + +\nameref{squarep}, + +\nameref{symmetricp}. + +\end{Introduction} + + +\begin{Switch}{fast_la} + +By turning the \name{fast\_la} switch on, the speed of the following +functions will be increased: + + +\nameref{add\_columns}, + +\nameref{add\_rows}, + +\nameref{augment\_columns}, + +\nameref{column\_dim}, + +\nameref{copy\_into}, + +\nameref{make\_identity}, + +\nameref{matrix\_augment}, + +\nameref{matrix\_stack}, + +\nameref{minor}, + +\nameref{mult\_columns}, + +\nameref{mult\_rows}, + +\nameref{pivot}, + +\nameref{remove\_columns}, + +\nameref{remove\_rows}, + +\nameref{rows\_pivot}, + +\nameref{squarep}, + +\nameref{stack\_rows}, + +\nameref{sub\_matrix}, + +\nameref{swap\_columns}, + +\nameref{swap\_entries}, + +\nameref{swap\_rows}, + +\nameref{symmetricp}. + + +The increase in speed will be negligible unless you are making a +significant number (i.e. thousands) of calls. When using this switch, +error checking is minimized. This means that illegal input may give +strange error messages. Beware. +\end{Switch} + +\begin{Operator}{add_columns} +Add columns, add rows: +\begin{Syntax} +\name{add\_columns}\(\meta{matrix},\meta{c1},\meta{c2},\meta{expr}\) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{c1},\meta{c2} :- positive integers. + +\meta{expr} :- a scalar expression. + +The Operator \name{add\_columns} replaces column \meta{\meta{c2}} of +\meta{matrix} by \meta{expr} * column(\meta{matrix},\meta{c1}) + +column(\meta{matrix},\meta{c2}). + +\name{add\_rows} performs the equivalent task on the rows of +\meta{matrix}. + +\begin{Examples} + +add_columns(A,1,2,x); & +\begin{multilineoutput}{6cm} +[1 x + 2 3] +[ ] +[4 4*x + 5 6] +[ ] +[7 7*x + 8 9] +\end{multilineoutput} \\ + +add_rows(A,2,3,5); & +\begin{multilineoutput}{6cm} +[1 2 3 ] +[ ] +[4 5 6 ] +[ ] +[27 33 39] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: \nameref{add\_to\_columns}, +\nameref{add\_to\_rows}, \nameref{mult\_columns}, +\nameref{mult\_rows}. + +\end{Operator} + + +\begin{Operator}{add_rows} + see: \nameref{add\_columns}. +\end{Operator} + + +\begin{Operator}{add_to_columns} +Add to columns, add to rows: + +\begin{Syntax} +\name{add\_to\_columns}\(\meta{matrix},\meta{column\_list},\meta{expr}\) +\end{Syntax} + +\meta{matrix} :- a matrix. + +\meta{column\_list} :- a positive integer or a list of positive + integers. + +\meta{expr} :- a scalar expression. + +\name{add\_to\_columns} adds \meta{expr} to each column specified in +\meta{column\_list} of \meta{matrix}. + +\name{add\_to\_rows} performs the equivalent task on the rows of +\meta{matrix}. + +\begin{Examples} + +add_to_columns(A,\{1,2\},10); & +\begin{multilineoutput}{6cm} +[11 12 3] +[ ] +[14 15 6] +[ ] +[17 18 9] +\end{multilineoutput}\\ + +add_to_rows(A,2,-x) & +\begin{multilineoutput}{6cm} +[ 1 2 3 ] +[ ] +[ - x + 4 - x + 5 - x + 6] +[ ] +[ 7 8 9 ] +\end{multilineoutput} \\ +\end{Examples} + +Related functions: +\nameref{add\_columns}, \nameref{add\_rows}, \nameref{mult\_rows}, +\nameref{mult\_columns}. + +\end{Operator} + + +\begin{Operator}{add_to_rows} + see: \nameref{add\_to\_columns}. +\end{Operator} + + +\begin{Operator}{augment_columns} +Augment columns, stack rows: + +\begin{Syntax} +\name{augment\_columns}(\meta{matrix},\meta{column\_list}) +\end{Syntax} + +\meta{matrix} :- a matrix. + +\meta{column\_list} :- either a positive integer or a list of positive + integers. + +\name{augment\_columns} gets hold of the columns of \meta{matrix} +specified in \name{column\_list} and sticks them together. + +\name{stack\_rows} performs the same task on rows of \meta{matrix}. + +\begin{Examples} + +augment_columns(A,\{1,2\}) & +\begin{multilineoutput}{6cm} +[1 2] +[ ] +[4 5] +[ ] +[7 8] +\end{multilineoutput} \\ + +stack_rows(A,\{1,3\}) & +\begin{multilineoutput}{6cm} +[1 2 3] +[ ] +[7 8 9] +\end{multilineoutput} \\ +\end{Examples} + +Related functions: +\nameref{get\_columns}, \nameref{get\_rows}, \nameref{sub\_matrix}. + +\end{Operator} + + +\begin{Operator}{band_matrix} + +\begin{Syntax} +\name{band\_matrix}(\meta{expr\_list},\meta{square\_size}) +\end{Syntax} + +\meta{expr\_list} :- either a single scalar expression or a list of + an odd number of scalar expressions. + +\meta{square\_size} :- a positive integer. + +\name{band\_matrix} creates a square matrix of dimension +\meta{square\_size}. The diagonal consists of the middle expression +of the \meta{expr\_list}. The expressions to the left of this fill +the required number of sub\_diagonals and the expressions to the right +the super\_diagonals. + +\begin{Examples} + +band_matrix(\{x,y,z\},6) & +\begin{multilineoutput}{6cm} +[y z 0 0 0 0] +[ ] +[x y z 0 0 0] +[ ] +[0 x y z 0 0] +[ ] +[0 0 x y z 0] +[ ] +[0 0 0 x y z] +[ ] +[0 0 0 0 x y] +\end{multilineoutput} \\ +\end{Examples} + +Related functions: \nameref{diagonal}. + +\end{Operator} + + +\begin{Operator}{block_matrix} + +\begin{Syntax} +\name{block\_matrix}(\meta{r},\meta{c},\meta{matrix\_list}) +\end{Syntax} + +\meta{r},\meta{c} :- positive integers. + +\meta{matrix\_list} :- a list of matrices. + +\name{block\_matrix} creates a matrix that consists of \meta{r} by +\meta{c} matrices filled from the \meta{matrix\_list} row wise. + +\begin{Examples} +B := make_identity(2); & +\begin{multilineoutput}{6cm} + [1 0] +b := [ ] + [0 1] +\end{multilineoutput} \\ + +C := mat((5),(5)); & +\begin{multilineoutput}{6cm} + [5] +c := [ ] + [5] +\end{multilineoutput} \\ + +D := mat((22,33),(44,55)); & +\begin{multilineoutput}{6cm} + [22 33] +d := [ ] + [44 55] +\end{multilineoutput} \\ + +block_matrix(2,3,\{B,C,D,D,C,B\}); & +\begin{multilineoutput}{6cm} +[1 0 5 22 33] +[ ] +[0 1 5 44 55] +[ ] +[22 33 5 1 0 ] +[ ] +[44 55 5 0 1 ] +\end{multilineoutput} \\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{char_matrix} + +\begin{Syntax} +\name{char\_matrix}(\meta{matrix},\meta{lambda}) +\end{Syntax} + +\meta{matrix} :- a square matrix. +\meta{lambda} :- a symbol or algebraic expression. + +\meta{char\_matrix} creates the characteristic matrix C of +\meta{matrix}. + +This is C = \meta{lambda} * Id - A. +Id is the identity matrix. + +\begin{Examples} + +char_matrix(A,x); & +\begin{multilineoutput}{6cm} +[x - 1 -2 -3 ] +[ ] +[ -4 x - 5 -6 ] +[ ] +[ -7 -8 x - 9] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: \nameref{char\_poly}. + +\end{Operator} + + +\begin{Operator}{char_poly} + +\begin{Syntax} +\name{char\_poly}(\meta{matrix},\meta{lambda}) +\end{Syntax} + +\meta{matrix} :- a square matrix. + +\meta{lambda} :- a symbol or algebraic expression. + +\name{char\_poly} finds the characteristic polynomial of \meta{matrix}. +This is the determinant of \meta{lambda} * Id - A. +Id is the identity matrix. + +\begin{Examples} +char_poly(A,x); & +x^3-15*x^2-18*x +\end{Examples} + +Related functions: \nameref{char\_matrix}. + +\end{Operator} + + +\begin{Operator}{cholesky} + +\begin{Syntax} +\name{cholesky}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a positive definite matrix containing numeric entries. + +\name{cholesky} computes the cholesky decomposition of \meta{matrix}. + +It returns \{L,U\} where L is a lower matrix, U is an upper matrix, +A = LU, and U = $L^T$. + +\begin{Examples} +F := mat((1,1,0),(1,3,1),(0,1,1)); & +\begin{multilineoutput}{6cm} + [1 1 0] + [ ] +f := [1 3 1] + [ ] + [0 1 1] +\end{multilineoutput} \\ + +on rounded; \\ +cholesky(F); & +\begin{multilineoutput}{6cm} +\{ + + [1 0 0 ] + [ ] + [1 1.41421356237 0 ] + [ ] + [0 0.707106781187 0.707106781187] + + , + + + [1 1 0 ] + [ ] + [0 1.41421356237 0.707106781187] + [ ] + [0 0 0.707106781187] + +\} +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: \nameref{lu\_decom}. + +\end{Operator} + + +\begin{Operator}{coeff_matrix} + +\begin{Syntax} +\name{coeff\_matrix}(\{\meta{lineq\_list}\}) +\end{Syntax} + +(If you are feeling lazy then the braces can be omitted.) + +\meta{lineq\_list} :- linear equations. Can be of the form equation = number +or just equation. + +\name{coeff\_matrix} creates the coefficient matrix C of the linear +equations. + +It returns \{C,X,B\} such that CX = B. + +\begin{Examples} + +coeff_matrix(\{x+y+4*z=10,y+x-z=20,x+y+4\}); & +\begin{multilineoutput}{6cm} +\{ + + [4 1 1] + [ ] + [-1 1 1] + [ ] + [0 1 1] + + , + + [z] + [ ] + [y] + [ ] + [x] + + , + + [10] + [ ] + [20] + [ ] + [-4] + +\} +\end{multilineoutput} \\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{column_dim} +Column dimension, row dimension: + +\begin{Syntax} +\name{column\_dim}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a matrix. + +\name{column\_dim} finds the column dimension of \meta{matrix}. + +\name{row\_dim} finds the row dimension of \meta{matrix}. + + +\begin{Examples} + +column_dim(A); & +3 \\ +row_dim(A); & +3 \\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{companion} + +\begin{Syntax} +\name{companion}(\meta{poly},\meta{x}) +\end{Syntax} + +\meta{poly} :- a monic univariate polynomial in \meta{x}. + +\meta{x} :- the variable. + + +\name{companion} creates the companion matrix C of \meta{poly}. + +This is the square matrix of dimension n, where n is the degree of +\meta{poly} w.r.t. \meta{x}. + +The entries of C are: + + C(i,n) = -coeffn(\meta{poly},\meta{x},i-1) for i = 1 + \ldots n, C(i,i-1) = 1 for i = 2 \ldots n and + the rest are 0. + +\begin{Examples} + +companion(x^4+17*x^3-9*x^2+11,x); & +\begin{multilineoutput}{6cm} +[0 0 0 -11] +[ ] +[1 0 0 0 ] +[ ] +[0 1 0 9 ] +[ ] +[0 0 1 -17] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{find\_companion}. + +\end{Operator} + + +\begin{Operator}{copy_into} + +\begin{Syntax} +\name{copy\_into}(\meta{A},\meta{B},\meta{r},\meta{c}) +\end{Syntax} + +\meta{A},\meta{B} :- matrices. + +\meta{r},\meta{c} :- positive integers. + + +\name{copy\_into} copies matrix \meta{matrix} into \meta{B} with +\meta{matrix}(1,1) at \meta{B}(\meta{r},\meta{c}). + +\begin{Examples} + +G := mat((0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0),(0,0,0,0,0)); & +\begin{multilineoutput}{6cm} + [0 0 0 0 0] + [ ] + [0 0 0 0 0] + [ ] +g := [0 0 0 0 0] + [ ] + [0 0 0 0 0] + [ ] + [0 0 0 0 0] +\end{multilineoutput} \\ + +copy_into(A,G,1,2); & +\begin{multilineoutput}{6cm} +[0 1 2 3 0] +[ ] +[0 4 5 6 0] +[ ] +[0 7 8 9 0] +[ ] +[0 0 0 0 0] +[ ] +[0 0 0 0 0] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{augment\_columns}, \nameref{extend}, \nameref{matrix\_augment}, +\nameref{matrix\_stack}, \nameref{stack\_rows}, \nameref{sub\_matrix}. + +\end{Operator} + + +\begin{Operator}{diagonal} + +\begin{Syntax} +\name{diagonal}(\{\meta{mat\_list}\}) +\end{Syntax} +(If you are feeling lazy then the braces can be omitted.) + +\meta{mat\_list} :- each can be either a scalar expression or a +square \nameref{matrix}. + +\name{diagonal} creates a matrix that contains the input on the +diagonal. + +\begin{Examples} + +H := mat((66,77),(88,99)); & +\begin{multilineoutput}{6cm} + [66 77] +h := [ ] + [88 99] +\end{multilineoutput} \\ + +diagonal(\{A,x,H\}); & +\begin{multilineoutput}{6cm} +[1 2 3 0 0 0 ] +[ ] +[4 5 6 0 0 0 ] +[ ] +[7 8 9 0 0 0 ] +[ ] +[0 0 0 x 0 0 ] +[ ] +[0 0 0 0 66 77] +[ ] +[0 0 0 0 88 99] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{jordan\_block}. + +\end{Operator} + + +\begin{Operator}{extend} + +\begin{Syntax} +\name{extend}(\meta{matrix},\meta{r},\meta{c},\meta{expr}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{r},\meta{c} :- positive integers. + +\meta{expr} :- algebraic expression or symbol. + +\name{extend} returns a copy of \meta{matrix} that has been extended by +\meta{r} rows and \meta{c} columns. The new entries are made equal to +\meta{expr}. + +\begin{Examples} + +extend(A,1,2,x); & +\begin{multilineoutput}{6cm} +[1 2 3 x x] +[ ] +[4 5 6 x x] +[ ] +[7 8 9 x x] +[ ] +[x x x x x] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{copy\_into}, \nameref{matrix\_augment}, \nameref{matrix\_stack}, +\nameref{remove\_columns}, \nameref{remove\_rows}. + +\end{Operator} + + +\begin{Operator}{find_companion} + +\begin{Syntax} +\name{find\_companion}(\meta{matrix},\meta{x}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{x} :- the variable. + +Given a companion matrix, \name{find\_companion} finds the polynomial +from which it was made. + +\begin{Examples} + +C := companion(x^4+17*x^3-9*x^2+11,x); & +\begin{multilineoutput}{6cm} + [0 0 0 -11] + [ ] + [1 0 0 0 ] +c := [ ] + [0 1 0 9 ] + [ ] + [0 0 1 -17] +\end{multilineoutput}\\ + +find_companion(C,x); & +x^4+17*x^3-9*x^2+11 + +\end{Examples} + +Related functions: +\nameref{companion}. + +\end{Operator} + + +\begin{Operator}{get_columns} +Get columns, get rows: + +\begin{Syntax} +\name{get\_columns}(\meta{matrix},\meta{column\_list}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{c} :- either a positive integer or a list of positive + integers. + +\name{get\_columns} removes the columns of \meta{matrix} specified in +\meta{column\_list} and returns them as a list of column matrices. + +\name{get\_rows} performs the same task on the rows of \meta{matrix}. + +\begin{Examples} + +get_columns(A,\{1,3\}); & +\begin{multilineoutput}{6cm} +\{ + + [1] + [ ] + [4] + [ ] + [7] + + , + + [3] + [ ] + [6] + [ ] + [9] + +\} +\end{multilineoutput} \\ + +get_rows(A,2); & +\begin{multilineoutput}{6cm} +\{ + + [4 5 6] + +\} +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{augment\_columns}, \nameref{stack\_rows}, \nameref{sub\_matrix}. + +\end{Operator} + + +\begin{Operator}{get_rows} +see: \nameref{get\_columns}. +\end{Operator} + + +\begin{Operator}{gram_schmidt} + +\begin{Syntax} +\name{gram\_schmidt}(\{\meta{vec\_list}\}) +\end{Syntax} + +(If you are feeling lazy then the braces can be omitted.) + +\meta{vec\_list} :- linearly independent vectors. Each vector must be +written as a list, eg:\{1,0,0\}. + +\name{gram\_schmidt} performs the gram\_schmidt orthonormalization on +the input vectors. + +It returns a list of orthogonal normalized vectors. + +\begin{Examples} + +gram_schmidt(\{\{1,0,0\},\{1,1,0\},\{1,1,1\}\}); & +\{\{1,0,0\},\{0,1,0\},\{0,0,1\}\} \\ + +gram_schmidt(\{\{1,2\},\{3,4\}\}); & +\{\{ \rfrac{1}{{sqrt(5)}} , \rfrac{2}{sqrt(5)} \}, +\{ \rfrac{2*sqrt(5)}{5} , \rfrac{-sqrt(5)}{5} \}\} + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{hermitian_tp} + +\begin{Syntax} +\name{ hermitian\_tp}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\name{hermitian\_tp} computes the hermitian transpose of \meta{matrix}. + +This is a \nameref{matrix} in which the (i,j)'th entry is the conjugate +of the (j,i)'th entry of \meta{matrix}. + +\begin{Examples} + +J := mat((i+1,i+2,i+3),(4,5,2),(1,i,0)); & +\begin{multilineoutput}{6cm} + [i + 1 i + 2 i + 3] + [ ] +j := [ 4 5 2 ] + [ ] + [ 1 i 0 ] +\end{multilineoutput} \\ + +hermitian_tp(j); & +\begin{multilineoutput}{6cm} +[ - i + 1 4 1 ] +[ ] +[ - i + 2 5 - i] +[ ] +[ - i + 3 2 0 ] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{tp}. + +\end{Operator} + + +\begin{Operator}{hessian} + +\begin{Syntax} +\name{hessian}(\meta{expr},\meta{variable\_list}) +\end{Syntax} + +\meta{expr} :- a scalar expression. + +\meta{variable\_list} :- either a single variable or a list of + variables. + +\name{hessian} computes the hessian matrix of \meta{expr} w.r.t. the +variables in \meta{variable\_list}. + +% Does df exist in the help pages? +This is an n by n matrix where n is the number of variables and the +(i,j)'th entry is \nameref{df}(\meta{expr},\meta{variable\_list}(i), +\meta{variable\_list}(j)). + +\begin{Examples} + +hessian(x*y*z+x^2,\{w,x,y,z\}); & +\begin{multilineoutput}{6cm} +[0 0 0 0] +[ ] +[0 2 z y] +[ ] +[0 z 0 x] +[ ] +[0 y x 0] +\end{multilineoutput}{6cm} + +\end{Examples} + +Related functions: \nameref{df}. + +\end{Operator} + + +\begin{Operator}{hilbert} + +\begin{Syntax} +\name{hilbert}(\meta{square\_size},\meta{expr}) +\end{Syntax} + +\meta{square\_size} :- a positive integer. + +\meta{expr} :- an algebraic expression. + +\name{hilbert} computes the square hilbert matrix of dimension +\meta{square\_size}. + +This is the symmetric matrix in which the (i,j)'th entry is +1/(i+j-\meta{expr}). + +\begin{Examples} + +hilbert(3,y+x); & +\begin{multilineoutput}{6cm} +[ - 1 - 1 - 1 ] +[----------- ----------- -----------] +[ x + y - 2 x + y - 3 x + y - 4 ] +[ ] +[ - 1 - 1 - 1 ] +[----------- ----------- -----------] +[ x + y - 3 x + y - 4 x + y - 5 ] +[ ] +[ - 1 - 1 - 1 ] +[----------- ----------- -----------] +[ x + y - 4 x + y - 5 x + y - 6 ] +\end{multilineoutput} + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{jacobian} + +\begin{Syntax} +\name{jacobian}(\meta{expr\_list},\meta{variable\_list}) +\end{Syntax} + +\meta{expr\_list} :- either a single algebraic expression or a list + of algebraic expressions. + +\meta{variable\_list} :- either a single variable or a list of + variables. + +\name{jacobian} computes the jacobian matrix of \meta{expr\_list} +w.r.t. \meta{variable\_list}. + +This is a matrix whose (i,j)'th entry is \nameref{df}(\meta{expr\_list} +(i),\meta{variable\_list}(j)). + +The matrix is n by m where n is the number of variables and m the number +of expressions. + +\begin{Examples} + +jacobian(\{x^4,x*y^2,x*y*z^3\},\{w,x,y,z\}); & +\begin{multilineoutput}{6cm} +[ 3 ] +[0 4*x 0 0 ] +[ ] +[ 2 ] +[0 y 2*x*y 0 ] +[ ] +[ 3 3 2] +[0 y*z x*z 3*x*y*z ] +\end{multilineoutput} + +\end{Examples} + +Related functions: +\nameref{hessian}, \nameref{df}. + +\end{Operator} + + +\begin{Operator}{jordan_block} + +\begin{Syntax} +\name{jordan\_block}(\meta{expr},\meta{square\_size}) +\end{Syntax} + +\meta{expr} :- an algebraic expression or symbol. + +\meta{square\_size} :- a positive integer. + +\name{jordan\_block} computes the square jordan block matrix J of +dimension \meta{square\_size}. + +The entries of J are: + + J(i,i) = \meta{expr} for i=1 + \ldots n, J(i,i+1) = 1 for i=1 + \ldots n-1, and all other entries are 0. + +\begin{Examples} + +jordan\_block(x,5); & +\begin{multilineoutput}{6cm} +[x 1 0 0 0] +[ ] +[0 x 1 0 0] +[ ] +[0 0 x 1 0] +[ ] +[0 0 0 x 1] +[ ] +[0 0 0 0 x] +\end{multilineoutput} + +\end{Examples} + +Related functions: \nameref{diagonal}, \nameref{companion}. + +\end{Operator} + + +\begin{Operator}{lu_decom} + +\begin{Syntax} +\name{lu\_decom}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix} containing either numeric entries + or imaginary entries with numeric coefficients. + +\name{lu\_decom} performs LU decomposition on \meta{matrix}, ie: it +returns \{L,U\} where L is a lower diagonal \nameref{matrix}, U an +upper diagonal \nameref{matrix} and A = LU. + +Caution: + +The algorithm used can swap the rows of \meta{matrix} during the +calculation. This means that LU does not equal \meta{matrix} but a row +equivalent of it. Due to this, \name{lu\_decom} returns \{L,U,vec\}. +The call \name{convert(\meta{matrix},vec)} will return the matrix that has +been decomposed, i.e: LU = convert(\meta{matrix},vec). + + +\begin{Examples} + +K := mat((1,3,5),(-4,3,7),(8,6,4)); & +\begin{multilineoutput}{6cm} + [1 3 5] + [ ] +k := [-4 3 7] + [ ] + [8 6 4] +\end{multilineoutput}\\ + +on rounded;\\ +lu := lu_decom(K); & +\begin{multilineoutput}{6cm} +lu := \{ + + [8 0 0 ] + [ ] + [-4 6.0 0 ] + [ ] + [1 2.25 1.125] + + , + + + [1 0.75 0.5] + [ ] + [0 1 1.5] + [ ] + [0 0 1 ] + + , + + [3 2 3]\} +\end{multilineoutput} \\ + +first lu * second lu; & +\begin{multilineoutput}{6cm} +[8 6.0 4.0] +[ ] +[-4 3.0 7.0] +[ ] +[1 3.0 5.0] +\end{multilineoutput}\\ + +convert(K,third lu); & +\begin{multilineoutput} +[8 6 4] +[ ] +[-4 3 7] +[ ] +[1 3 5] +\end{multilineoutput}\\ + +P := mat((i+1,i+2,i+3),(4,5,2),(1,i,0)); & +\begin{multilineoutput}{6cm} + [i + 1 i + 2 i + 3] + [ ] +p := [ 4 5 2 ] + [ ] + [ 1 i 0 ] +\end{multilineoutput}\\ + +lu := lu_decom(P); & +\begin{multilineoutput}{6cm} +lu := \{ + + [ 1 0 0 ] + [ ] + [ 4 - 4*i + 5 0 ] + [ ] + [i + 1 3 0.414634146341*i + 2.26829268293] + + , + + + [1 i 0 ] + [ ] + [0 1 0.19512195122*i + 0.243902439024] + [ ] + [0 0 1 ] + + , + + [3 2 3]\} +\end{multilineoutput}\\ + +first lu * second lu; & +\begin{multilineoutput}{6cm} +[ 1 i 0 ] +[ ] +[ 4 5 2.0 ] +[ ] +[i + 1 i + 2 i + 3.0] +\end{multilineoutput}\\ + +convert(P,third lu); & +\begin{multilineoutput}{6cm} +[ 1 i 0 ] +[ ] +[ 4 5 2 ] +[ ] +[i + 1 i + 2 i + 3] +\end{multilineoutput}\\ + +\end{Examples} + +Related functions: \nameref{cholesky}. + +\end{Operator} + + +\begin{Operator}{make_identity} + +\begin{Syntax} +\name{make\_identity}(\meta{square\_size}) +\end{Syntax} + +\meta{square\_size} :- a positive integer. + +\name{make\_identity} creates the identity matrix of dimension +\meta{square\_size}. + +\begin{Examples} + +make_identity(4); & +\begin{multilineoutput}{6cm} +[1 0 0 0] +[ ] +[0 1 0 0] +[ ] +[0 0 1 0] +[ ] +[0 0 0 1] +\end{multilineoutput} + +\end{Examples} + +Related functions: \nameref{diagonal}. + +\end{Operator} + + +\begin{Operator}{matrix_augment} +Matrix augment, matrix stack: + +\begin{Syntax} +\name{matrix\_augment} \{\meta{matrix\_list}\} +\end{Syntax} + +(If you are feeling lazy then the braces can be omitted.) + +\meta{matrix\_list} :- matrices. + +\name{matrix\_augment} sticks the matrices in \meta{matrix\_list} +together horizontally. + +\name{matrix\_stack} sticks the matrices in \meta{matrix\_list} +together vertically. + + +\begin{Examples} + +matrix_augment(\{A,A\}); & +\begin{multilineoutput}{6cm} +[1 2 3 1 2 3] +[ ] +[4 5 6 4 5 6] +[ ] +[7 8 9 7 8 9] +\end{multilineoutput}\\ + +matrix_stack(A,A); & +\begin{multilineoutput}{6cm} +[1 2 3] +[ ] +[4 5 6] +[ ] +[7 8 9] +[ ] +[1 2 3] +[ ] +[4 5 6] +[ ] +[7 8 9] +\end{multilineoutput} \\ + +\end{Examples} + +Related functions: +\nameref{augment\_columns}, \nameref{stack\_rows}, \nameref{sub\_matrix}. + +\end{Operator} + + +\begin{Operator}{matrixp} + +\begin{Syntax} +\name{matrixp}(\meta{test\_input}) +\end{Syntax} + +\meta{test\_input} :- anything you like. + +\name{matrixp} is a boolean function that returns t if the input is a +matrix and nil otherwise. + + +\begin{Examples} + +matrixp A; & +t \\ +matrixp(doodlesackbanana);& +nil + +\end{Examples} + +Related functions: \nameref{squarep}, \nameref{symmetricp}. + +\end{Operator} + + +\begin{Operator}{matrix_stack} +see: \nameref{matrix\_augment}. +\end{Operator} + + +\begin{Operator}{minor} + +\begin{Syntax} +\name{minor}(\meta{matrix},\meta{r},\meta{c}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. +\meta{r},\meta{c} :- positive integers. + +\name{minor} computes the (\meta{r},\meta{c})'th minor of \meta{matrix}. +This is created by removing the \meta{r}'th row and the \meta{c}'th +column from \meta{matrix}. + + +\begin{Examples} + +minor(A,1,3); & +\begin{multilineoutput}{6cm} +[4 5] +[ ] +[7 8] +\end{multilineoutput} + +\end{Examples} + +Related functions: +\nameref{remove\_columns}, \nameref{remove\_rows}. + +\end{Operator} + + +\begin{Operator}{mult_columns} +Mult columns, mult rows: + +\begin{Syntax} +\name{mult\_columns}(\meta{matrix},\meta{column\_list},\meta{expr}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{column\_list} :- a positive integer or a list of positive + integers. + +\meta{expr} :- an algebraic expression. + +\name{mult\_columns} returns a copy of \meta{matrix} in which the +columns specified in \meta{column\_list} have been multiplied by +\meta{expr}. + +\name{mult\_rows} performs the same task on the rows of \meta{matrix}. + +\begin{Examples} + +mult_columns(A,\{1,3\},x); & +\begin{multilineoutput}{6cm} +[ x 2 3*x] +[ ] +[4*x 5 6*x] +[ ] +[7*x 8 9*x] +\end{multilineoutput}\\ + +mult_rows(A,2,10); & +\begin{multilineoutput}{6cm} +[1 2 3 ] +[ ] +[40 50 60] +[ ] +[7 8 9 ] +\end{multilineoutput} + +\end{Examples} + +Related functions: \nameref{add\_to\_columns}, \nameref{add\_to\_rows}. + +\end{Operator} + + +\begin{Operator}{mult_rows} +see: \nameref{mult\_columns}. +\end{Operator} + + +\begin{Operator}{pivot} + +\begin{Syntax} +\name{pivot}(\meta{matrix},\meta{r},\meta{c}) +\end{Syntax} + +\meta{matrix} :- a matrix. + +\meta{r},\meta{c} :- positive integers such that \meta{matrix}(\meta{r}, + \meta{c}) neq 0. + +\name{pivot} pivots \meta{matrix} about it's (\meta{r},\meta{c})'th +entry. + +To do this, multiples of the \meta{r}'th row are added to every other +row in the matrix. + +This means that the \meta{c}'th column will be 0 except for the +(\meta{r},\meta{c})'th entry. + + +\begin{Examples} + +pivot(A,2,3); & +\begin{multilineoutput}{6cm} +[ - 1 ] +[-1 ------ 0] +[ 2 ] +[ ] +[4 5 6] +[ ] +[ 1 ] +[1 --- 0] +[ 2 ] +\end{multilineoutput} + +\end{Examples} + +Related functions: +\nameref{rows\_pivot}. + +\end{Operator} + +\begin{Operator}{pseudo_inverse} + +\begin{Syntax} +\name{pseudo\_inverse}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\name{pseudo\_inverse}, also known as the Moore-Penrose inverse, +computes the pseudo inverse of \meta{matrix}. + +Given the singular value decomposition of \meta{matrix}, i.e: +A = $U*P*V^T$, then the pseudo inverse $A^{-1}$ is defined by +$A^{-1} = V^T*P^{-1}*U$. + +Thus \meta{matrix} * pseudo\_inverse(A) = Id. +(Id is the identity matrix). + + +\begin{Examples} + +R := mat((1,2,3,4),(9,8,7,6)); & +\begin{multilineoutput}{6cm} + [1 2 3 4] +r := [ ] + [9 8 7 6] +\end{multilineoutput}\\ + +on rounded; \\ +pseudo_inverse(R); & +\begin{multilineoutput}{6cm} +[ - 0.199999999996 0.100000000013 ] +[ ] +[ - 0.0499999999988 0.0500000000037 ] +[ ] +[ 0.0999999999982 - 5.57825497203e-12] +[ ] +[ 0.249999999995 - 0.0500000000148 ] +\end{multilineoutput} + +\end{Examples} + + +Related functions: \nameref{svd}. + +\end{Operator} + + +\begin{Operator}{random_matrix} + +\begin{Syntax} +\name{random\_matrix}(\meta{r},\meta{c},\meta{limit}) +\end{Syntax} + +\meta{r},\meta{c},\meta{limit} :- positive integers. + +\name{random\_matrix} creates an \meta{r} by \meta{c} matrix with random +entries in the range -limit < entry < limit. + + +Switches: + +\name{imaginary} :- if on then matrix entries are x+i*y where -limit < x,y + < \meta{limit}. + +\name{not\_negative} :- if on then 0 < entry < \meta{limit}. In the imaginary + case we have 0 < x,y < \meta{limit}. + +\name{only\_integer} :- if on then each entry is an integer. In the imaginary + case x and y are integers. + +\name{symmetric} :- if on then the matrix is symmetric. + +\name{upper\_matrix} :- if on then the matrix is upper triangular. + +\name{lower\_matrix} :- if on then the matrix is lower triangular. + + + +\begin{Examples} + +on rounded; \\ +random_matrix(3,3,10); & +\begin{multilineoutput}{6cm} +[ - 8.11911717343 - 5.71677292768 0.620580830035 ] +[ ] +[ - 0.032596262422 7.1655452861 5.86742633837 ] +[ ] +[ - 9.37155438255 - 7.55636708637 - 8.88618627557] +\end{multilineoutput}\\ + +on only_integer, not_negative, upper_matrix, imaginary; \\ +random_matrix(4,4,10); & +\begin{multilineoutput}{6cm} +[70*i + 15 28*i + 8 2*i + 79 27*i + 44] +[ ] +[ 0 46*i + 95 9*i + 63 95*i + 50] +[ ] +[ 0 0 31*i + 75 14*i + 65] +[ ] +[ 0 0 0 5*i + 52 ] +\end{multilineoutput}\\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{remove_columns} +Remove columns, remove rows: + +\begin{Syntax} +\name{remove\_columns}(\meta{matrix},\meta{column\_list}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. +\meta{column\_list} :- either a positive integer or a list of positive + integers. + +\name{remove\_columns} removes the columns specified in +\meta{column\_list} from \meta{matrix}. + +\name{remove\_rows} performs the same task on the rows of \meta{matrix}. + +\begin{Examples} + +remove_columns(A,2); & +\begin{multilineoutput}{6cm} +[1 3] +[ ] +[4 6] +[ ] +[7 9] +\end{multilineoutput}\\ + +remove_rows(A,\{1,3\}); & +\begin{multilineoutput}{6cm} +[4 5 6] +\end{multilineoutput}\\ + + +\end{Examples} + +Related functions: \nameref{minor}. + +\end{Operator} + + +\begin{Operator}{remove_rows} +see: \nameref{remove\_columns}. +\end{Operator} + + +\begin{Operator}{row_dim} +see: \nameref{column\_dim}. +\end{Operator} + + +\begin{Operator}{rows_pivot} + +\begin{Syntax} +\name{rows\_pivot}(\meta{matrix},\meta{r},\meta{c},\{\meta{row\_list}\}) +\end{Syntax} + +\meta{matrix} :- a nameref{matrix}. + +\meta{r},\meta{c} :- positive integers such that \meta{matrix}(\meta{r}, + \meta{c}) neq 0. + +\meta{row\_list} :- positive integer or a list of positive integers. + +\name{rows\_pivot} performs the same task as \name{pivot} but applies +the pivot only to the rows specified in \meta{row\_list}. + + +\begin{Examples} + +N := mat((1,2,3),(4,5,6),(7,8,9),(1,2,3),(4,5,6)); & +\begin{multilineoutput}{6cm} + [1 2 3] + [ ] + [4 5 6] + [ ] +n := [7 8 9] + [ ] + [1 2 3] + [ ] + [4 5 6] +\end{multilineoutput}\\ + +rows_pivot(N,2,3,{4,5}); & +\begin{multilineoutput}{6cm} +[1 2 3] +[ ] +[4 5 6] +[ ] +[7 8 9] +[ ] +[ - 1 ] +[-1 ------ 0] +[ 2 ] +[ ] +[0 0 0] +\end{multilineoutput}\\ + +\end{Examples} + +Related functions: \nameref{pivot}. + +\end{Operator} + + +\begin{Operator}{simplex} + +\begin{Syntax} +\name{simplex}(\meta{max/min},\meta{objective function}, +\{\meta{linear inequalities}\}) +\end{Syntax} + +\meta{max/min} :- either max or min (signifying maximize and + minimize). + +\meta{objective function} :- the function you are maximizing or + minimizing. + +\meta{linear inequalities} :- the constraint inequalities. Each one must + be of the form {\it sum of variables ( + <=,=,>=) number}. + +\name{simplex} applies the revised simplex algorithm to find the +optimal(either maximum or minimum) value of the +\meta{objective function} under the linear inequality constraints. + +It returns \{optimal value,\{ values of variables at this optimal\}\}. + +The algorithm implies that all the variables are non-negative. + +\begin{Examples} + + simplex(max,x+y,\{x>=10,y>=20,x+y<=25\}); & + + ***** Error in simplex: Problem has no feasible solution\\ + +simplex(max,10x+5y+5.5z,\{5x+3z<=200,x+0.1y+0.5z<=12, +0.1x+0.2y+0.3z<=9, 30x+10y+50z<=1500\}); & + +\{525.0,\{x=40.0,y=25.0,z=0\}\}\\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{squarep} + +\begin{Syntax} +\name{squarep}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\name{squarep} is a predicate that returns t if the \meta{matrix} is +square and nil otherwise. + +\begin{Examples} + +squarep(mat((1,3,5))); & +nil \\ +squarep(A); +t\\ + +\end{Examples} + +Related functions: \nameref{matrixp}, \nameref{symmetricp}. + +\end{Operator} + + +\begin{Operator}{stack_rows} +see: \nameref{augment\_columns}. +\end{Operator} + + +\begin{Operator}{sub_matrix} + +\begin{Syntax} +\name{sub\_matrix}(\meta{matrix},\meta{row\_list},\meta{column\_list}) +\end{Syntax} + +\meta{matrix} :- a matrix. +\meta{row\_list}, \meta{column\_list} :- either a positive integer or a + list of positive integers. + +name{sub\_matrix} produces the matrix consisting of the intersection of +the rows specified in \meta{row\_list} and the columns specified in +\meta{column\_list}. + + +\begin{Examples} + +sub_matrix(A,\{1,3\},\{2,3\}); & +\begin{multilineoutput}{6cm} +[2 3] +[ ] +[8 9] +\end{multilineoutput} + +\end{Examples} + +Related functions: +\nameref{augment\_columns}, \nameref{stack\_rows}. + +\end{Operator} + + +\begin{Operator}{svd} +\index{singular value decomposition} +Singular value decomposition: + +\begin{Syntax} +\name{svd}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix} containing only numeric entries. + + +\name{svd} computes the singular value decomposition of \meta{matrix}. + +It returns + +\{U,P,V\} + +where A = $U*P*V^T$ + +and P = diag(sigma(1) ... sigma(n)). + +sigma(i) for i= 1 ... n are the singular values of +\meta{matrix}. + +n is the column dimension of \meta{matrix}. + +The singular values of \meta{matrix} are the non-negative square roots +of the eigenvalues of $A^T*A$. + +U and V are such that $U*U^T = V*V^T = V^T*V$ = Id. +Id is the identity matrix. + + +\begin{Examples} + +Q := mat((1,3),(-4,3)); & +\begin{multilineoutput}{6cm} + [1 3] +q := [ ] + [-4 3] +\end{multilineoutput}\\ + +on rounded; \\ +svd(Q); & +\begin{multilineoutput}{6cm} +\{ + + [ 0.289784137735 0.957092029805] + [ ] + [ - 0.957092029805 0.289784137735] + + , + + + [5.1491628629 0 ] + [ ] + [ 0 2.9130948854] + + , + + + [ - 0.687215403194 0.726453707825 ] + [ ] + [ - 0.726453707825 - 0.687215403194] + +\} +\end{multilineoutput}\\ + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{swap_columns} +Swap columns, swap rows: + +\begin{Syntax} +\name{swap\_columns} (\meta{matrix},\meta{c1},\meta{c2}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{c1},\meta{c1} :- positive integers. + +\name{swap\_columns} swaps column \meta{c1} of \meta{matrix} with +column \meta{c2}. + +\name{swap\_rows} performs the same task on two rows of \meta{matrix}. + +\begin{Examples} + +swap_columns(A,2,3); & +\begin{multilineoutput}{6cm} +[1 3 2] +[ ] +[4 6 5] +[ ] +[7 9 8] +\end{multilineoutput}\\ + +swap_rows(A,1,3); & +\begin{multilineoutput}{6cm} +[7 8 9] +[ ] +[4 5 6] +[ ] +[1 2 3] +\end{multilineoutput} + +\end{Examples} + +Related functions: \nameref{swap\_entries}. + +\end{Operator} + + +\begin{Operator}{swap_entries} + +\begin{Syntax} +\name{swap\_entries}(\meta{matrix},\{\meta{r1},\meta{c1}\},\{\meta{r2}, +\meta{c2}\}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\meta{r1},\meta{c1},\meta{r2},\meta{c2} :- positive integers. + +\name{swap\_entries} swaps \meta{matrix}(\meta{r1},\meta{c1}) with +\meta{matrix}(\meta{r2},\meta{c2}). + +\begin{Examples} + +swap_entries(A,\{1,1\},\{3,3\}); & +\begin{multilineoutput}{6cm} +[9 2 3] +[ ] +[4 5 6] +[ ] +[7 8 1] +\end{multilineoutput} + +\end{Examples} + +Related functions: \nameref{swap\_columns}, \nameref{swap\_rows}. + +\end{Operator} + + +\begin{Operator}{swap_rows} +see: \nameref{swap\_columns}. +\end{Operator} + + +\begin{Operator}{symmetricp} + +\begin{Syntax} +\name{symmetricp}(\meta{matrix}) +\end{Syntax} + +\meta{matrix} :- a \nameref{matrix}. + +\name{symmetricp} is a predicate that returns t if the matrix is symmetric +and nil otherwise. + + +\begin{Examples} + +symmetricp(make_identity(11)); & +t \\ +symmetricp(A); & +nil\\ + +\end{Examples} + +Related functions: \nameref{matrixp}, \nameref{squarep}. + +\end{Operator} + + +\begin{Operator}{toeplitz} + +\begin{Syntax} +\name{toeplitz}(\meta{expr\_list}) +\end{Syntax} +(If you are feeling lazy then the braces can be omitted.) + +\meta{expr\_list} :- list of algebraic expressions. + +\name{toeplitz} creates the toeplitz matrix from the \meta{expr\_list}. + +This is a square symmetric matrix in which the first expression is +placed on the diagonal and the i'th expression is placed on the (i-1)'th +sub and super diagonals. + +It has dimension n where n is the number of expressions. + + +\begin{Examples} + +toeplitz({w,x,y,z}); & +\begin{multilineoutput}{6cm} +[w x y z] +[ ] +[x w x y] +[ ] +[y x w x] +[ ] +[z y x w] +\end{multilineoutput} + +\end{Examples} + +\end{Operator} + + +\begin{Operator}{vandermonde} + +\begin{Syntax} +\name{vandermonde}(\{\meta{expr\_list}\}) +\end{Syntax} +(If you are feeling lazy then the braces can be omitted.) + +\meta{expr\_list} :- list of algebraic expressions. + +\name{vandermonde} creates the vandermonde matrix from the +\meta{expr\_list}. + +This is the square matrix in which the (i,j)'th entry is +\meta{expr\_list}$(i)^(j-1)$. + +It has dimension n where n is the number of expressions. + + +\begin{Examples} +vandermonde({x,2*y,3*z}); & +\begin{multilineoutput}{6cm} +[ 2 ] +[1 x x ] +[ ] +[ 2] +[1 2*y 4*y ] +[ ] +[ 2] +[1 3*z 9*z ] +\end{multilineoutput} + +\end{Examples} + +\end{Operator} + Index: r36/help/normform.tex ================================================================== --- r36/help/normform.tex +++ r36/help/normform.tex @@ -1,362 +1,362 @@ -\section{Matrix Normal Forms} - -\begin{Operator}{Smithex} -The operator \name{smithex} computes the Smith normal form S of a -\nameref{matrix} A (say). It returns \{S,P,$P^-1$\} where $P*S*P^-1 = A$. - -\begin{Syntax} -\name{smithex}\(\meta{matrix},\meta{variable}\) - -\meta{matrix} :- a rectangular \nameref{matrix} of univariate polynomials in - \meta{variable}. -\meta{variable} :- the variable. -\end{Syntax} - -\begin{Examples} - a := mat((x,x+1),(0,3*x^2)); & -\begin{multilineoutput}{6cm} - [x x + 1] - [ ] - a := [ 2 ] - [0 3*x ] -\end{multilineoutput}\\ - - smithex(a,x); & -\begin{multilineoutput}{6cm} - [1 0 ] [1 0] [x x + 1] -\{ [ ], [ ], [ ] \} - [ 3] [ 2 ] [ ] - [0 x ] [3*x 1] [-3 -3 ] -\end{multilineoutput}\\ -\end{Examples} -\end{Operator} - - -\begin{Operator}{Smithex\_int} -The operator \name{smithex\_int} performs the same task as \name{smithex} -but on matrices containing only integer entries. Namely, -\name{smithex\_int} returns \{S,P,$P^-1$\} where S is the smith normal -form of the input \nameref{matrix} (A say), and $P*S*P^-1 = A$. - -\begin{Syntax} -\name{smithex\_int}\(\meta{matrix}\) - -\meta{matrix} :- a rectangular \nameref{matrix} of integer entries. -\end{Syntax} - -\begin{Examples} - a := mat((9,-36,30),(-36,192,-180),(30,-180,180)); & -\begin{multilineoutput}{6cm} - [ 9 -36 30 ] - [ ] -a := [-36 192 -180] - [ ] - [30 -180 180 ] -\end{multilineoutput}\\ - - smithex_int(a); & -\begin{multilineoutput}{6cm} - [3 0 0 ] [-17 -5 -4 ] [1 -24 30 ] - [ ] [ ] [ ] -\{ [0 12 0 ], [64 19 15 ], [-1 25 -30] \} - [ ] [ ] [ ] - [0 0 60] [-50 -15 -12] [0 -1 1 ] -\end{multilineoutput}\\ -\end{Examples} -\end{Operator} - - -\begin{Operator}{Frobenius} -The operator \name{frobenius} computes the \name{frobenius} normal form F of a -\nameref{matrix} (A say). It returns \{F,P,$P^-1$\} where $P*F*P^-1 = A$. - -\begin{Syntax} -\name{frobenius}\(\meta{matrix}\) - -\meta{matrix} :- a square \nameref{matrix}. -\end{Syntax} - -Field Extensions: - -By default, calculations are performed in the rational numbers. To -extend this field the \nameref{arnum} package can be used. The package must -first be loaded by load\_package arnum;. The field can now be extended -by using the defpoly command. For example, defpoly sqrt2**2-2; will -extend the field to include the square root of 2 (now defined by sqrt2). - -Modular Arithmetic: - -\name{Frobenius} can also be calculated in a modular base. To do this -first type on modular;. Then setmod p; (where p is a prime) will set -the modular base of calculation to p. By further typing on balanced\_mod -the answer will appear using a symmetric modular representation. See -\nameref{ratjordan} for an example. - -\begin{Examples} - a := mat((x,x^2),(3,5*x)); & -\begin{multilineoutput}{6cm} - [ 2 ] - [x x ] -a := [ ] - [3 5*x] -\end{multilineoutput}\\ - frobenius(a);& -\begin{multilineoutput}{6cm} - [ 2] [1 x] [ - x ] -\{ [0 - 2*x ], [ ], [1 -----] \} - [ ] [0 3] [ 3 ] - [1 6*x ] [ ] - [ 1 ] - [0 --- ] - [ 3 ] - -\end{multilineoutput}\\ - load\_package arnum;\\ - defpoly sqrt2**2-2;\\ - a := mat((sqrt2,5),(7*sqrt2,sqrt2));& -\begin{multilineoutput}{6cm} - [ sqrt2 5 ] -a := [ ] - [7*sqrt2 sqrt2] -\end{multilineoutput}\\ - - frobenius(a); & -\begin{multilineoutput}{6cm} - [0 35*sqrt2 - 2] [1 sqrt2 ] [ 1 ] -\{ [ ], [ ], [1 - --- ] \} - [1 2*sqrt2 ] [1 7*sqrt2] [ 7 ] - [ ] - [ 1 ] - [0 ----*sqrt2] - [ 14 ] - -\end{multilineoutput}\\ -\end{Examples} -\end{Operator} - - - -\begin{Operator}{Ratjordan} -The operator \name{ratjordan} computes the rational Jordan normal form R -of a \nameref{matrix} (A say). It returns \{R,P,$P^-1$\} where $P*R*P^-1 = A$. - -\begin{Syntax} -\name{ratjordan}\(\meta{matrix}\) - -\meta{matrix} :- a square \nameref{matrix}. -\end{Syntax} - -Field Extensions: - -By default, calculations are performed in the rational numbers. To -extend this field the \name{arnum} package can be used. The package must -first be loaded by load\_package arnum;. The field can now be extended -by using the defpoly command. For example, defpoly sqrt2**2-2; will -extend the field to include the square root of 2 (now defined by sqrt2). -See \nameref{frobenius} for an example. - -Modular Arithmetic: - -\name{ratjordan} can also be calculated in a modular base. To do this -first type on modular;. Then setmod p; (where p is a prime) will set -the modular base of calculation to p. By further typing on balanced\_mod -the answer will appear using a symmetric modular representation. - -\begin{Examples} - a := mat((5,4*x),(2,x^2));& -\begin{multilineoutput}{6cm} - [5 4*x] - [ ] -a := [ 2 ] - [2 x ] -\end{multilineoutput}\\ - - ratjordan(a); & -\begin{multilineoutput}{6cm} - [0 x*( - 5*x + 8)] [1 5] [ -5 ] -\{ [ ], [ ], [1 -----] \} - [ 2 ] [0 2] [ 2 ] - [1 x + 5 ] [ ] - [ 1 ] - [0 -----] - [ 2 ] -\end{multilineoutput}\\ - on modular; \\ - setmod 23; \\ - a := mat((12,34),(56,78)); & -\begin{multilineoutput}{6cm} - [12 11] -a := [ ] - [10 9 ] -\end{multilineoutput}\\ - - ratjordan(a); & -\begin{multilineoutput}{6cm} - [15 0] [16 8] [1 21] -\{ [ ], [ ], [ ] \} - [0 6] [19 4] [1 4 ] -\end{multilineoutput}\\ - - on balanced\_mod;\\ - ratjordan(a);& -\begin{multilineoutput}{6cm} - [- 8 0] [ - 7 8] [1 - 2] -\{ [ ], [ ], [ ] \} - [ 0 6] [ - 4 4] [1 4 ] -\end{multilineoutput}\\ - -\end{Examples} -\end{Operator} - - - -\begin{Operator}{Jordansymbolic} -The operator \name{jordansymbolic} computes the Jordan normal form J -of a \nameref{matrix} (A say). It returns \{J,L,P,$P^-1$\} where -$P*J*P^-1 = A$. L = \{ll,mm\} where mm is a name and ll is a list of -irreducible factors of p(mm). - -\begin{Syntax} -\name{jordansymbolic}\(\meta{matrix}\) - -\meta{matrix} :- a square \nameref{matrix}. -\end{Syntax} - -Field Extensions: - -By default, calculations are performed in the rational numbers. To -extend this field the \nameref{arnum} package can be used. The package must -first be loaded by load\_package arnum;. The field can now be extended -by using the defpoly command. For example, defpoly sqrt2**2-2; will -extend the field to include the square root of 2 (now defined by sqrt2). -See \nameref{frobenius} for an example. - -Modular Arithmetic: - -\name{jordansymbolic} can also be calculated in a modular base. To do this -first type on modular;. Then setmod p; (where p is a prime) will set -the modular base of calculation to p. By further typing on balanced\_mod -the answer will appear using a symmetric modular representation. See -\nameref{ratjordan} for an example. - -% Extras: - -% If using \name{xr}, the X interface for REDUCE, then the appearance of the -% output can be improved by switching on looking\_good. This -% converts any lambdas to a greek font. - -\begin{Examples} - - a := mat((1,y),(2,5*y)); & -\begin{multilineoutput}{6cm} - [1 y ] -a := [ ] - [2 5*y] -\end{multilineoutput}\\ - - jordansymbolic(a); & -\begin{multilineoutput}{6cm} -\{ - - [lambda11 0 ] - [ ] - [ 0 lambda12] - - , - - 2 - {{lambda - 5*lambda*y - lambda + 3*y},lambda}, - - - [lambda11 - 5*y lambda12 - 5*y] - [ ] - [ 2 2 ] - - , - - - [ 2*lambda11 - 5*y - 1 5*lambda11*y - lambda11 - y + 1 ] - [---------------------- ---------------------------------] - [ 2 2 ] - [ 25*y - 2*y + 1 2*(25*y - 2*y + 1) ] - [ ] - [ 2*lambda12 - 5*y - 1 5*lambda12*y - lambda12 - y + 1 ] - [---------------------- ---------------------------------] - [ 2 2 ] - [ 25*y - 2*y + 1 2*(25*y - 2*y + 1) ] - - \} - -\end{multilineoutput}\\ -\end{Examples} -\end{Operator} - - - -\begin{Operator}{Jordan} -The operator \name{jordan} computes the Jordan normal form J -of a \nameref{matrix} (A say). It returns \{J,P,$P^-1$\} where $P*J*P^-1 = A$. - -\begin{Syntax} -\name{jordan}\(\meta{matrix}\) - -\meta{matrix} :- a square \nameref{matrix}. -\end{Syntax} - -Field Extensions: -By default, calculations are performed in the rational numbers. To -extend this field the \name{arnum} package can be used. The package must -first be loaded by load\_package arnum;. The field can now be extended -by using the defpoly command. For example, defpoly sqrt2**2-2; will -extend the field to include the square root of 2 (now defined by sqrt2). -See \nameref{frobenius} for an example. - -Modular Arithmetic: -\name{Jordan} can also be calculated in a modular base. To do this -first type on modular;. Then setmod p; (where p is a prime) will set -the modular base of calculation to p. By further typing on balanced\_mod -the answer will appear using a symmetric modular representation. See -\nameref{ratjordan} for an example. - -\begin{Examples} - - a := mat((1,x),(0,x)); & -\begin{multilineoutput}{6cm} - [1 x] -a := [ ] - [0 x] -\end{multilineoutput}\\ - - jordan(a);& -\begin{multilineoutput}{6cm} -\{ - - [1 0] - [ ] - [0 x] - - , - - - [ 1 x ] - [------- --------------] - [ x - 1 2 ] - [ x - 2*x + 1 ] - [ ] - [ 1 ] - [ 0 ------- ] - [ x - 1 ] - - , - - - [x - 1 - x ] - [ ] - [ 0 x - 1] - - \} -\end{multilineoutput}\\ -\end{Examples} - -\end{Operator} - +\section{Matrix Normal Forms} + +\begin{Operator}{Smithex} +The operator \name{smithex} computes the Smith normal form S of a +\nameref{matrix} A (say). It returns \{S,P,$P^-1$\} where $P*S*P^-1 = A$. + +\begin{Syntax} +\name{smithex}\(\meta{matrix},\meta{variable}\) + +\meta{matrix} :- a rectangular \nameref{matrix} of univariate polynomials in + \meta{variable}. +\meta{variable} :- the variable. +\end{Syntax} + +\begin{Examples} + a := mat((x,x+1),(0,3*x^2)); & +\begin{multilineoutput}{6cm} + [x x + 1] + [ ] + a := [ 2 ] + [0 3*x ] +\end{multilineoutput}\\ + + smithex(a,x); & +\begin{multilineoutput}{6cm} + [1 0 ] [1 0] [x x + 1] +\{ [ ], [ ], [ ] \} + [ 3] [ 2 ] [ ] + [0 x ] [3*x 1] [-3 -3 ] +\end{multilineoutput}\\ +\end{Examples} +\end{Operator} + + +\begin{Operator}{Smithex\_int} +The operator \name{smithex\_int} performs the same task as \name{smithex} +but on matrices containing only integer entries. Namely, +\name{smithex\_int} returns \{S,P,$P^-1$\} where S is the smith normal +form of the input \nameref{matrix} (A say), and $P*S*P^-1 = A$. + +\begin{Syntax} +\name{smithex\_int}\(\meta{matrix}\) + +\meta{matrix} :- a rectangular \nameref{matrix} of integer entries. +\end{Syntax} + +\begin{Examples} + a := mat((9,-36,30),(-36,192,-180),(30,-180,180)); & +\begin{multilineoutput}{6cm} + [ 9 -36 30 ] + [ ] +a := [-36 192 -180] + [ ] + [30 -180 180 ] +\end{multilineoutput}\\ + + smithex_int(a); & +\begin{multilineoutput}{6cm} + [3 0 0 ] [-17 -5 -4 ] [1 -24 30 ] + [ ] [ ] [ ] +\{ [0 12 0 ], [64 19 15 ], [-1 25 -30] \} + [ ] [ ] [ ] + [0 0 60] [-50 -15 -12] [0 -1 1 ] +\end{multilineoutput}\\ +\end{Examples} +\end{Operator} + + +\begin{Operator}{Frobenius} +The operator \name{frobenius} computes the \name{frobenius} normal form F of a +\nameref{matrix} (A say). It returns \{F,P,$P^-1$\} where $P*F*P^-1 = A$. + +\begin{Syntax} +\name{frobenius}\(\meta{matrix}\) + +\meta{matrix} :- a square \nameref{matrix}. +\end{Syntax} + +Field Extensions: + +By default, calculations are performed in the rational numbers. To +extend this field the \nameref{arnum} package can be used. The package must +first be loaded by load\_package arnum;. The field can now be extended +by using the defpoly command. For example, defpoly sqrt2**2-2; will +extend the field to include the square root of 2 (now defined by sqrt2). + +Modular Arithmetic: + +\name{Frobenius} can also be calculated in a modular base. To do this +first type on modular;. Then setmod p; (where p is a prime) will set +the modular base of calculation to p. By further typing on balanced\_mod +the answer will appear using a symmetric modular representation. See +\nameref{ratjordan} for an example. + +\begin{Examples} + a := mat((x,x^2),(3,5*x)); & +\begin{multilineoutput}{6cm} + [ 2 ] + [x x ] +a := [ ] + [3 5*x] +\end{multilineoutput}\\ + frobenius(a);& +\begin{multilineoutput}{6cm} + [ 2] [1 x] [ - x ] +\{ [0 - 2*x ], [ ], [1 -----] \} + [ ] [0 3] [ 3 ] + [1 6*x ] [ ] + [ 1 ] + [0 --- ] + [ 3 ] + +\end{multilineoutput}\\ + load\_package arnum;\\ + defpoly sqrt2**2-2;\\ + a := mat((sqrt2,5),(7*sqrt2,sqrt2));& +\begin{multilineoutput}{6cm} + [ sqrt2 5 ] +a := [ ] + [7*sqrt2 sqrt2] +\end{multilineoutput}\\ + + frobenius(a); & +\begin{multilineoutput}{6cm} + [0 35*sqrt2 - 2] [1 sqrt2 ] [ 1 ] +\{ [ ], [ ], [1 - --- ] \} + [1 2*sqrt2 ] [1 7*sqrt2] [ 7 ] + [ ] + [ 1 ] + [0 ----*sqrt2] + [ 14 ] + +\end{multilineoutput}\\ +\end{Examples} +\end{Operator} + + + +\begin{Operator}{Ratjordan} +The operator \name{ratjordan} computes the rational Jordan normal form R +of a \nameref{matrix} (A say). It returns \{R,P,$P^-1$\} where $P*R*P^-1 = A$. + +\begin{Syntax} +\name{ratjordan}\(\meta{matrix}\) + +\meta{matrix} :- a square \nameref{matrix}. +\end{Syntax} + +Field Extensions: + +By default, calculations are performed in the rational numbers. To +extend this field the \name{arnum} package can be used. The package must +first be loaded by load\_package arnum;. The field can now be extended +by using the defpoly command. For example, defpoly sqrt2**2-2; will +extend the field to include the square root of 2 (now defined by sqrt2). +See \nameref{frobenius} for an example. + +Modular Arithmetic: + +\name{ratjordan} can also be calculated in a modular base. To do this +first type on modular;. Then setmod p; (where p is a prime) will set +the modular base of calculation to p. By further typing on balanced\_mod +the answer will appear using a symmetric modular representation. + +\begin{Examples} + a := mat((5,4*x),(2,x^2));& +\begin{multilineoutput}{6cm} + [5 4*x] + [ ] +a := [ 2 ] + [2 x ] +\end{multilineoutput}\\ + + ratjordan(a); & +\begin{multilineoutput}{6cm} + [0 x*( - 5*x + 8)] [1 5] [ -5 ] +\{ [ ], [ ], [1 -----] \} + [ 2 ] [0 2] [ 2 ] + [1 x + 5 ] [ ] + [ 1 ] + [0 -----] + [ 2 ] +\end{multilineoutput}\\ + on modular; \\ + setmod 23; \\ + a := mat((12,34),(56,78)); & +\begin{multilineoutput}{6cm} + [12 11] +a := [ ] + [10 9 ] +\end{multilineoutput}\\ + + ratjordan(a); & +\begin{multilineoutput}{6cm} + [15 0] [16 8] [1 21] +\{ [ ], [ ], [ ] \} + [0 6] [19 4] [1 4 ] +\end{multilineoutput}\\ + + on balanced\_mod;\\ + ratjordan(a);& +\begin{multilineoutput}{6cm} + [- 8 0] [ - 7 8] [1 - 2] +\{ [ ], [ ], [ ] \} + [ 0 6] [ - 4 4] [1 4 ] +\end{multilineoutput}\\ + +\end{Examples} +\end{Operator} + + + +\begin{Operator}{Jordansymbolic} +The operator \name{jordansymbolic} computes the Jordan normal form J +of a \nameref{matrix} (A say). It returns \{J,L,P,$P^-1$\} where +$P*J*P^-1 = A$. L = \{ll,mm\} where mm is a name and ll is a list of +irreducible factors of p(mm). + +\begin{Syntax} +\name{jordansymbolic}\(\meta{matrix}\) + +\meta{matrix} :- a square \nameref{matrix}. +\end{Syntax} + +Field Extensions: + +By default, calculations are performed in the rational numbers. To +extend this field the \nameref{arnum} package can be used. The package must +first be loaded by load\_package arnum;. The field can now be extended +by using the defpoly command. For example, defpoly sqrt2**2-2; will +extend the field to include the square root of 2 (now defined by sqrt2). +See \nameref{frobenius} for an example. + +Modular Arithmetic: + +\name{jordansymbolic} can also be calculated in a modular base. To do this +first type on modular;. Then setmod p; (where p is a prime) will set +the modular base of calculation to p. By further typing on balanced\_mod +the answer will appear using a symmetric modular representation. See +\nameref{ratjordan} for an example. + +% Extras: + +% If using \name{xr}, the X interface for REDUCE, then the appearance of the +% output can be improved by switching on looking\_good. This +% converts any lambdas to a greek font. + +\begin{Examples} + + a := mat((1,y),(2,5*y)); & +\begin{multilineoutput}{6cm} + [1 y ] +a := [ ] + [2 5*y] +\end{multilineoutput}\\ + + jordansymbolic(a); & +\begin{multilineoutput}{6cm} +\{ + + [lambda11 0 ] + [ ] + [ 0 lambda12] + + , + + 2 + {{lambda - 5*lambda*y - lambda + 3*y},lambda}, + + + [lambda11 - 5*y lambda12 - 5*y] + [ ] + [ 2 2 ] + + , + + + [ 2*lambda11 - 5*y - 1 5*lambda11*y - lambda11 - y + 1 ] + [---------------------- ---------------------------------] + [ 2 2 ] + [ 25*y - 2*y + 1 2*(25*y - 2*y + 1) ] + [ ] + [ 2*lambda12 - 5*y - 1 5*lambda12*y - lambda12 - y + 1 ] + [---------------------- ---------------------------------] + [ 2 2 ] + [ 25*y - 2*y + 1 2*(25*y - 2*y + 1) ] + + \} + +\end{multilineoutput}\\ +\end{Examples} +\end{Operator} + + + +\begin{Operator}{Jordan} +The operator \name{jordan} computes the Jordan normal form J +of a \nameref{matrix} (A say). It returns \{J,P,$P^-1$\} where $P*J*P^-1 = A$. + +\begin{Syntax} +\name{jordan}\(\meta{matrix}\) + +\meta{matrix} :- a square \nameref{matrix}. +\end{Syntax} + +Field Extensions: +By default, calculations are performed in the rational numbers. To +extend this field the \name{arnum} package can be used. The package must +first be loaded by load\_package arnum;. The field can now be extended +by using the defpoly command. For example, defpoly sqrt2**2-2; will +extend the field to include the square root of 2 (now defined by sqrt2). +See \nameref{frobenius} for an example. + +Modular Arithmetic: +\name{Jordan} can also be calculated in a modular base. To do this +first type on modular;. Then setmod p; (where p is a prime) will set +the modular base of calculation to p. By further typing on balanced\_mod +the answer will appear using a symmetric modular representation. See +\nameref{ratjordan} for an example. + +\begin{Examples} + + a := mat((1,x),(0,x)); & +\begin{multilineoutput}{6cm} + [1 x] +a := [ ] + [0 x] +\end{multilineoutput}\\ + + jordan(a);& +\begin{multilineoutput}{6cm} +\{ + + [1 0] + [ ] + [0 x] + + , + + + [ 1 x ] + [------- --------------] + [ x - 1 2 ] + [ x - 2*x + 1 ] + [ ] + [ 1 ] + [ 0 ------- ] + [ x - 1 ] + + , + + + [x - 1 - x ] + [ ] + [ 0 x - 1] + + \} +\end{multilineoutput}\\ +\end{Examples} + +\end{Operator} + Index: r36/help/outmode.tex ================================================================== --- r36/help/outmode.tex +++ r36/help/outmode.tex @@ -1,232 +1,232 @@ -\section{Outmoded Operations} - -\begin{Command}{ED} -The \name{ed} command invokes a simple line editor for REDUCE input -statements. - -\begin{Syntax} -\name{ed} \meta{integer} or \name{ed} -\end{Syntax} - -\name{ed} called with no argument edits the last input statement. If -\meta{integer} is greater than or equal to the current line number, an error -message is printed. Reenter a proper \name{ed} command or return to the -top level with a semicolon. - -The editor formats REDUCE's version of the desired input statement, -dividing it into lines at semicolons and dollar signs. The statement is -printed at the beginning of the edit session. The editor works on one -line at a time, and has a pointer (shown by \name{^}) to the current -character of that line. When the session begins, the pointer is at the -left hand side of the first line. The editing prompt is \name{>}. - -The following commands are available. They may be entered in either upper -or lower case. All commands are activated by the carriage return, which -also prints out the current line after changes. Several commands can be -placed on a single line, except that commands terminated by an \key{ESC} -must be the last command before the carriage return. - -\begin{itemize} -\item[b] -Move pointer to beginning of current line. - -\item[d\meta{digit}] -Delete current character and next (digit-1) characters. An error message -is printed if anything other than a single digit follows d. If there are -fewer than \meta{digit} characters left on the line, all but the final -dollar sign or semicolon is removed. To delete a line completely, use the -k command. - -\item[e] -End the current session, causing the edited expression to be reparsed by -REDUCE. - -\item[f\meta{char}] -Find the next occurrence of the character \meta{char} to the right of the -pointer on the current line and move the pointer to it. If the character is -not found, an error message is printed and the pointer remains in its -original position. Other lines are not searched. The f command is not -case-sensitive. - -\item[i\meta{string}\key{ESC}] -Insert \meta{string} in front of pointer. The \key{ESC} key is your -delimiter for the input string. No other command may follow this one on -the same line. - -\item[k] -Kill rest of the current line, including the semicolon or dollar sign -terminator. If there are characters remaining on the current line, and it -is the last line of the input statement, a semicolon is added to the line -as a terminator for REDUCE. If the current line is now empty, one of the -following actions is performed: If there is a following line, it becomes -the current line and the pointer is placed at its first character. If the -current line was the final line of the statement, and there is a previous -line, the previous line becomes the current line. If the current line was -the only line of the statement, and it is empty, a single semicolon is -inserted for REDUCE to parse. - -\item[l] -Finish editing this line and move to the last previous line. An error message -is printed if there is no previous line. - -\item[n] -Finish editing this line and move to the next line. An error message is -printed if there is no next line. - -\item[p] -Print out all the lines of the statement. Then a dotted line is printed, and -the current line is reprinted, with the pointer under it. - -\item[q] -Quit the editing session without saving the changes. If a semicolon is -entered after q, a new line prompt is given, otherwise REDUCE prompts you -for another command. Whatever you type in to the prompt appearing after -the q is entered is stored as the input for the line number in which you -called the edit. Thus if you enter a semicolon, neither \nameref{input} -\name{ed} will find anything under the current number. - -\item[r\meta{char}] -Replace the character at the pointer by \meta{char}. - -\item[s\meta{string}\key{ESC}] -Search for the first occurrence of \meta{string} to the right of the -pointer on the current line and move the pointer to its first character. -The \key{ESC} key is your delimiter for the input string. The s function -does not search other lines of the statement. If the string is not found, -an error message is printed and the pointer remains in its original -position. The s command is not case-sensitive. No other command may -follow this one on the same line. - -\item[x \meta{or space}] -Move the pointer one character to the right. If the pointer is already at -the end of the line, an error message is printed. - -\item[- \meta{(minus)}] -Move the pointer one character to the left. If the pointer is already at the -beginning of the line, an error message is printed. - -\item[?] -Display the Help menu, showing the commands and their actions. -\end{itemize} - -\begin{Examples} -\explanation{(Line numbers are shown in the following examples)} \\ -2: >>x**2 + y; \\ -X^{2} + Y \\ -3: >>ed 2; \\ - X**2 + Y; \\ - ^ \\ -For help, type '?' \\ -?- (Enter three spaces and \key{Return}) \\ - X**2 + Y; \\ - ^ \\ -?- r5 \\ - X**5 + Y; \\ - ^ \\ -?- fY \\ - X**5 + Y; \\ - ^ \\ -?- iabc (Terminate with \key{ESC} and \key{Return}) \\ - X**5 + abcY; \\ - ^ \\ -?- ---- \\ - X**5 + abcY; \\ - ^ \\ -?- fbd2 \\ - X**5 + aY; \\ - ^ \\ -?- b \\ - X**5 + aY; \\ - ^ \\ -?- e \\ -AY + X^{5} \\ -4: >>procedure dumb(a); \\ ->>write a; \\ -DUMB \\ -5: >>dumb(17); \\ -17 \\ -6: >>ed 4; \\ - PROCEDURE DUMB (A); \\ - ^ \\ -WRITE A; \\ -?- fArBn \\ - WRITE A; \\ - ^ \\ -?- ibegin scalar a; a := b + 10; (Type a space, \key{ESC}, and \key{Return}) \\ - begin scalar a; a := b + 10; WRITE A; \\ -?- f;i end \key{ESC}, \key{Return} \\ - begin scalar b; b := a + 10; WRITE A end; \\ - ^ \\ -?- p \\ - PROCEDURE DUMB (B); \\ - begin scalar b; b := a + 10; WRITE A end; \\ - - - - - - - - - - - \\ - begin scalar b; b := a + 10; WRITE A end; \\ - ^ \\ -?- e \\ -DUMB \\ -7: >>dumb(17); \\ -27 \\ -8: >> & -\end{Examples} - -\begin{Comments} -Note that REDUCE reparsed the procedure \name{dumb} and updated the -definition. - -Since REDUCE divides the expression to be edited into lines at semicolons or -dollar sign terminators, some lines may occupy more than one line of screen -space. If the pointer is directly beneath the last line of text, it -refers to the top line of text. If there is a blank line between the -last line of text and the pointer, it refers to the second line -of text, and likewise for cases of greater than two lines of text. In other -words, the entire REDUCE statement up to the next terminator is printed, even -if it runs to several lines, then the pointer line is printed. - -You can insert new statements which contain semicolons of their own into the -current line. They are run into the current line where you placed them -until you edit the statement again. REDUCE will understand the set of -statements if the syntax is correct. - -If you leave out needed closing brackets when you exit the editor, a message -is printed allowing you to redo the edit (you can edit the previous line -number and return to where you were). If you leave out a closing -double-quotation mark, an error message is printed, and the editing must be -redone from the original version; the edited version has been destroyed. -Most syntax errors which you inadvertently leave in an edited statement are -caught as usual by the REDUCE parser, and you will be able to re-edit the -statement. - -When the editor processes a previous statement for your editing, escape -characters are removed. Most special characters that you may use in -identifiers are printed in legal fashion, prefixed by the exclamation -point. Be sure to treat the special character and its escape as a pair in -your editing. The characters \name{( ) # ; ' `} are different. Since -they have special meaning in Lisp, they are double-escaped in the editor. -It is unwise to use these characters inside identifiers anyway, due to the -probability of confusion. - -If you see a Lisp error message during editing, the edit has been aborted. -Enter a semicolon and you will see a new line prompt. - -Since the editor has no dependence on any window system, it can be used if you -are running REDUCE without windows. -\end{Comments} -\end{Command} - - -\begin{Command}{EDITDEF} - -The interactive editor \nameref{ed} may be used to edit a user-defined -procedure that has not been compiled. -\begin{Syntax} -\name{editdef}(\name{identifier}) -\end{Syntax} -where \name{identifier} is the name of the procedure. When \name{editdef} -is invoked, the procedure definition will be displayed in editing mode, -and may then be edited and redefined on exiting from the editor using -standard \nameref{ed} commands. - -\end{Command} - - +\section{Outmoded Operations} + +\begin{Command}{ED} +The \name{ed} command invokes a simple line editor for REDUCE input +statements. + +\begin{Syntax} +\name{ed} \meta{integer} or \name{ed} +\end{Syntax} + +\name{ed} called with no argument edits the last input statement. If +\meta{integer} is greater than or equal to the current line number, an error +message is printed. Reenter a proper \name{ed} command or return to the +top level with a semicolon. + +The editor formats REDUCE's version of the desired input statement, +dividing it into lines at semicolons and dollar signs. The statement is +printed at the beginning of the edit session. The editor works on one +line at a time, and has a pointer (shown by \name{^}) to the current +character of that line. When the session begins, the pointer is at the +left hand side of the first line. The editing prompt is \name{>}. + +The following commands are available. They may be entered in either upper +or lower case. All commands are activated by the carriage return, which +also prints out the current line after changes. Several commands can be +placed on a single line, except that commands terminated by an \key{ESC} +must be the last command before the carriage return. + +\begin{itemize} +\item[b] +Move pointer to beginning of current line. + +\item[d\meta{digit}] +Delete current character and next (digit-1) characters. An error message +is printed if anything other than a single digit follows d. If there are +fewer than \meta{digit} characters left on the line, all but the final +dollar sign or semicolon is removed. To delete a line completely, use the +k command. + +\item[e] +End the current session, causing the edited expression to be reparsed by +REDUCE. + +\item[f\meta{char}] +Find the next occurrence of the character \meta{char} to the right of the +pointer on the current line and move the pointer to it. If the character is +not found, an error message is printed and the pointer remains in its +original position. Other lines are not searched. The f command is not +case-sensitive. + +\item[i\meta{string}\key{ESC}] +Insert \meta{string} in front of pointer. The \key{ESC} key is your +delimiter for the input string. No other command may follow this one on +the same line. + +\item[k] +Kill rest of the current line, including the semicolon or dollar sign +terminator. If there are characters remaining on the current line, and it +is the last line of the input statement, a semicolon is added to the line +as a terminator for REDUCE. If the current line is now empty, one of the +following actions is performed: If there is a following line, it becomes +the current line and the pointer is placed at its first character. If the +current line was the final line of the statement, and there is a previous +line, the previous line becomes the current line. If the current line was +the only line of the statement, and it is empty, a single semicolon is +inserted for REDUCE to parse. + +\item[l] +Finish editing this line and move to the last previous line. An error message +is printed if there is no previous line. + +\item[n] +Finish editing this line and move to the next line. An error message is +printed if there is no next line. + +\item[p] +Print out all the lines of the statement. Then a dotted line is printed, and +the current line is reprinted, with the pointer under it. + +\item[q] +Quit the editing session without saving the changes. If a semicolon is +entered after q, a new line prompt is given, otherwise REDUCE prompts you +for another command. Whatever you type in to the prompt appearing after +the q is entered is stored as the input for the line number in which you +called the edit. Thus if you enter a semicolon, neither \nameref{input} +\name{ed} will find anything under the current number. + +\item[r\meta{char}] +Replace the character at the pointer by \meta{char}. + +\item[s\meta{string}\key{ESC}] +Search for the first occurrence of \meta{string} to the right of the +pointer on the current line and move the pointer to its first character. +The \key{ESC} key is your delimiter for the input string. The s function +does not search other lines of the statement. If the string is not found, +an error message is printed and the pointer remains in its original +position. The s command is not case-sensitive. No other command may +follow this one on the same line. + +\item[x \meta{or space}] +Move the pointer one character to the right. If the pointer is already at +the end of the line, an error message is printed. + +\item[- \meta{(minus)}] +Move the pointer one character to the left. If the pointer is already at the +beginning of the line, an error message is printed. + +\item[?] +Display the Help menu, showing the commands and their actions. +\end{itemize} + +\begin{Examples} +\explanation{(Line numbers are shown in the following examples)} \\ +2: >>x**2 + y; \\ +X^{2} + Y \\ +3: >>ed 2; \\ + X**2 + Y; \\ + ^ \\ +For help, type '?' \\ +?- (Enter three spaces and \key{Return}) \\ + X**2 + Y; \\ + ^ \\ +?- r5 \\ + X**5 + Y; \\ + ^ \\ +?- fY \\ + X**5 + Y; \\ + ^ \\ +?- iabc (Terminate with \key{ESC} and \key{Return}) \\ + X**5 + abcY; \\ + ^ \\ +?- ---- \\ + X**5 + abcY; \\ + ^ \\ +?- fbd2 \\ + X**5 + aY; \\ + ^ \\ +?- b \\ + X**5 + aY; \\ + ^ \\ +?- e \\ +AY + X^{5} \\ +4: >>procedure dumb(a); \\ +>>write a; \\ +DUMB \\ +5: >>dumb(17); \\ +17 \\ +6: >>ed 4; \\ + PROCEDURE DUMB (A); \\ + ^ \\ +WRITE A; \\ +?- fArBn \\ + WRITE A; \\ + ^ \\ +?- ibegin scalar a; a := b + 10; (Type a space, \key{ESC}, and \key{Return}) \\ + begin scalar a; a := b + 10; WRITE A; \\ +?- f;i end \key{ESC}, \key{Return} \\ + begin scalar b; b := a + 10; WRITE A end; \\ + ^ \\ +?- p \\ + PROCEDURE DUMB (B); \\ + begin scalar b; b := a + 10; WRITE A end; \\ + - - - - - - - - - - \\ + begin scalar b; b := a + 10; WRITE A end; \\ + ^ \\ +?- e \\ +DUMB \\ +7: >>dumb(17); \\ +27 \\ +8: >> & +\end{Examples} + +\begin{Comments} +Note that REDUCE reparsed the procedure \name{dumb} and updated the +definition. + +Since REDUCE divides the expression to be edited into lines at semicolons or +dollar sign terminators, some lines may occupy more than one line of screen +space. If the pointer is directly beneath the last line of text, it +refers to the top line of text. If there is a blank line between the +last line of text and the pointer, it refers to the second line +of text, and likewise for cases of greater than two lines of text. In other +words, the entire REDUCE statement up to the next terminator is printed, even +if it runs to several lines, then the pointer line is printed. + +You can insert new statements which contain semicolons of their own into the +current line. They are run into the current line where you placed them +until you edit the statement again. REDUCE will understand the set of +statements if the syntax is correct. + +If you leave out needed closing brackets when you exit the editor, a message +is printed allowing you to redo the edit (you can edit the previous line +number and return to where you were). If you leave out a closing +double-quotation mark, an error message is printed, and the editing must be +redone from the original version; the edited version has been destroyed. +Most syntax errors which you inadvertently leave in an edited statement are +caught as usual by the REDUCE parser, and you will be able to re-edit the +statement. + +When the editor processes a previous statement for your editing, escape +characters are removed. Most special characters that you may use in +identifiers are printed in legal fashion, prefixed by the exclamation +point. Be sure to treat the special character and its escape as a pair in +your editing. The characters \name{( ) # ; ' `} are different. Since +they have special meaning in Lisp, they are double-escaped in the editor. +It is unwise to use these characters inside identifiers anyway, due to the +probability of confusion. + +If you see a Lisp error message during editing, the edit has been aborted. +Enter a semicolon and you will see a new line prompt. + +Since the editor has no dependence on any window system, it can be used if you +are running REDUCE without windows. +\end{Comments} +\end{Command} + + +\begin{Command}{EDITDEF} + +The interactive editor \nameref{ed} may be used to edit a user-defined +procedure that has not been compiled. +\begin{Syntax} +\name{editdef}(\name{identifier}) +\end{Syntax} +where \name{identifier} is the name of the procedure. When \name{editdef} +is invoked, the procedure definition will be displayed in editing mode, +and may then be edited and redefined on exiting from the editor using +standard \nameref{ed} commands. + +\end{Command} + + Index: r36/help/pk-gplot.tex ================================================================== --- r36/help/pk-gplot.tex +++ r36/help/pk-gplot.tex @@ -1,353 +1,353 @@ -\section{Gnuplot package} - -\begin{Introduction}{GNUPLOT and REDUCE} - -The GNUPLOT system provides easy to use graphics output -for curves or surfaces which are defined by -formulas and/or data sets. GNUPLOT supports -a great variety of output devices -such as X-windows, VGA screen, postscript, picTeX. -The REDUCE GNUPLOT package lets one use the GNUPLOT -graphical output directly from inside REDUCE, either for -the interactive display of curves/surfaces or for the production -of pictures on paper. - -Note that this package may not be supported on all system -platforms. - -For a detailed description you should read the GNUPLOT -system documentation, available together with the GNUPLOT -installation material from several servers by anonymous FTP. - -The REDUCE developers thank the GNUPLOT people for their permission -to distribute GNUPLOT together with REDUCE. -\end{Introduction} - -\begin{Concept}{Axes names} -Inside REDUCE the choice of variable names for a graph is completely -free. For referring to the GNUPLOT axes the names -X and Y for 2 dimensions, X,Y and Z for 3 dimensions are used -in the usual schoolbook sense independent from the variables of -the REDUCE expression. - -\begin{Examples} - plot(w=sin(a),a=(0 .. 10),xlabel="angle",ylabel="sine"); -\end{Examples} - -\end{Concept} - -\begin{Type}{Pointset} -\index{plot} -A curve can be give as set of precomputed points (a polygon) -in 2 or 3 dimensions. Such a point set is a \nameref{list} -of points, where each point is a \nameref{list} 2 (or 3) -numbers. These numbers are interpreted as \name{(x,y)} -(or \name{x,y,z}) coordinates. All points of one set must have -the same dimension. - -\begin{Examples} - for i:=2:10 collect{i,factorial(i)}; - -\end{Examples} - -Also a surface in 3d can be given by precomputed points, -but only on a logically orthogonal mesh: the surface is defined -by a list of curves (in 3d) which must have a uniform length. -GNUPLOT then will draw an orthogonal mesh by first drawing the -given lines, and second connecting the 1st point of the 1st curve -with the 1st point of the 2nd curve, that one with the 1st point -of the 3rd curve and so on for all curves and for all indexes. - - -\end{Type} - - -\begin{Command}{PLOT} -\index{graphics}\index{plot} -The command \name{plot} is the main entry for drawing a -picture from inside REDUCE. - -\begin{Syntax} -\name{plot}\(\meta{spec},\meta{spec},...\) -\end{Syntax} - -where \meta{spec} is a \meta{function}, a \meta{range} or an \meta{option}. - -\meta{function}: - -- an expression depending -on one unknown (e.g. \name{sin(x)} or two unknowns (e.g. -\name{sin(x+y)}, - -- an equation with a function on its right-hand -side and a single name on its left-hand side (e.g. -\name{z=sin(x+y)} where the name on the left-hand side specifies -the dependent variable. - -- a list of functions: -if in 2 dimensions the picture should have more than one -curve the expressions can be given as list (e.g. \name{\{sin(x),cos(x)\}}). - -- an equation with zero left or right hand side describing - an implicit curve in two dimensions (e.g. \name{x**3+x*y**3-9x=0}). - -- a point set: the graph can be given -as point set in 2 dimensions or a \nameref{pointset} or pointset list -in 3 dimensions. - -\meta{range}: - -Each dependent and independent variable can be limited -to an interval by an equation where the left-hand side specifies -the variable and the right-hand side defines the \nameref{interval}, -e.g. \name{x=( -3 .. 5)}. - -If omitted the independent variables -range from -10 to 10 and the dependent variable is limited only -by the precision of the IEEE floating point arithmetic. - -\meta{option}: - -An option can be an equation equating a variable -and a value (in general a string), or a keyword(GNUPLOT switch). -These have to be included in the gnuplot command arguments directly. -Strings have to be enclosed in -string quotes (see \nameref{string}). Available options are: - -\nameref{title}: assign a heading (default: empty) - -\nameref{xlabel}: set label for the x axis - -\nameref{ylabel}: set label for the y axis - -\nameref{zlabel}: set label for the z axis - -\nameref{terminal}: select an output device - -\nameref{size}: rescale the picture - -\nameref{view}: set a viewpoint - -\name{(no)}\nameref{contour}: 3d: add contour lines - -\name{(no)}\nameref{surface}: 3d: draw surface (default: yes) - -\name{(no)}\nameref{hidden3d}: 3d: remove hidden lines (default: no) - -\begin{Examples} -plot(cos x);\\ -plot(s=sin phi,phi=(-3 .. 3));\\ -plot(sin phi,cos phi,phi=(-3 .. 3));\\ -plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3),hidden3d);\\ -plot {{0,0},{0,1},{1,1},{0,0},{1,0},{0,1},{0.5,1.5},{1,1},{1,0}};\\ -\\ -on rounded;\\ -w:=for j:=1:200 collect {1/j*sin j,1/j*cos j,j/200}$\\ -plot w; \\ -\end{Examples} - -Additional control of the \name{plot} operation: -\nameref{plotrefine}, -\nameref{plot_xmesh}, \nameref{plot_ymesh}, \nameref{trplot}, -\nameref{plotkeep}, \nameref{show_grid}. - -\end{Command} - -\begin{Command}{PLOTRESET} -The command \name{plotreset} closes the current GNUPLOT windows. -The next call to \nameref{plot} will create a new one. \name{plotreset} -can also be used to reset the system status after technical problems. - -\begin{Syntax} -\name{plotreset}; -\end{Syntax} -\end{Command} - - -\begin{Variable}{title} -\index{plot} -\nameref{plot} option: -Assign a title to the GNUPLOT graph. - -\begin{Syntax} -\name{title} = \meta{string} -\end{Syntax} -\begin{Examples} -title="annual revenue in 1993"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{xlabel} -\index{plot} -\nameref{plot} option: -Assign a name to to the x axis (see \nameref{axes names}). - -\begin{Syntax} -\name{xlabel} = \meta{string} -\end{Syntax} -\begin{Examples} -xlabel="month"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{ylabel} -\index{plot} -\nameref{plot} option: -Assign a name to to the x axis (see \nameref{axes names}). - -\begin{Syntax} -\name{ylabel} = \meta{string} -\end{Syntax} -\begin{Examples} -ylabel="million forint"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{zlabel} -\index{plot} -\nameref{plot} option: -Assign a name to to the z axis (see \nameref{axes names}). - -\begin{Syntax} -\name{zlabel} = \meta{string} -\end{Syntax} -\begin{Examples} -zlabel="local weight"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{terminal} -\index{plot} -\nameref{plot} option: -Select a different output device. The possible values here -depend highly on the facilities installed for your GNUPLOT -software. - -\begin{Syntax} -\name{terminal} = \meta{string} -\end{Syntax} -\begin{Examples} -terminal="x11"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{size} -\index{plot} -\nameref{plot} option: -Rescale the graph (not the window!) in x and y direction. -Default is 1.0 (no rescaling). - -\begin{Syntax} -\name{size} = "\meta{sx},\meta{sy}" -\end{Syntax} -where \meta{sx},\meta{sy} are floating point number not too -far from 1.0. -\begin{Examples} -size="0.7,1"\\ -\end{Examples} -\end{Variable} - -\begin{Variable}{view} -\index{plot} -\nameref{plot} option: -Set a new viewpoint by turning the object around the x and then -around the z axis (see \nameref{axes names}). - -\begin{Syntax} -\name{view} = "\meta{sx},\meta{sz}" -\end{Syntax} -where \meta{sx},\meta{sz} are floating point number representing -angles in degrees. -\begin{Examples} -view="30,130"\\ -\end{Examples} -\end{Variable} - -\begin{Switch}{contour} -\index{plot} -\nameref{plot} option: -If \name{contour} is member of the options for a 3d \nameref{plot} -contour lines are projected to the z=0 plane -(see \nameref{axes names}). The absence of contour lines -can be selected explicitly by including \name{nocontour}. Default -is \name{nocontour}. -\end{Switch} - - -\begin{Switch}{surface} -\index{plot} -\nameref{plot} option: -If \name{surface} is member of the options for a 3d \nameref{plot} -the surface is drawn. The absence of the surface plotting -can be selected by including \name{nosurface}, e.g. if -only the \nameref{contour} should be visualized. Default is \name{surface}. -\end{Switch} - - -\begin{Switch}{hidden3d} -\index{plot} -\nameref{plot} option: -If \name{hidden3d} is member of the options for a 3d \nameref{plot} -hidden lines are removed from the picture. Otherwise a -surface is drawn as transparent object. Default is -\name{nohidden3d}. Selecting \name{hidden3d} increases the -computing time substantially. -\end{Switch} - -\begin{Switch}{PLOTKEEP} -\index{plot} -Normally all intermediate data sets are deleted after terminating -a plot session. If the switch \name{plotkeep} is set \nameref{on}, -the data sets are kept for eventual post processing independent -of REDUCE. -\end{Switch} - -\begin{Switch}{PLOTREFINE} -\index{plot} -In general \nameref{plot} tries to generate smooth pictures by evaluating -the functions at interior points until the distances are fine -enough. This can require a lot of computing time if the -single function evaluation is expensive. The refinement is -controlled by the switch \name{plotrefine} which is \nameref{on} -by default. When you turn it \nameref{off} the functions will -be evaluated only at the basic points (see \nameref{plot_xmesh}, -\nameref{plot_ymesh}). -\end{Switch} - -\begin{Variable}{plot_xmesh} -\index{plot} -The integer value of the global variable \name{plot_xmesh} -defines the number of initial function evaluations in x -direction (see \nameref{axes names}) for \nameref{plot}. For 2d graphs additional -points will be used as long as \nameref{plotrefine} is \name{on}. -For 3d graphs this number defines also the number of mesh lines -orthogonal to the x axis. -\end{Variable} - -\begin{Variable}{plot_ymesh} -\index{plot} -The integer value of the global variable \name{plot_ymesh} -defines for 3d \nameref{plot} calls the number of function evaluations in y -direction (see \nameref{axes names}) and the number of mesh lines -orthogonal to the y axis. -\end{Variable} - -\begin{Switch}{SHOW_GRID} -\index{plot} -The grid for localizing an implicitly defined curve in \nameref{plot} -consists of triangles. These are computed initially equally distributed -over the x-y plane controlled by \nameref{plot_xmesh}. The grid is -refined adaptively in several levels. The final grid can be visualized -by setting on the switch \name{show_grid}. -\end{Switch} - - -\begin{Switch}{TRPLOT} -\index{plot} -In general the interaction between REDUCE and GNUPLOT is performed -as silently as possible. However, sometimes it might be useful -to see the GNUPLOT commands generated by REDUCE, e.g. for a -postprocessing of generated data sets independent of REDUCE. -When the switch \name{trplot} is set on all GNUPLOT commands will -be printed to the standard output additionally. -\end{Switch} +\section{Gnuplot package} + +\begin{Introduction}{GNUPLOT and REDUCE} + +The GNUPLOT system provides easy to use graphics output +for curves or surfaces which are defined by +formulas and/or data sets. GNUPLOT supports +a great variety of output devices +such as X-windows, VGA screen, postscript, picTeX. +The REDUCE GNUPLOT package lets one use the GNUPLOT +graphical output directly from inside REDUCE, either for +the interactive display of curves/surfaces or for the production +of pictures on paper. + +Note that this package may not be supported on all system +platforms. + +For a detailed description you should read the GNUPLOT +system documentation, available together with the GNUPLOT +installation material from several servers by anonymous FTP. + +The REDUCE developers thank the GNUPLOT people for their permission +to distribute GNUPLOT together with REDUCE. +\end{Introduction} + +\begin{Concept}{Axes names} +Inside REDUCE the choice of variable names for a graph is completely +free. For referring to the GNUPLOT axes the names +X and Y for 2 dimensions, X,Y and Z for 3 dimensions are used +in the usual schoolbook sense independent from the variables of +the REDUCE expression. + +\begin{Examples} + plot(w=sin(a),a=(0 .. 10),xlabel="angle",ylabel="sine"); +\end{Examples} + +\end{Concept} + +\begin{Type}{Pointset} +\index{plot} +A curve can be give as set of precomputed points (a polygon) +in 2 or 3 dimensions. Such a point set is a \nameref{list} +of points, where each point is a \nameref{list} 2 (or 3) +numbers. These numbers are interpreted as \name{(x,y)} +(or \name{x,y,z}) coordinates. All points of one set must have +the same dimension. + +\begin{Examples} + for i:=2:10 collect{i,factorial(i)}; + +\end{Examples} + +Also a surface in 3d can be given by precomputed points, +but only on a logically orthogonal mesh: the surface is defined +by a list of curves (in 3d) which must have a uniform length. +GNUPLOT then will draw an orthogonal mesh by first drawing the +given lines, and second connecting the 1st point of the 1st curve +with the 1st point of the 2nd curve, that one with the 1st point +of the 3rd curve and so on for all curves and for all indexes. + + +\end{Type} + + +\begin{Command}{PLOT} +\index{graphics}\index{plot} +The command \name{plot} is the main entry for drawing a +picture from inside REDUCE. + +\begin{Syntax} +\name{plot}\(\meta{spec},\meta{spec},...\) +\end{Syntax} + +where \meta{spec} is a \meta{function}, a \meta{range} or an \meta{option}. + +\meta{function}: + +- an expression depending +on one unknown (e.g. \name{sin(x)} or two unknowns (e.g. +\name{sin(x+y)}, + +- an equation with a function on its right-hand +side and a single name on its left-hand side (e.g. +\name{z=sin(x+y)} where the name on the left-hand side specifies +the dependent variable. + +- a list of functions: +if in 2 dimensions the picture should have more than one +curve the expressions can be given as list (e.g. \name{\{sin(x),cos(x)\}}). + +- an equation with zero left or right hand side describing + an implicit curve in two dimensions (e.g. \name{x**3+x*y**3-9x=0}). + +- a point set: the graph can be given +as point set in 2 dimensions or a \nameref{pointset} or pointset list +in 3 dimensions. + +\meta{range}: + +Each dependent and independent variable can be limited +to an interval by an equation where the left-hand side specifies +the variable and the right-hand side defines the \nameref{interval}, +e.g. \name{x=( -3 .. 5)}. + +If omitted the independent variables +range from -10 to 10 and the dependent variable is limited only +by the precision of the IEEE floating point arithmetic. + +\meta{option}: + +An option can be an equation equating a variable +and a value (in general a string), or a keyword(GNUPLOT switch). +These have to be included in the gnuplot command arguments directly. +Strings have to be enclosed in +string quotes (see \nameref{string}). Available options are: + +\nameref{title}: assign a heading (default: empty) + +\nameref{xlabel}: set label for the x axis + +\nameref{ylabel}: set label for the y axis + +\nameref{zlabel}: set label for the z axis + +\nameref{terminal}: select an output device + +\nameref{size}: rescale the picture + +\nameref{view}: set a viewpoint + +\name{(no)}\nameref{contour}: 3d: add contour lines + +\name{(no)}\nameref{surface}: 3d: draw surface (default: yes) + +\name{(no)}\nameref{hidden3d}: 3d: remove hidden lines (default: no) + +\begin{Examples} +plot(cos x);\\ +plot(s=sin phi,phi=(-3 .. 3));\\ +plot(sin phi,cos phi,phi=(-3 .. 3));\\ +plot (cos sqrt(x**2 + y**2),x=(-3 .. 3),y=(-3 .. 3),hidden3d);\\ +plot {{0,0},{0,1},{1,1},{0,0},{1,0},{0,1},{0.5,1.5},{1,1},{1,0}};\\ +\\ +on rounded;\\ +w:=for j:=1:200 collect {1/j*sin j,1/j*cos j,j/200}$\\ +plot w; \\ +\end{Examples} + +Additional control of the \name{plot} operation: +\nameref{plotrefine}, +\nameref{plot_xmesh}, \nameref{plot_ymesh}, \nameref{trplot}, +\nameref{plotkeep}, \nameref{show_grid}. + +\end{Command} + +\begin{Command}{PLOTRESET} +The command \name{plotreset} closes the current GNUPLOT windows. +The next call to \nameref{plot} will create a new one. \name{plotreset} +can also be used to reset the system status after technical problems. + +\begin{Syntax} +\name{plotreset}; +\end{Syntax} +\end{Command} + + +\begin{Variable}{title} +\index{plot} +\nameref{plot} option: +Assign a title to the GNUPLOT graph. + +\begin{Syntax} +\name{title} = \meta{string} +\end{Syntax} +\begin{Examples} +title="annual revenue in 1993"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{xlabel} +\index{plot} +\nameref{plot} option: +Assign a name to to the x axis (see \nameref{axes names}). + +\begin{Syntax} +\name{xlabel} = \meta{string} +\end{Syntax} +\begin{Examples} +xlabel="month"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{ylabel} +\index{plot} +\nameref{plot} option: +Assign a name to to the x axis (see \nameref{axes names}). + +\begin{Syntax} +\name{ylabel} = \meta{string} +\end{Syntax} +\begin{Examples} +ylabel="million forint"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{zlabel} +\index{plot} +\nameref{plot} option: +Assign a name to to the z axis (see \nameref{axes names}). + +\begin{Syntax} +\name{zlabel} = \meta{string} +\end{Syntax} +\begin{Examples} +zlabel="local weight"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{terminal} +\index{plot} +\nameref{plot} option: +Select a different output device. The possible values here +depend highly on the facilities installed for your GNUPLOT +software. + +\begin{Syntax} +\name{terminal} = \meta{string} +\end{Syntax} +\begin{Examples} +terminal="x11"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{size} +\index{plot} +\nameref{plot} option: +Rescale the graph (not the window!) in x and y direction. +Default is 1.0 (no rescaling). + +\begin{Syntax} +\name{size} = "\meta{sx},\meta{sy}" +\end{Syntax} +where \meta{sx},\meta{sy} are floating point number not too +far from 1.0. +\begin{Examples} +size="0.7,1"\\ +\end{Examples} +\end{Variable} + +\begin{Variable}{view} +\index{plot} +\nameref{plot} option: +Set a new viewpoint by turning the object around the x and then +around the z axis (see \nameref{axes names}). + +\begin{Syntax} +\name{view} = "\meta{sx},\meta{sz}" +\end{Syntax} +where \meta{sx},\meta{sz} are floating point number representing +angles in degrees. +\begin{Examples} +view="30,130"\\ +\end{Examples} +\end{Variable} + +\begin{Switch}{contour} +\index{plot} +\nameref{plot} option: +If \name{contour} is member of the options for a 3d \nameref{plot} +contour lines are projected to the z=0 plane +(see \nameref{axes names}). The absence of contour lines +can be selected explicitly by including \name{nocontour}. Default +is \name{nocontour}. +\end{Switch} + + +\begin{Switch}{surface} +\index{plot} +\nameref{plot} option: +If \name{surface} is member of the options for a 3d \nameref{plot} +the surface is drawn. The absence of the surface plotting +can be selected by including \name{nosurface}, e.g. if +only the \nameref{contour} should be visualized. Default is \name{surface}. +\end{Switch} + + +\begin{Switch}{hidden3d} +\index{plot} +\nameref{plot} option: +If \name{hidden3d} is member of the options for a 3d \nameref{plot} +hidden lines are removed from the picture. Otherwise a +surface is drawn as transparent object. Default is +\name{nohidden3d}. Selecting \name{hidden3d} increases the +computing time substantially. +\end{Switch} + +\begin{Switch}{PLOTKEEP} +\index{plot} +Normally all intermediate data sets are deleted after terminating +a plot session. If the switch \name{plotkeep} is set \nameref{on}, +the data sets are kept for eventual post processing independent +of REDUCE. +\end{Switch} + +\begin{Switch}{PLOTREFINE} +\index{plot} +In general \nameref{plot} tries to generate smooth pictures by evaluating +the functions at interior points until the distances are fine +enough. This can require a lot of computing time if the +single function evaluation is expensive. The refinement is +controlled by the switch \name{plotrefine} which is \nameref{on} +by default. When you turn it \nameref{off} the functions will +be evaluated only at the basic points (see \nameref{plot_xmesh}, +\nameref{plot_ymesh}). +\end{Switch} + +\begin{Variable}{plot_xmesh} +\index{plot} +The integer value of the global variable \name{plot_xmesh} +defines the number of initial function evaluations in x +direction (see \nameref{axes names}) for \nameref{plot}. For 2d graphs additional +points will be used as long as \nameref{plotrefine} is \name{on}. +For 3d graphs this number defines also the number of mesh lines +orthogonal to the x axis. +\end{Variable} + +\begin{Variable}{plot_ymesh} +\index{plot} +The integer value of the global variable \name{plot_ymesh} +defines for 3d \nameref{plot} calls the number of function evaluations in y +direction (see \nameref{axes names}) and the number of mesh lines +orthogonal to the y axis. +\end{Variable} + +\begin{Switch}{SHOW_GRID} +\index{plot} +The grid for localizing an implicitly defined curve in \nameref{plot} +consists of triangles. These are computed initially equally distributed +over the x-y plane controlled by \nameref{plot_xmesh}. The grid is +refined adaptively in several levels. The final grid can be visualized +by setting on the switch \name{show_grid}. +\end{Switch} + + +\begin{Switch}{TRPLOT} +\index{plot} +In general the interaction between REDUCE and GNUPLOT is performed +as silently as possible. However, sometimes it might be useful +to see the GNUPLOT commands generated by REDUCE, e.g. for a +postprocessing of generated data sets independent of REDUCE. +When the switch \name{trplot} is set on all GNUPLOT commands will +be printed to the standard output additionally. +\end{Switch} Index: r36/help/pk-groeb.tex ================================================================== --- r36/help/pk-groeb.tex +++ r36/help/pk-groeb.tex @@ -1,890 +1,890 @@ -\section{Groebner package} -\begin{Introduction}{Groebner bases} -The GROEBNER package calculates \nameindex{Groebner bases} using the -\nameindex{Buchberger algorithm} and provides related algorithms -for arithmetic with ideal bases, such as ideal quotients, -Hilbert polynomials (\nameindex{Hollmann algorithm}), -basis conversion ( -\nameindex{Faugere-Gianni-Lazard-Mora algorithm}), independent -variable set (\nameindex{Kredel-Weispfenning algorithm}). - - - -Some routines of the Groebner package are used by \nameref{solve} - in -that context the package is loaded automatically. However, if you -want to use the package by explicit calls you must load it by -\begin{verbatim} - load_package groebner; -\end{verbatim} - -For the common parameter setting of most operators in this package -see \nameref{ideal parameters}. -\end{Introduction} - - - -\begin{Concept}{Ideal Parameters} -\index{polynomial} -Most operators of the \name{Groebner} package compute expressions in a -polynomial ring which given as \meta{R}[\meta{var},\meta{var},...] where -\meta{R} is the current REDUCE coefficient domain. All algebraically -exact domains of REDUCE are supported. The package can operate over rings -and fields. The operation mode is distinguished automatically. In -general the ring mode is a bit faster than the field mode. The factoring -variant can be applied only over domains which allow you factoring of -multivariate polynomials. - -The variable sequence \meta{var} is either declared explicitly as argument -in form of a \nameref{list} in \nameref{torder}, or it is extracted -automatically from the expressions. In the second case the current REDUCE -system order is used (see \nameref{korder}) for arranging the variables. -If some kernels should play the role of formal parameters (the ground -domain \meta{R} then is the polynomial ring over these), the variable -sequences must be given explicitly. - -All REDUCE \nameref{kernel}s can be used as variables. But please note, -that all variables are considered as independent. E.g. when using -\name{sin(a)} and \name{cos(a)} as variables, the basic relation -\name{sin(a)^2+cos(a)^2-1=0} must be explicitly added to an equation set -because the Groebner operators don't include such knowledge automatically. - -The terms (monomials) in polynomials are arranged according to the current -\nameref{term order}. Note that the algebraic properties of the computed -results only are valid as long as neither the ordering nor the variable -sequence changes. - -The input expressions \meta{exp} can be polynomials \meta{p}, rational -functions \meta{n}/\meta{d} or equations \meta{lh}=\meta{rh} built from -polynomials or rational functions. Apart from the \name{tracing} -algorithms \nameref{groebnert} and \nameref{preducet}, where the equations -have a specific meaning, equations are converted to simple expressions by -taking the difference of the left-hand and right-hand sides -\meta{lh}-\meta{rh}=>\meta{p}. Rational functions are converted to -polynomials by converting the expression to a common denominator form -first, and then using the numerator only \meta{n}=>\meta{p}. So eventual -zeros of the denominators are ignored. - -A basis on input or output of an algorithm is coded as \nameref{list} of -expressions \{\meta{exp},\meta{exp},...\} . \end{Concept} - -%----------------------------------------------------------------- -\subsection{Term order} -%----------------------------------------------------------------- -\begin{Introduction}{Term order} -\index{distributive polynomials} -For all \name{Groebner} operations the polynomials are -represented in distributive form: a sum of terms (monomials). -The terms are ordered corresponding to the actual \name{term order} -which is set by the \nameref{torder} operator, and to the -actual variable sequence which is either given as explicit -parameter or by the system \nameref{kernel} order. -\end{Introduction} - -\begin{Operator}{TORDER} -The operator \name{torder} sets the actual variable sequence and term order. - -1. simple term order: -\begin{Syntax} - \name{torder}\(\meta{vl}, \meta{m}\) -\end{Syntax} - -where \meta{vl} is a \nameref{list} of variables (\nameref{kernel}s) and -\meta{m} is the name of a simple \nameref{term order} mode -\ref{lex term order}, \ref{gradlex term order}, -\ref{revgradlex term order} or another implemented parameterless mode. - -2. stepped term order: -\begin{Syntax} - - \name{torder} \(\meta{vl},\meta{m},\meta{n}\) - -\end{Syntax} - -where \meta{m} is the name of a two step term order, one of -\nameref{gradlexgradlex term order}, \nameref{gradlexrevgradlex term order}, -\nameref{lexgradlex term order} or \nameref{lexrevgradlex term order}, and -\meta{n} is a positive integer. - -3. weighted term order -\begin{Syntax} - \name{torder} \(\meta{vl}, \name{weighted}, \meta{n},\meta{n},...\); -\end{Syntax} - -where the \meta{n} are positive integers, see \nameref{weighted term order}. - -4. matrix term order -\begin{Syntax} - \name{torder} \(\meta{vl}, \name{matrix}, \meta{m}\); -\end{Syntax} - -where \meta{m} is a matrix with integer elements, see -\nameref{torder_compile}. - -5. compiled term order -\begin{Syntax} - \name{torder} \(\meta{vl}, \name{co}\); -\end{Syntax} - -where \meta{co} is the name of a routine generated by -\nameref{torder_compile}. - -\name{torder} sets the variable sequence and the term order mode. If the -an empty list is used as variable sequence, the automatic variable extraction -is activated. The defaults are the empty variable list an the -\nameref{lex term order}. -The previous setting is returned as a list. - -Alternatively to the above syntax the arguments of \name{torder} may be -collected in a \nameref{list} and passed as one argument to -\name{torder}. - -\end{Operator} -%------------------------------------------------------------ -\begin{Operator}{torder_compile} -\index{term order} -A matrix can be converted into -a compilable LISP program for faster execution by using -\begin{Syntax} - \name{torder\_compile}\(\meta{name},\meta{mat}\) -\end{Syntax} -where \meta{name} is an identifier for the new term order and \meta{mat} -is an integer matrix to be used as \nameref{matrix term order}. Afterwards -the term order can be activated by using \meta{name} in a \nameref{torder} -expression. The resulting program is compiled if the switch \nameref{comp} -is on, or if the \name{torder\_compile} expression is part of a compiled -module. -\end{Operator} -%------------------------------------------------------------ -\begin{Concept}{lex term order} -\index{term order}\index{variable elimination} -The terms are ordered lexicographically: two terms t1 t2 -are compared for their degrees -along the fixed variable sequence: t1 is higher than t2 -if the first different degree is higher in t1. -This order has the \name{elimination property} -for \name{groebner basis} calculations. -If the ideal has a univariate polynomial in the last -variable the groebner basis will contain -such polynomial. \name{Lex} is best -suited for solving of polynomial equation systems. - -\end{Concept} - -%------------------------------------------------------------ -\begin{Concept}{gradlex term order} -\index{term order} -The terms are ordered first with their total -degree, and if the total degree is identical -the comparison is \nameref{lex term order}. -With \name{groebner} basis calculations this term order -produces polynomials of lowest degree. -\end{Concept} - -%------------------------------------------------------------ -\begin{Concept}{revgradlex term order} -\index{term order} -The terms are ordered first with their total -degree (degree sum), and if the total degree is identical -the comparison is the inverse of \nameref{lex term order}. -With \nameref{groebner} and \nameref{groebnerf} -calculations this term order -is similar to \nameref{gradlex term order}; it is known -as most efficient ordering with respect to computing time. -\end{Concept} - -%------------------------------------------------------------ -\begin{Concept}{gradlexgradlex term order} -\index{term order} -The terms are separated into two groups where the -second parameter of the \nameref{torder} call determines -the length of the first group. For a comparison first -the total degrees of both variable groups are compared. -If both are equal -\nameref{gradlex term order} comparison is applied to the first -group, and if that does not decide \nameref{gradlex term order} -is applied for the second group. This order has the elimination -property for the variable groups. It can be used e.g. for -separating variables from parameters. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{gradlexrevgradlex term order} -\index{term order} -Similar to \nameref{gradlexgradlex term order}, but using -\nameref{revgradlex term order} for the second group. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{lexgradlex term order} -\index{term order} -Similar to \nameref{gradlexgradlex term order}, but using -\nameref{lex term order} for the first group. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{lexrevgradlex term order} -\index{term order} -Similar to \nameref{gradlexgradlex term order}, but using -\nameref{lex term order} for the first group -\nameref{revgradlex term order} for the second group. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{weighted term order} -\index{term order} -establishes a graduated ordering -similar to \nameref{gradlex term order}, where the exponents first are -multiplied by the given weights. If there are less weight values than -variables, the weight list is extended by ones. If the weighted degree -comparison is not decidable, the -\nameref{lex term order} is used. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{graded term order} -\index{term order} -establishes a cascaded term ordering: first a graduated ordering -similar to \nameref{gradlex term order} is used, where the exponents first are -multiplied by the given weights. If there are less weight values than -variables, the weight list is extended by ones. If the weighted degree -comparison is not decidable, the term ordering described in the following -parameters of the \nameref{torder} command is used. -\end{Concept} -%------------------------------------------------------------ -\begin{Concept}{matrix term order} -\index{term order} -Any arbitrary term order mode can be installed by a matrix with -integer elements where the row length corresponds to the variable -number. The matrix must have at least as many rows as columns. -It must have full rank, and the top nonzero element of each column -must be positive. - -The matrix \name{term order mode} -defines a term order where the exponent vectors of the monomials are -first multiplied by the matrix and the resulting vectors are compared -lexicographically. - -If the switch \nameref{comp} is on, the matrix is converted into -a compiled LISP program for faster execution. A matrix can also be -compiled explicitly, see \nameref{torder_compile}. -\end{Concept} -%--------------------------------------------------------------- -%------------------------------------------------------------ -\subsection{Basic Groebner operators} -%------------------------------------------------------------- -\begin{Operator}{GVARS} -\begin{Syntax} - - \name{gvars}\(\{\meta{exp},\meta{exp},... \}\) - -\end{Syntax} - where \meta{exp} are expressions or \nameref{equation}s. - -\name{gvars} extracts from the expressions the \nameref{kernel}\name{s} -which can -play the role of variables for a \nameref{groebner} or \nameref{groebnerf} -calculation. -\end{Operator} - -%--------------------------------------------------------------- - -\begin{Operator}{GROEBNER} -\index{Buchberger algorithm} -\begin{Syntax} - - \name{groebner}\(\{\name{exp}, ...\}\) - -\end{Syntax} -where \{\name{exp}, ... \} is a list of -expressions or equations. - - -The operator \name{groebner} implements the Buchberger algorithm -for computing Groebner bases for a given set of -expressions with respect to the given set of variables in the order -given. As a side effect, the sequence of variables is stored as a REDUCE list -in the shared variable \nameref{gvarslast} - this is important in cases -where the algorithm rearranges the variable sequence because \nameref{groebopt} -is \name{on}. - -\begin{Examples} - groebner({x**2+y**2-1,x-y}) & \{X - Y,2*Y**2 -1\} -\end{Examples} -\begin{Related} -\item[ \nameref{groebnerf} operator] -\item[ \nameref{gvarslast} variable] -\item[ \nameref{groebopt} switch] -\item[ \nameref{groebprereduce} switch] -\item[ \nameref{groebfullreduction} switch] -\item[ \nameref{gltbasis} switch] -\item[ \nameref{gltb} variable] -\item[ \nameref{glterms} variable] -\item[ \nameref{groebstat} switch] -\item[ \nameref{trgroeb} switch] -\item[ \nameref{trgroebs} switch] -\item[ \nameref{groebprot} switch] -\item[ \nameref{groebprotfile} variable] -\item[ \nameref{groebnert} operator] -\end{Related} -\end{Operator} - -%------------------------------------------------------- - -\begin{Switch}{groebopt} -If \name{groebopt} is set ON, the sequence of variables is optimized -with respect to execution speed of \name{groebner} calculations; -note that the final list of variables is available in \nameref{gvarslast}. -By default \name{groebopt} is off, conserving the original variable -sequence. - -An explicitly declared dependency using the \nameref{depend} -declaration supersedes the variable optimization. -\begin{Examples} - - depend a, x, y; - -\end{Examples} -guarantees that a will be placed in front of x and y. -\end{Switch} - - -%------------------------------------------------------- - -\begin{Variable}{gvarslast} -After a \nameref{groebner} or \nameref{groebnerf} calculation -the actual variable sequence is stored in the variable -\name{gvarslast}. If \nameref{groebopt} is \name{on} -\name{gvarslast} shows the variable sequence after reordering. -\end{Variable} - -%-------------------------------------------------------------- - -\begin{Switch}{groebprereduce} -If \name{groebprereduce} set ON, \nameref{groebner} -and \nameref{groebnerf} try to simplify the -input expressions: if the head term of an input expression is a -multiple of the head term of another expression, it can be reduced; -these reductions are done cyclicly as long as possible in order to -shorten the main part of the algorithm. - -By default \name{groebprereduce} is off. -\end{Switch} - -%--------------------------------------------------------------- - -\begin{Switch}{groebfullreduction} -If \name{groebfullreduction} set off, the polynomial reduction steps during -\nameref{groebner} and \nameref{groebnerf} are limited to the pure head -term reduction; subsequent terms are reduced otherwise. - -By default \name{groebfullreduction} is on. -\end{Switch} - -%---------------------------------------------------------------- - -\begin{Switch}{gltbasis} -If \name{gltbasis} set on, the leading terms of the result basis -of a \nameref{groebner} or \nameref{groebnerf} calculation are -extracted. They are collected as a basis of monomials, which is -available as value of the global variable \nameref{gltb}. -\end{Switch} -%------------------------------------------------------------------ -\begin{Variable}{gltb} -See \nameref{gltbasis} -\end{Variable} -%------------------------------------------------------------------ - -\begin{Variable}{glterms} -If the expressions in a \nameref{groebner} or \nameref{groebnerf} -call contain parameters (symbols -which are not member of the variable list), the share variable -\name{glterms} is set to a list of expression which during the -calculation were assumed to be nonzero. The calculated bases -are valid only under the assumption that all these expressions do -not vanish. -\end{Variable} - -%----------------------------------------------------------- -\begin{Switch}{groebstat} -if \name{groebstat} is on, a summary of the -\nameref{groebner} or \nameref{groebnerf} computation is printed -at the end -including the computing time, the number of intermediate -H polynomials and the counters for the criteria hits. -\end{Switch} - -%----------------------------------------------------------- -\begin{Switch}{trgroeb} -if \name{trgroeb} is on, intermediate H polynomials are -printed during a \nameref{groebner} -or \nameref{groebnerf} calculation. -\end{Switch} - -%----------------------------------------------------------- -\begin{Switch}{trgroebs} -if \name{trgroebs} is on, intermediate H and S polynomials are -printed during a \nameref{groebner} or \nameref{groebnerf} calculation. -\end{Switch} - -%----------------------------------------------------------- -\begin{Operator}{gzerodim?} -\begin{Syntax} - - \name{gzerodim!?}\(\meta{basis}\) - -\end{Syntax} -where \meta{bas} is a Groebner basis in the current -\nameref{term order} with the actual setting -(see \nameref{ideal parameters}). - - -\name{gzerodim!?} tests whether the ideal spanned by the given basis -has dimension zero. If yes, the number of zeros is returned, -\nameref{nil} otherwise. -\end{Operator} - -%--------------------------------------------------------------- - -\begin{Operator}{gdimension} -\index{ideal dimension}\index{groebner} -\begin{Syntax} - - \name{gdimension}\(\meta{bas}\) - -\end{Syntax} -where \meta{bas} is a \nameref{groebner} basis in the current -term order (see \nameref{ideal parameters}). -\name{gdimension} computes the dimension of the ideal -spanned by the given basis and returns the dimension as an integer -number. The Kredel-Weispfenning algorithm is used: the dimension -is the length of the longest independent variable set, -see \nameref{gindependent\_sets} -\end{Operator} - - -%--------------------------------------------------------------- - -\begin{Operator}{gindependent\_sets} -\index{ideal variables}\index{ideal dimension}\index{groebner} -\index{Kredel-Weispfenning algorithm} -\begin{Syntax} - - \name{gindependent\_sets}\(\meta{bas}\) - -\end{Syntax} -where \meta{bas} is a \nameref{groebner} basis in any \name{term order} -(which must be the current \name{term order}) with the specified -variables (see \nameref{ideal parameters}). - - -\name{Gindependent_sets} computes the maximal -left independent variable sets of the ideal, that are -the variable sets which play the role of free parameters in the -current ideal basis. Each set is a list which is a subset of the -variable list. The result is a list of these sets. For an -ideal with dimension zero the list is empty. -The Kredel-Weispfenning algorithm is used. -\end{Operator} - -%-------------------------------------------------------------- - -\begin{Operator}{dd_groebner} -For a homogeneous system of polynomials under -\nameref{graded term order}, \nameref{gradlex term order}, -\nameref{revgradlex term order} -or \nameref{weighted term order} -a Groebner Base can be computed with limiting the grade -of the intermediate S polynomials: -\begin{Syntax} -\name{dd_groebner}\(\meta{d1},\meta{d2},\meta{plist}\) -\end{Syntax} -where \meta{d1} is a non negative integer and \meta{d2} is an integer -or ``infinity". A pair of polynomials is considered -only if the grade of the lcm of their head terms is between -\meta{d1} and \meta{d2}. -For the term orders \name{graded} or \name{weighted} the (first) weight -vector is used for the grade computation. Otherwise the total -degree of a term is used. -\end{Operator} - -%-------------------------------------------------------------- - - -\begin{Operator}{glexconvert} -\index{ideal variables}\index{term order} -\begin{Syntax} - -\name{glexconvert}\(\meta{bas}[,\meta{vars}][,MAXDEG=\meta{mx}] -[,NEWVARS=\meta{nv}]\) - -\end{Syntax} -where \meta{bas} is a \nameref{groebner} basis -in the current term order, \meta{mx} (optional) is a positive -integer and \meta{nvl} (optional) is a list of variables -(see \nameref{ideal parameters}). - - -The operator \name{glexconvert} converts the basis -of a zero-dimensional ideal (finite number -of isolated solutions) from arbitrary ordering into a basis under -\nameref{lex term order}. - - -The parameter \meta{newvars} defines the new variable sequence. -If omitted, the -original variable sequence is used. If only a subset of variables is -specified here, the partial ideal basis is evaluated. - -If \meta{newvars} is a list with one element, the minimal -\nameindex{univariate polynomial} is computed. - -\meta{maxdeg} is an upper limit for the degrees. The algorithm stops with -an error message, if this limit is reached. - -A warning occurs, if the ideal is not zero dimensional. -\begin{Comments} -During the call the \name{term order} of the input basis must -be active. -\end{Comments} -\end{Operator} - -%-------------------------------------------------------------- - -\begin{Operator}{greduce} -\begin{Syntax} - -\name{greduce}\(exp, \{exp1, exp2, \ldots , expm\}\) - -\end{Syntax} - -where exp is an expression, and \{exp1, exp2, ... , expm\} is -a list of expressions or equations. - - -\name{greduce} is functionally equivalent with a call to -\nameref{groebner} and then a call to \nameref{preduce}. -\end{Operator} - -%--------------------------------------------------------- - -\begin{Operator}{preduce} -\begin{Syntax} - - \name{preduce}\(\meta{p}, \{\meta{exp}, \ldots \}\) - -\end{Syntax} - -where \meta{p} is an expression, and \{\meta{exp}, ... \} is -a list of expressions or equations. - - -\name{preduce} computes the remainder of \name{exp} -modulo the given set of polynomials resp. equations. -This result is unique (canonical) only if the given set -is a \name{groebner} basis under the current \nameref{term order} - -see also: \nameref{preducet} operator. - -\end{Operator} - - -%------------------------------------------- - -\begin{Operator}{idealquotient} -\begin{Syntax} - - -\name{idealquotient}\(\{\meta{exp}, ...\}, \meta{d}\) - -\end{Syntax} -where \{\meta{exp},...\} is a list of -expressions or equations, \meta{d} is a single expression or equation. - - -\name{idealquotient} computes the ideal quotient: -ideal spanned by the expressions \{\meta{exp},...\} -divided by the single polynomial/expression \meta{f}. The result -is the \nameref{groebner} basis of the quotient ideal. -\end{Operator} -%------------------------------------------------------------- -\begin{Operator}{hilbertpolynomial} -\index{Hollmann algorithm} -\begin{Syntax} - - hilbertpolynomial\(\meta{bas}\) - -\end{Syntax} -where \meta{bas} is a \nameref{groebner} basis in the -current \nameref{term order}. - -The degree of the \name{Hilbert polynomial} is the -dimension of the ideal spanned by the basis. For an -ideal of dimension zero the Hilbert polynomial is a -constant which is the number of common zeros of the -ideal (including eventual multiplicities). -The \name{Hollmann algorithm} is used. -\end{Operator} - -%------------------------------------------------------------- -\subsection{Factorizing Groebner bases} -%------------------------------------------------------------- - -\begin{Operator}{groebnerf} -\begin{Syntax} - -\name{groebnerf}\(\{\meta{exp}, ...\}[,\{\},\{\meta{nz}, ... \}]\); - -\end{Syntax} -where \{\meta{exp}, ... \} is a list of expressions or -equations, and \{\meta{nz},... \} is -an optional list of polynomials to be considered as non zero -for this calculation. An empty list must be passed as second argument -if the non-zero list is specified. - - -\name{groebnerf} tries to separate polynomials into individual factors and -to branch the computation in a recursive manner (factorization tree). -The result is a list of partial Groebner bases. -Multiplicities (one factor with a higher power, the same partial basis -twice) are deleted as early as possible in order to speed up the -calculation. - -The third parameter of \name{groebnerf} declares some polynomials -nonzero. If any of these is found in a branch of the calculation -the branch is canceled. - -\begin{Bigexample} -groebnerf({ 3*x**2*y+2*x*y+y+9*x**2+5*x = 3, - 2*x**3*y-x*y-y+6*x**3-2*x**2-3*x = -3, - x**3*y+x**2*y+3*x**3+2*x**2 }, {y,x}); - - {{Y - 3,X}, - - 2 - {2*Y + 2*X - 1,2*X - 5*X - 5}} -\end{Bigexample} - -\begin{Related} -\item[ \nameref{groebresmax} variable] -\item[ \nameref{groebmonfac} variable] -\item[ \nameref{groebrestriction} variable] -\item[ \nameref{groebner} operator] -\item[ \nameref{gvarslast} variable] -\item[ \nameref{groebopt} switch] -\item[ \nameref{groebprereduce} switch] -\item[ \nameref{groebfullreduction} switch] -\item[ \nameref{gltbasis} switch] -\item[ \nameref{gltb} variable] -\item[ \nameref{glterms} variable] -\item[ \nameref{groebstat} switch] -\item[ \nameref{trgroeb} switch] -\item[ \nameref{trgroebs} switch] -\item[ \nameref{groebnert} operator] -\end{Related} - -\end{Operator} - -% ------------------------------------------------------------------ - -\begin{Variable}{groebmonfac} -The variable \name{groebmonfac} is connected to -the handling of monomial factors. A monomial factor is a product -of variable powers as a factor, e.g. x**2*y in x**3*y - -2*x**2*y**2. A monomial factor represents a solution of the type - x = 0 or y = 0 with a certain multiplicity. With -\nameref{groebnerf} the multiplicity of monomial factors is lowered -to the value of the shared variable \name{groebmonfac} -which by default is 1 (= monomial factors remain present, but their -multiplicity is brought down). With -\name{groebmonfac}:= 0 -the monomial factors are suppressed completely. -\end{Variable} - -% ---------------------------------------------------------------- -\begin{Variable}{groebresmax} -The variable \name{groebresmax} -controls during \nameref{groebnerf} calculations -the number of partial results. Its default value is 300. If -more partial results are calculated, the calculation is -terminated. -\end{Variable} - -% ---------------------------------------------------------------- -\begin{Variable}{groebrestriction} -During \nameref{groebnerf} calculations -irrelevant branches can be excluded -by setting the variable \name{groebrestriction}. The -following restrictions are implemented: -\begin{Syntax} - \name{groebrestriction} := \name{nonnegative} \\ - \name{groebrestriction} := \name{positive}\\ - \name{groebrestriction} := \name{zeropoint} -\end{Syntax} -With \name{nonnegative} branches are excluded where one -polynomial has no nonnegative real zeros; with \name{positive} -the restriction is sharpened to positive zeros only. -The restriction \name{zeropoint} excludes all branches -which do not have the origin (0,0,...0) in their solution -set. -\end{Variable} - -%--------------------------------------------------------- -\subsection{Tracing Groebner bases} -%--------------------------------------------------------- -\index{tracing Groebner} -\begin{Switch}{groebprot} -If \name{groebprot} is \name{ON} the computation steps during -\nameref{preduce}, \nameref{greduce} and \nameref{groebner} -are collected in a list which is assigned to the variable -\nameref{groebprotfile}. -\end{Switch} -%---------------------------------------------------------- -\begin{Variable}{groebprotfile} -See \nameref{groebprot} switch. -\end{Variable} -%---------------------------------------------------------- - -\begin{Operator}{groebnert} -\begin{Syntax} - - \name{groebnert}\(\{\meta{v}=\meta{exp},...\}\) - -\end{Syntax} -where \meta{v} are \nameref{kernel}\name{s} (simple or indexed variables), -\meta{exp} are polynomials. - - -\name{groebnert} is functionally equivalent to a \nameref{groebner} -call for \{\meta{exp},...\}, but the result is a set of -equations where the left-hand sides are the basis elements while -the right-hand sides are the same values expressed as combinations -of the input formulas, expressed in terms of the names \meta{v} -\begin{Bigexample} - groebnert({p1=2*x**2+4*y**2-100,p2=2*x-y+1}); - - GB1 := {2*X - Y + 1=P2, - - 2 - 9*Y - 2*Y - 199= - 2*X*P2 - Y*P2 + 2*P1 + P2} -\end{Bigexample} -\end{Operator} -%---------------------------------------------------------- - -\begin{Operator}{preducet} -\begin{Syntax} - -\name{preduce}\(\meta{p},\{\meta{v}=\meta{exp}...\}\) -\end{Syntax} -where \meta{p} is an expression, \meta{v} are kernels -(simple or indexed variables), -\name{exp} are polynomials. - -\name{preducet} computes the remainder of \meta{p} modulo \{\meta{exp},...\} -similar to \nameref{preduce}, but the result is an equation -which expresses the remainder as combination of the polynomials. -\begin{Bigexample} - - GB2 := {G1=2*X - Y + 1,G2=9*Y**2 - 2*Y - 199} - preducet(q=x**2,gb2); - - - 16*Y + 208= - 18*X*G1 - 9*Y*G1 + 36*Q + 9*G1 - G2 -\end{Bigexample} -\end{Operator} - -%------------------------------------------------------------ -\subsection{Groebner Bases for Modules} -%------------------------------------------------------------ -\begin{Concept}{Module} -Given a polynomial ring, e.g. R=Z[x,y,...] and an integer n>1. -The vectors with n elements of R form a free MODULE under -elementwise addition and multiplication with elements of R. - -For a submodule given by a finite basis a Groebner basis -can be computed, and the facilities of the GROEBNER package -are available except the operators \nameref{groebnerf} -and \name{groesolve}. The vectors are encoded using auxiliary -variables which represent the unit vectors in the module. -These are declared in the share variable \nameref{gmodule}. - -\end{Concept} - -\begin{Variable}{gmodule} -The vectors of a free \nameref{module} over a polynomial ring R -are encoded as linear combinations with unit vectors of -M which are represented by auxiliary variables. These -must be collected in the variable \name{gmodule} before -any call to an operator of the Groebner package. - -\begin{verbatim} - torder({x,y,v1,v2,v3})$ - gmodule := {v1,v2,v3}$ - g:=groebner({x^2*v1 + y*v2,x*y*v1 - v3,2y*v1 + y*v3}); -\end{verbatim} - -compute the Groebner basis of the submodule - -\begin{verbatim} - ([x^2,y,0],[xy,0,-1],[0,2y,y]) -\end{verbatim} -The members of the list \name{gmodule} are automatically -appended to the end of the variable list, if they are not -yet members there. They take part in the actual term ordering. -\end{Variable} - -%------------------------------------------------------------ -\subsection{Computing with distributive polynomials} -%------------------------------------------------------------ - -\begin{Operator}{gsort} -\index{distributive polynomials} -\begin{Syntax} - - \name{gsort}\(\meta{p}\) -\end{Syntax} -where \meta{p} is a polynomial or a list of polynomials. - -The polynomials are reordered and sorted corresponding to -the current \nameref{term order}. -\begin{Examples} - - torder lex;\\ - gsort(x**2+2x*y+y**2,{y,x}); & {y**2+2y*x+x**2} - -\end{Examples} -\end{Operator} - -%------------------------------------------------------------ - -\begin{Operator}{gsplit} -\index{distributive polynomials} -\begin{Syntax} - - \name{gsplit}\(\meta{p}[,\meta{vars}]\); -\end{Syntax} -where \meta{p} is a polynomial or a list of polynomials. - -The polynomial is reordered corresponding to the -the current \nameref{term order} and then -separated into leading term and reductum. Result is -a list with the leading term as first and the reductum -as second element. -\begin{Examples} - - torder lex;\\ - gsplit(x**2+2x*y+y**2,{y,x}); & \{y**2,2y*x+x**2\} - -\end{Examples} -\end{Operator} -%------------------------------------------------------- - -\begin{Operator}{gspoly} -\index{distributive polynomials} -\begin{Syntax} - - \name{gspoly}\(\meta{p1},\meta{p2}\); - -\end{Syntax} -where \meta{p1} and \meta{p2} are polynomials. - -The \name{subtraction} polynomial of p1 and p2 is computed -corresponding to the method of the Buchberger algorithm for -computing \name{groebner bases}: p1 and p2 are multiplied -with terms such that when subtracting them the leading terms -cancel each other. -\end{Operator} - +\section{Groebner package} +\begin{Introduction}{Groebner bases} +The GROEBNER package calculates \nameindex{Groebner bases} using the +\nameindex{Buchberger algorithm} and provides related algorithms +for arithmetic with ideal bases, such as ideal quotients, +Hilbert polynomials (\nameindex{Hollmann algorithm}), +basis conversion ( +\nameindex{Faugere-Gianni-Lazard-Mora algorithm}), independent +variable set (\nameindex{Kredel-Weispfenning algorithm}). + + + +Some routines of the Groebner package are used by \nameref{solve} - in +that context the package is loaded automatically. However, if you +want to use the package by explicit calls you must load it by +\begin{verbatim} + load_package groebner; +\end{verbatim} + +For the common parameter setting of most operators in this package +see \nameref{ideal parameters}. +\end{Introduction} + + + +\begin{Concept}{Ideal Parameters} +\index{polynomial} +Most operators of the \name{Groebner} package compute expressions in a +polynomial ring which given as \meta{R}[\meta{var},\meta{var},...] where +\meta{R} is the current REDUCE coefficient domain. All algebraically +exact domains of REDUCE are supported. The package can operate over rings +and fields. The operation mode is distinguished automatically. In +general the ring mode is a bit faster than the field mode. The factoring +variant can be applied only over domains which allow you factoring of +multivariate polynomials. + +The variable sequence \meta{var} is either declared explicitly as argument +in form of a \nameref{list} in \nameref{torder}, or it is extracted +automatically from the expressions. In the second case the current REDUCE +system order is used (see \nameref{korder}) for arranging the variables. +If some kernels should play the role of formal parameters (the ground +domain \meta{R} then is the polynomial ring over these), the variable +sequences must be given explicitly. + +All REDUCE \nameref{kernel}s can be used as variables. But please note, +that all variables are considered as independent. E.g. when using +\name{sin(a)} and \name{cos(a)} as variables, the basic relation +\name{sin(a)^2+cos(a)^2-1=0} must be explicitly added to an equation set +because the Groebner operators don't include such knowledge automatically. + +The terms (monomials) in polynomials are arranged according to the current +\nameref{term order}. Note that the algebraic properties of the computed +results only are valid as long as neither the ordering nor the variable +sequence changes. + +The input expressions \meta{exp} can be polynomials \meta{p}, rational +functions \meta{n}/\meta{d} or equations \meta{lh}=\meta{rh} built from +polynomials or rational functions. Apart from the \name{tracing} +algorithms \nameref{groebnert} and \nameref{preducet}, where the equations +have a specific meaning, equations are converted to simple expressions by +taking the difference of the left-hand and right-hand sides +\meta{lh}-\meta{rh}=>\meta{p}. Rational functions are converted to +polynomials by converting the expression to a common denominator form +first, and then using the numerator only \meta{n}=>\meta{p}. So eventual +zeros of the denominators are ignored. + +A basis on input or output of an algorithm is coded as \nameref{list} of +expressions \{\meta{exp},\meta{exp},...\} . \end{Concept} + +%----------------------------------------------------------------- +\subsection{Term order} +%----------------------------------------------------------------- +\begin{Introduction}{Term order} +\index{distributive polynomials} +For all \name{Groebner} operations the polynomials are +represented in distributive form: a sum of terms (monomials). +The terms are ordered corresponding to the actual \name{term order} +which is set by the \nameref{torder} operator, and to the +actual variable sequence which is either given as explicit +parameter or by the system \nameref{kernel} order. +\end{Introduction} + +\begin{Operator}{TORDER} +The operator \name{torder} sets the actual variable sequence and term order. + +1. simple term order: +\begin{Syntax} + \name{torder}\(\meta{vl}, \meta{m}\) +\end{Syntax} + +where \meta{vl} is a \nameref{list} of variables (\nameref{kernel}s) and +\meta{m} is the name of a simple \nameref{term order} mode +\ref{lex term order}, \ref{gradlex term order}, +\ref{revgradlex term order} or another implemented parameterless mode. + +2. stepped term order: +\begin{Syntax} + + \name{torder} \(\meta{vl},\meta{m},\meta{n}\) + +\end{Syntax} + +where \meta{m} is the name of a two step term order, one of +\nameref{gradlexgradlex term order}, \nameref{gradlexrevgradlex term order}, +\nameref{lexgradlex term order} or \nameref{lexrevgradlex term order}, and +\meta{n} is a positive integer. + +3. weighted term order +\begin{Syntax} + \name{torder} \(\meta{vl}, \name{weighted}, \meta{n},\meta{n},...\); +\end{Syntax} + +where the \meta{n} are positive integers, see \nameref{weighted term order}. + +4. matrix term order +\begin{Syntax} + \name{torder} \(\meta{vl}, \name{matrix}, \meta{m}\); +\end{Syntax} + +where \meta{m} is a matrix with integer elements, see +\nameref{torder_compile}. + +5. compiled term order +\begin{Syntax} + \name{torder} \(\meta{vl}, \name{co}\); +\end{Syntax} + +where \meta{co} is the name of a routine generated by +\nameref{torder_compile}. + +\name{torder} sets the variable sequence and the term order mode. If the +an empty list is used as variable sequence, the automatic variable extraction +is activated. The defaults are the empty variable list an the +\nameref{lex term order}. +The previous setting is returned as a list. + +Alternatively to the above syntax the arguments of \name{torder} may be +collected in a \nameref{list} and passed as one argument to +\name{torder}. + +\end{Operator} +%------------------------------------------------------------ +\begin{Operator}{torder_compile} +\index{term order} +A matrix can be converted into +a compilable LISP program for faster execution by using +\begin{Syntax} + \name{torder\_compile}\(\meta{name},\meta{mat}\) +\end{Syntax} +where \meta{name} is an identifier for the new term order and \meta{mat} +is an integer matrix to be used as \nameref{matrix term order}. Afterwards +the term order can be activated by using \meta{name} in a \nameref{torder} +expression. The resulting program is compiled if the switch \nameref{comp} +is on, or if the \name{torder\_compile} expression is part of a compiled +module. +\end{Operator} +%------------------------------------------------------------ +\begin{Concept}{lex term order} +\index{term order}\index{variable elimination} +The terms are ordered lexicographically: two terms t1 t2 +are compared for their degrees +along the fixed variable sequence: t1 is higher than t2 +if the first different degree is higher in t1. +This order has the \name{elimination property} +for \name{groebner basis} calculations. +If the ideal has a univariate polynomial in the last +variable the groebner basis will contain +such polynomial. \name{Lex} is best +suited for solving of polynomial equation systems. + +\end{Concept} + +%------------------------------------------------------------ +\begin{Concept}{gradlex term order} +\index{term order} +The terms are ordered first with their total +degree, and if the total degree is identical +the comparison is \nameref{lex term order}. +With \name{groebner} basis calculations this term order +produces polynomials of lowest degree. +\end{Concept} + +%------------------------------------------------------------ +\begin{Concept}{revgradlex term order} +\index{term order} +The terms are ordered first with their total +degree (degree sum), and if the total degree is identical +the comparison is the inverse of \nameref{lex term order}. +With \nameref{groebner} and \nameref{groebnerf} +calculations this term order +is similar to \nameref{gradlex term order}; it is known +as most efficient ordering with respect to computing time. +\end{Concept} + +%------------------------------------------------------------ +\begin{Concept}{gradlexgradlex term order} +\index{term order} +The terms are separated into two groups where the +second parameter of the \nameref{torder} call determines +the length of the first group. For a comparison first +the total degrees of both variable groups are compared. +If both are equal +\nameref{gradlex term order} comparison is applied to the first +group, and if that does not decide \nameref{gradlex term order} +is applied for the second group. This order has the elimination +property for the variable groups. It can be used e.g. for +separating variables from parameters. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{gradlexrevgradlex term order} +\index{term order} +Similar to \nameref{gradlexgradlex term order}, but using +\nameref{revgradlex term order} for the second group. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{lexgradlex term order} +\index{term order} +Similar to \nameref{gradlexgradlex term order}, but using +\nameref{lex term order} for the first group. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{lexrevgradlex term order} +\index{term order} +Similar to \nameref{gradlexgradlex term order}, but using +\nameref{lex term order} for the first group +\nameref{revgradlex term order} for the second group. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{weighted term order} +\index{term order} +establishes a graduated ordering +similar to \nameref{gradlex term order}, where the exponents first are +multiplied by the given weights. If there are less weight values than +variables, the weight list is extended by ones. If the weighted degree +comparison is not decidable, the +\nameref{lex term order} is used. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{graded term order} +\index{term order} +establishes a cascaded term ordering: first a graduated ordering +similar to \nameref{gradlex term order} is used, where the exponents first are +multiplied by the given weights. If there are less weight values than +variables, the weight list is extended by ones. If the weighted degree +comparison is not decidable, the term ordering described in the following +parameters of the \nameref{torder} command is used. +\end{Concept} +%------------------------------------------------------------ +\begin{Concept}{matrix term order} +\index{term order} +Any arbitrary term order mode can be installed by a matrix with +integer elements where the row length corresponds to the variable +number. The matrix must have at least as many rows as columns. +It must have full rank, and the top nonzero element of each column +must be positive. + +The matrix \name{term order mode} +defines a term order where the exponent vectors of the monomials are +first multiplied by the matrix and the resulting vectors are compared +lexicographically. + +If the switch \nameref{comp} is on, the matrix is converted into +a compiled LISP program for faster execution. A matrix can also be +compiled explicitly, see \nameref{torder_compile}. +\end{Concept} +%--------------------------------------------------------------- +%------------------------------------------------------------ +\subsection{Basic Groebner operators} +%------------------------------------------------------------- +\begin{Operator}{GVARS} +\begin{Syntax} + + \name{gvars}\(\{\meta{exp},\meta{exp},... \}\) + +\end{Syntax} + where \meta{exp} are expressions or \nameref{equation}s. + +\name{gvars} extracts from the expressions the \nameref{kernel}\name{s} +which can +play the role of variables for a \nameref{groebner} or \nameref{groebnerf} +calculation. +\end{Operator} + +%--------------------------------------------------------------- + +\begin{Operator}{GROEBNER} +\index{Buchberger algorithm} +\begin{Syntax} + + \name{groebner}\(\{\name{exp}, ...\}\) + +\end{Syntax} +where \{\name{exp}, ... \} is a list of +expressions or equations. + + +The operator \name{groebner} implements the Buchberger algorithm +for computing Groebner bases for a given set of +expressions with respect to the given set of variables in the order +given. As a side effect, the sequence of variables is stored as a REDUCE list +in the shared variable \nameref{gvarslast} - this is important in cases +where the algorithm rearranges the variable sequence because \nameref{groebopt} +is \name{on}. + +\begin{Examples} + groebner({x**2+y**2-1,x-y}) & \{X - Y,2*Y**2 -1\} +\end{Examples} +\begin{Related} +\item[ \nameref{groebnerf} operator] +\item[ \nameref{gvarslast} variable] +\item[ \nameref{groebopt} switch] +\item[ \nameref{groebprereduce} switch] +\item[ \nameref{groebfullreduction} switch] +\item[ \nameref{gltbasis} switch] +\item[ \nameref{gltb} variable] +\item[ \nameref{glterms} variable] +\item[ \nameref{groebstat} switch] +\item[ \nameref{trgroeb} switch] +\item[ \nameref{trgroebs} switch] +\item[ \nameref{groebprot} switch] +\item[ \nameref{groebprotfile} variable] +\item[ \nameref{groebnert} operator] +\end{Related} +\end{Operator} + +%------------------------------------------------------- + +\begin{Switch}{groebopt} +If \name{groebopt} is set ON, the sequence of variables is optimized +with respect to execution speed of \name{groebner} calculations; +note that the final list of variables is available in \nameref{gvarslast}. +By default \name{groebopt} is off, conserving the original variable +sequence. + +An explicitly declared dependency using the \nameref{depend} +declaration supersedes the variable optimization. +\begin{Examples} + + depend a, x, y; + +\end{Examples} +guarantees that a will be placed in front of x and y. +\end{Switch} + + +%------------------------------------------------------- + +\begin{Variable}{gvarslast} +After a \nameref{groebner} or \nameref{groebnerf} calculation +the actual variable sequence is stored in the variable +\name{gvarslast}. If \nameref{groebopt} is \name{on} +\name{gvarslast} shows the variable sequence after reordering. +\end{Variable} + +%-------------------------------------------------------------- + +\begin{Switch}{groebprereduce} +If \name{groebprereduce} set ON, \nameref{groebner} +and \nameref{groebnerf} try to simplify the +input expressions: if the head term of an input expression is a +multiple of the head term of another expression, it can be reduced; +these reductions are done cyclicly as long as possible in order to +shorten the main part of the algorithm. + +By default \name{groebprereduce} is off. +\end{Switch} + +%--------------------------------------------------------------- + +\begin{Switch}{groebfullreduction} +If \name{groebfullreduction} set off, the polynomial reduction steps during +\nameref{groebner} and \nameref{groebnerf} are limited to the pure head +term reduction; subsequent terms are reduced otherwise. + +By default \name{groebfullreduction} is on. +\end{Switch} + +%---------------------------------------------------------------- + +\begin{Switch}{gltbasis} +If \name{gltbasis} set on, the leading terms of the result basis +of a \nameref{groebner} or \nameref{groebnerf} calculation are +extracted. They are collected as a basis of monomials, which is +available as value of the global variable \nameref{gltb}. +\end{Switch} +%------------------------------------------------------------------ +\begin{Variable}{gltb} +See \nameref{gltbasis} +\end{Variable} +%------------------------------------------------------------------ + +\begin{Variable}{glterms} +If the expressions in a \nameref{groebner} or \nameref{groebnerf} +call contain parameters (symbols +which are not member of the variable list), the share variable +\name{glterms} is set to a list of expression which during the +calculation were assumed to be nonzero. The calculated bases +are valid only under the assumption that all these expressions do +not vanish. +\end{Variable} + +%----------------------------------------------------------- +\begin{Switch}{groebstat} +if \name{groebstat} is on, a summary of the +\nameref{groebner} or \nameref{groebnerf} computation is printed +at the end +including the computing time, the number of intermediate +H polynomials and the counters for the criteria hits. +\end{Switch} + +%----------------------------------------------------------- +\begin{Switch}{trgroeb} +if \name{trgroeb} is on, intermediate H polynomials are +printed during a \nameref{groebner} +or \nameref{groebnerf} calculation. +\end{Switch} + +%----------------------------------------------------------- +\begin{Switch}{trgroebs} +if \name{trgroebs} is on, intermediate H and S polynomials are +printed during a \nameref{groebner} or \nameref{groebnerf} calculation. +\end{Switch} + +%----------------------------------------------------------- +\begin{Operator}{gzerodim?} +\begin{Syntax} + + \name{gzerodim!?}\(\meta{basis}\) + +\end{Syntax} +where \meta{bas} is a Groebner basis in the current +\nameref{term order} with the actual setting +(see \nameref{ideal parameters}). + + +\name{gzerodim!?} tests whether the ideal spanned by the given basis +has dimension zero. If yes, the number of zeros is returned, +\nameref{nil} otherwise. +\end{Operator} + +%--------------------------------------------------------------- + +\begin{Operator}{gdimension} +\index{ideal dimension}\index{groebner} +\begin{Syntax} + + \name{gdimension}\(\meta{bas}\) + +\end{Syntax} +where \meta{bas} is a \nameref{groebner} basis in the current +term order (see \nameref{ideal parameters}). +\name{gdimension} computes the dimension of the ideal +spanned by the given basis and returns the dimension as an integer +number. The Kredel-Weispfenning algorithm is used: the dimension +is the length of the longest independent variable set, +see \nameref{gindependent\_sets} +\end{Operator} + + +%--------------------------------------------------------------- + +\begin{Operator}{gindependent\_sets} +\index{ideal variables}\index{ideal dimension}\index{groebner} +\index{Kredel-Weispfenning algorithm} +\begin{Syntax} + + \name{gindependent\_sets}\(\meta{bas}\) + +\end{Syntax} +where \meta{bas} is a \nameref{groebner} basis in any \name{term order} +(which must be the current \name{term order}) with the specified +variables (see \nameref{ideal parameters}). + + +\name{Gindependent_sets} computes the maximal +left independent variable sets of the ideal, that are +the variable sets which play the role of free parameters in the +current ideal basis. Each set is a list which is a subset of the +variable list. The result is a list of these sets. For an +ideal with dimension zero the list is empty. +The Kredel-Weispfenning algorithm is used. +\end{Operator} + +%-------------------------------------------------------------- + +\begin{Operator}{dd_groebner} +For a homogeneous system of polynomials under +\nameref{graded term order}, \nameref{gradlex term order}, +\nameref{revgradlex term order} +or \nameref{weighted term order} +a Groebner Base can be computed with limiting the grade +of the intermediate S polynomials: +\begin{Syntax} +\name{dd_groebner}\(\meta{d1},\meta{d2},\meta{plist}\) +\end{Syntax} +where \meta{d1} is a non negative integer and \meta{d2} is an integer +or ``infinity". A pair of polynomials is considered +only if the grade of the lcm of their head terms is between +\meta{d1} and \meta{d2}. +For the term orders \name{graded} or \name{weighted} the (first) weight +vector is used for the grade computation. Otherwise the total +degree of a term is used. +\end{Operator} + +%-------------------------------------------------------------- + + +\begin{Operator}{glexconvert} +\index{ideal variables}\index{term order} +\begin{Syntax} + +\name{glexconvert}\(\meta{bas}[,\meta{vars}][,MAXDEG=\meta{mx}] +[,NEWVARS=\meta{nv}]\) + +\end{Syntax} +where \meta{bas} is a \nameref{groebner} basis +in the current term order, \meta{mx} (optional) is a positive +integer and \meta{nvl} (optional) is a list of variables +(see \nameref{ideal parameters}). + + +The operator \name{glexconvert} converts the basis +of a zero-dimensional ideal (finite number +of isolated solutions) from arbitrary ordering into a basis under +\nameref{lex term order}. + + +The parameter \meta{newvars} defines the new variable sequence. +If omitted, the +original variable sequence is used. If only a subset of variables is +specified here, the partial ideal basis is evaluated. + +If \meta{newvars} is a list with one element, the minimal +\nameindex{univariate polynomial} is computed. + +\meta{maxdeg} is an upper limit for the degrees. The algorithm stops with +an error message, if this limit is reached. + +A warning occurs, if the ideal is not zero dimensional. +\begin{Comments} +During the call the \name{term order} of the input basis must +be active. +\end{Comments} +\end{Operator} + +%-------------------------------------------------------------- + +\begin{Operator}{greduce} +\begin{Syntax} + +\name{greduce}\(exp, \{exp1, exp2, \ldots , expm\}\) + +\end{Syntax} + +where exp is an expression, and \{exp1, exp2, ... , expm\} is +a list of expressions or equations. + + +\name{greduce} is functionally equivalent with a call to +\nameref{groebner} and then a call to \nameref{preduce}. +\end{Operator} + +%--------------------------------------------------------- + +\begin{Operator}{preduce} +\begin{Syntax} + + \name{preduce}\(\meta{p}, \{\meta{exp}, \ldots \}\) + +\end{Syntax} + +where \meta{p} is an expression, and \{\meta{exp}, ... \} is +a list of expressions or equations. + + +\name{preduce} computes the remainder of \name{exp} +modulo the given set of polynomials resp. equations. +This result is unique (canonical) only if the given set +is a \name{groebner} basis under the current \nameref{term order} + +see also: \nameref{preducet} operator. + +\end{Operator} + + +%------------------------------------------- + +\begin{Operator}{idealquotient} +\begin{Syntax} + + +\name{idealquotient}\(\{\meta{exp}, ...\}, \meta{d}\) + +\end{Syntax} +where \{\meta{exp},...\} is a list of +expressions or equations, \meta{d} is a single expression or equation. + + +\name{idealquotient} computes the ideal quotient: +ideal spanned by the expressions \{\meta{exp},...\} +divided by the single polynomial/expression \meta{f}. The result +is the \nameref{groebner} basis of the quotient ideal. +\end{Operator} +%------------------------------------------------------------- +\begin{Operator}{hilbertpolynomial} +\index{Hollmann algorithm} +\begin{Syntax} + + hilbertpolynomial\(\meta{bas}\) + +\end{Syntax} +where \meta{bas} is a \nameref{groebner} basis in the +current \nameref{term order}. + +The degree of the \name{Hilbert polynomial} is the +dimension of the ideal spanned by the basis. For an +ideal of dimension zero the Hilbert polynomial is a +constant which is the number of common zeros of the +ideal (including eventual multiplicities). +The \name{Hollmann algorithm} is used. +\end{Operator} + +%------------------------------------------------------------- +\subsection{Factorizing Groebner bases} +%------------------------------------------------------------- + +\begin{Operator}{groebnerf} +\begin{Syntax} + +\name{groebnerf}\(\{\meta{exp}, ...\}[,\{\},\{\meta{nz}, ... \}]\); + +\end{Syntax} +where \{\meta{exp}, ... \} is a list of expressions or +equations, and \{\meta{nz},... \} is +an optional list of polynomials to be considered as non zero +for this calculation. An empty list must be passed as second argument +if the non-zero list is specified. + + +\name{groebnerf} tries to separate polynomials into individual factors and +to branch the computation in a recursive manner (factorization tree). +The result is a list of partial Groebner bases. +Multiplicities (one factor with a higher power, the same partial basis +twice) are deleted as early as possible in order to speed up the +calculation. + +The third parameter of \name{groebnerf} declares some polynomials +nonzero. If any of these is found in a branch of the calculation +the branch is canceled. + +\begin{Bigexample} +groebnerf({ 3*x**2*y+2*x*y+y+9*x**2+5*x = 3, + 2*x**3*y-x*y-y+6*x**3-2*x**2-3*x = -3, + x**3*y+x**2*y+3*x**3+2*x**2 }, {y,x}); + + {{Y - 3,X}, + + 2 + {2*Y + 2*X - 1,2*X - 5*X - 5}} +\end{Bigexample} + +\begin{Related} +\item[ \nameref{groebresmax} variable] +\item[ \nameref{groebmonfac} variable] +\item[ \nameref{groebrestriction} variable] +\item[ \nameref{groebner} operator] +\item[ \nameref{gvarslast} variable] +\item[ \nameref{groebopt} switch] +\item[ \nameref{groebprereduce} switch] +\item[ \nameref{groebfullreduction} switch] +\item[ \nameref{gltbasis} switch] +\item[ \nameref{gltb} variable] +\item[ \nameref{glterms} variable] +\item[ \nameref{groebstat} switch] +\item[ \nameref{trgroeb} switch] +\item[ \nameref{trgroebs} switch] +\item[ \nameref{groebnert} operator] +\end{Related} + +\end{Operator} + +% ------------------------------------------------------------------ + +\begin{Variable}{groebmonfac} +The variable \name{groebmonfac} is connected to +the handling of monomial factors. A monomial factor is a product +of variable powers as a factor, e.g. x**2*y in x**3*y - +2*x**2*y**2. A monomial factor represents a solution of the type + x = 0 or y = 0 with a certain multiplicity. With +\nameref{groebnerf} the multiplicity of monomial factors is lowered +to the value of the shared variable \name{groebmonfac} +which by default is 1 (= monomial factors remain present, but their +multiplicity is brought down). With +\name{groebmonfac}:= 0 +the monomial factors are suppressed completely. +\end{Variable} + +% ---------------------------------------------------------------- +\begin{Variable}{groebresmax} +The variable \name{groebresmax} +controls during \nameref{groebnerf} calculations +the number of partial results. Its default value is 300. If +more partial results are calculated, the calculation is +terminated. +\end{Variable} + +% ---------------------------------------------------------------- +\begin{Variable}{groebrestriction} +During \nameref{groebnerf} calculations +irrelevant branches can be excluded +by setting the variable \name{groebrestriction}. The +following restrictions are implemented: +\begin{Syntax} + \name{groebrestriction} := \name{nonnegative} \\ + \name{groebrestriction} := \name{positive}\\ + \name{groebrestriction} := \name{zeropoint} +\end{Syntax} +With \name{nonnegative} branches are excluded where one +polynomial has no nonnegative real zeros; with \name{positive} +the restriction is sharpened to positive zeros only. +The restriction \name{zeropoint} excludes all branches +which do not have the origin (0,0,...0) in their solution +set. +\end{Variable} + +%--------------------------------------------------------- +\subsection{Tracing Groebner bases} +%--------------------------------------------------------- +\index{tracing Groebner} +\begin{Switch}{groebprot} +If \name{groebprot} is \name{ON} the computation steps during +\nameref{preduce}, \nameref{greduce} and \nameref{groebner} +are collected in a list which is assigned to the variable +\nameref{groebprotfile}. +\end{Switch} +%---------------------------------------------------------- +\begin{Variable}{groebprotfile} +See \nameref{groebprot} switch. +\end{Variable} +%---------------------------------------------------------- + +\begin{Operator}{groebnert} +\begin{Syntax} + + \name{groebnert}\(\{\meta{v}=\meta{exp},...\}\) + +\end{Syntax} +where \meta{v} are \nameref{kernel}\name{s} (simple or indexed variables), +\meta{exp} are polynomials. + + +\name{groebnert} is functionally equivalent to a \nameref{groebner} +call for \{\meta{exp},...\}, but the result is a set of +equations where the left-hand sides are the basis elements while +the right-hand sides are the same values expressed as combinations +of the input formulas, expressed in terms of the names \meta{v} +\begin{Bigexample} + groebnert({p1=2*x**2+4*y**2-100,p2=2*x-y+1}); + + GB1 := {2*X - Y + 1=P2, + + 2 + 9*Y - 2*Y - 199= - 2*X*P2 - Y*P2 + 2*P1 + P2} +\end{Bigexample} +\end{Operator} +%---------------------------------------------------------- + +\begin{Operator}{preducet} +\begin{Syntax} + +\name{preduce}\(\meta{p},\{\meta{v}=\meta{exp}...\}\) +\end{Syntax} +where \meta{p} is an expression, \meta{v} are kernels +(simple or indexed variables), +\name{exp} are polynomials. + +\name{preducet} computes the remainder of \meta{p} modulo \{\meta{exp},...\} +similar to \nameref{preduce}, but the result is an equation +which expresses the remainder as combination of the polynomials. +\begin{Bigexample} + + GB2 := {G1=2*X - Y + 1,G2=9*Y**2 - 2*Y - 199} + preducet(q=x**2,gb2); + + - 16*Y + 208= - 18*X*G1 - 9*Y*G1 + 36*Q + 9*G1 - G2 +\end{Bigexample} +\end{Operator} + +%------------------------------------------------------------ +\subsection{Groebner Bases for Modules} +%------------------------------------------------------------ +\begin{Concept}{Module} +Given a polynomial ring, e.g. R=Z[x,y,...] and an integer n>1. +The vectors with n elements of R form a free MODULE under +elementwise addition and multiplication with elements of R. + +For a submodule given by a finite basis a Groebner basis +can be computed, and the facilities of the GROEBNER package +are available except the operators \nameref{groebnerf} +and \name{groesolve}. The vectors are encoded using auxiliary +variables which represent the unit vectors in the module. +These are declared in the share variable \nameref{gmodule}. + +\end{Concept} + +\begin{Variable}{gmodule} +The vectors of a free \nameref{module} over a polynomial ring R +are encoded as linear combinations with unit vectors of +M which are represented by auxiliary variables. These +must be collected in the variable \name{gmodule} before +any call to an operator of the Groebner package. + +\begin{verbatim} + torder({x,y,v1,v2,v3})$ + gmodule := {v1,v2,v3}$ + g:=groebner({x^2*v1 + y*v2,x*y*v1 - v3,2y*v1 + y*v3}); +\end{verbatim} + +compute the Groebner basis of the submodule + +\begin{verbatim} + ([x^2,y,0],[xy,0,-1],[0,2y,y]) +\end{verbatim} +The members of the list \name{gmodule} are automatically +appended to the end of the variable list, if they are not +yet members there. They take part in the actual term ordering. +\end{Variable} + +%------------------------------------------------------------ +\subsection{Computing with distributive polynomials} +%------------------------------------------------------------ + +\begin{Operator}{gsort} +\index{distributive polynomials} +\begin{Syntax} + + \name{gsort}\(\meta{p}\) +\end{Syntax} +where \meta{p} is a polynomial or a list of polynomials. + +The polynomials are reordered and sorted corresponding to +the current \nameref{term order}. +\begin{Examples} + + torder lex;\\ + gsort(x**2+2x*y+y**2,{y,x}); & {y**2+2y*x+x**2} + +\end{Examples} +\end{Operator} + +%------------------------------------------------------------ + +\begin{Operator}{gsplit} +\index{distributive polynomials} +\begin{Syntax} + + \name{gsplit}\(\meta{p}[,\meta{vars}]\); +\end{Syntax} +where \meta{p} is a polynomial or a list of polynomials. + +The polynomial is reordered corresponding to the +the current \nameref{term order} and then +separated into leading term and reductum. Result is +a list with the leading term as first and the reductum +as second element. +\begin{Examples} + + torder lex;\\ + gsplit(x**2+2x*y+y**2,{y,x}); & \{y**2,2y*x+x**2\} + +\end{Examples} +\end{Operator} +%------------------------------------------------------- + +\begin{Operator}{gspoly} +\index{distributive polynomials} +\begin{Syntax} + + \name{gspoly}\(\meta{p1},\meta{p2}\); + +\end{Syntax} +where \meta{p1} and \meta{p2} are polynomials. + +The \name{subtraction} polynomial of p1 and p2 is computed +corresponding to the method of the Buchberger algorithm for +computing \name{groebner bases}: p1 and p2 are multiplied +with terms such that when subtracting them the leading terms +cancel each other. +\end{Operator} + Index: r36/help/pk-misc.tex ================================================================== --- r36/help/pk-misc.tex +++ r36/help/pk-misc.tex @@ -1,595 +1,595 @@ -\section{Miscellaneous Packages} - -\begin{Introduction}{Miscellaneous Packages} -REDUCE includes a large number of packages that have been contributed by -users from various fields. Some of these, together with their relevant -commands, switches and so on (e.g., the NUMERIC package), have -been described elsewhere. This section describes those packages for which -no separate help material exists. Each has its own switches, commands, -and operators, and some redefine special characters to aid in their -notation. However, the brief descriptions given here do not include all -such information. Readers are referred to the general package -documentation in this case, which can be found, along with the source -code, under the subdirectories \name{doc} and \name{src} in the -\name{reduce} directory. The \nameref{load_package} command is used to -load the files you wish into your system. There will be a short delay -while the package is loaded. A package cannot be {\it unloaded}. Once it -is in your system, it stays there until you end the session. Each package -also has a test file, which you will find under its name in the -\name{\$reduce/xmpl} directory. - -Finally, it should be mentioned that such user-contributed packages are -unsupported; any questions or problems should be directed to their -authors. - -\end{Introduction} - -\begin{Package}{ALGINT} -\index{integration}\index{integration of square roots} -Author: James H. Davenport \\ - -The \name{algint} package provides indefinite integration of square roots. -This package, which is an extension of the basic integration package -distributed with REDUCE, will analytically integrate a wide range of -expressions involving square roots. The \nameref{algint} switch provides for -the use of the facilities given by the package, and is automatically turned -on when the package is loaded. If you want to return to the standard -integration algorithms, turn \nameref{algint} off. An error message is given -if you try to turn the \nameref{algint} switch on when its package is not -loaded. -\end{Package} - -\begin{Package}{APPLYSYM} -\index{differential equations} \index{symmetries} -Author: Thomas Wolf \\ - -This package provides programs APPLYSYM, QUASILINPDE and DETRAFO for -computing with infinitesimal symmetries of differential equations. -\end{Package} - -\begin{Package}{ARNUM} -\index{algebraic numbers} -Author: Eberhard Schruefer\\ - -This package provides facilities for handling algebraic numbers as polynomial -coefficients in REDUCE calculations. It includes facilities for introducing -indeterminates to represent algebraic numbers, for calculating splitting -fields, and for factoring and finding greatest common divisors in such -domains. -\end{Package} - -\begin{Package}{ASSIST} -\index{utilities} -Author: Hubert Caprasse\\ - -ASSIST contains a large number of additional general purpose functions -that allow a user to better adapt REDUCE to various calculational -strategies and to make the programming task more straightforward and more -efficient. -\end{Package} - -\begin{Package}{AVECTOR} -\index{vector algebra}\index{cross product}\index{dot product} -Author: David Harper\\ - -This package provides REDUCE with the ability to perform vector algebra -using the same notation as scalar algebra. The basic algebraic operations -are supported, as are differentiation and integration of vectors with -respect to scalar variables, cross product and dot product, component -manipulation and application of scalar functions (e.g. cosine) to a vector -to yield a vector result. -\end{Package} - -\begin{Package}{BOOLEAN} -\index{boolean expressions} -Author: Herbert Melenk\\ - -This package supports the computation with boolean expressions in the -propositional calculus. The data objects are composed from algebraic -expressions connected by the infix boolean operators {\bf and}, {\bf or}, -{\bf implies}, {\bf equiv}, and the unary prefix operator {\bf not}. -{\bf Boolean} allows you to simplify expressions built from these -operators, and to test properties like equivalence, subset property etc. -\end{Package} - -\begin{Package}{CALI} -\index{polynomial}\index{Groebner}\index{commutative algebra} -Author: Hans-Gert Gr{\"a}be \\ - -This package contains algorithms for computations in commutative algebra -closely related to the Groebner algorithm for ideals and modules. Its -heart is a new implementation of the Groebner algorithm that also allows -for the computation of syzygies. This implementation is also applicable to -submodules of free modules with generators represented as rows of a matrix. -\end{Package} - -\begin{Package}{CAMAL} -\index{celestial mechanics}\index{Fourier series} -Author: John P. Fitch\\ - -This packages implements in REDUCE the Fourier transform procedures of the -CAMAL package for celestial mechanics. -\end{Package} - -\begin{Package}{CHANGEVR} -Author: G. Ucoluk\\ - -This package provides facilities for changing the independent variables in -a differential equation. It is basically the application of the chain rule. -\end{Package} - -\begin{Package}{COMPACT} -\index{simplification} -Author: Anthony C. Hearn\\ - -COMPACT is a package of functions for the reduction of a polynomial in the -presence of side relations. COMPACT applies the side relations to the -polynomial so that an equivalent expression results with as few terms as -possible. For example, the evaluation of - -\begin{verbatim} - compact(s*(1-sin x^2)+c*(1-cos x^2)+sin x^2+cos x^2, - {cos x^2+sin x^2=1}); - -\end{verbatim} -yields the result -\begin{verbatim} - - 2 2 - SIN(X) *C + COS(X) *S + 1 -\end{verbatim} - -The first argument to the operator \name{compact} is the expression -and the second is a list of side relations that can be -equations or simple expressions (implicitly equated to zero). The -kernels in the side relations may also be free variables with the -same meaning as in rules, e.g. -\begin{verbatim} - sin_cos_identity := {cos ~w^2+sin ~w^2=1}$ - compact(u,in_cos_identity); -\end{verbatim} -Also the full rule syntax with the replacement operator is allowed here. -\end{Package} - -\begin{Package}{CONTFR} -\index{continued fraction} -Author: Herbert Melenk\\ - -This package provides for the simultaneous approximation of a real number -by a continued fraction and a rational number with optional user -controlled precision (an upper bound for the denominator). - -To use this package, the \name{misc} package should be loaded. One can then -use the operator \name{continued\_fraction} to approximate the real -number by a continued fraction. This operator has one or two arguments, the -number to be converted and an optional precision. The result is a list of -two elements: the first is the rational value of the approximation and the -second the list of terms of the continued fraction that represent the same -value according to the definition \verb&t0 +1/(t1 + 1/(t2 + ...))&. The -second optional parameter \name{size} is an upper bound on the absolute -value of the result denominator. If omitted, the approximation is performed -up to the current system precision. - -\begin{Examples} -continued\_fraction pi; & -\begin{multilineoutput}{6cm} - 1146408 -\{---------,\{3,7,15,1,292,1,1,1,2,1\}\} - 364913 -\end{multilineoutput} \\ - -continued\_fraction(pi,100); & -\begin{multilineoutput}{6cm} - 22 -\{----,\{3,7\}\} - 7 -\end{multilineoutput} -\end{Examples} -\end{Package} - -\begin{Package}{CRACK} -\index{differential equation} -Authors: Andreas Brand, Thomas Wolf\\ - -CRACK is a package for solving overdetermined systems of partial or -ordinary differential equations (PDEs, ODEs). Examples of programs which -make use of CRACK for investigating ODEs (finding symmetries, first -integrals, an equivalent Lagrangian or a ``differential factorization'') are -included. -\end{Package} - -\begin{Package}{CVIT} -\index{Dirac algebra} -Authors: V.Ilyin, A.Kryukov, A.Rodionov, A.Taranov\\ - -This package provides an alternative method for computing traces of Dirac -gamma matrices, based on an algorithm by Cvitanovich that treats gamma -matrices as 3-j symbols. -\end{Package} - -\begin{Package}{DEFINT} -\index{definite integration} -Authors: Kerry Gaskell, Stanley M. Kameny, Winfried Neun\\ - -This package finds the definite integral of an expression in a stated -interval. It uses several techniques, including an innovative approach -based on the Meijer G-function, and contour integration. -\end{Package} - -\begin{Package}{DESIR} -\index{differential equation} -Authors: C. Dicrescenzo, F. Richard-Jung, E. Tournier\\ - -This package enables the basis of formal solutions to be computed for an -ordinary homogeneous differential equation with polynomial coefficients -over Q of any order, in the neighborhood of zero (regular or irregular -singular point, or ordinary point). -\end{Package} - -\begin{Package}{DFPART} -\index{partial derivative} -Author: Herbert Melenk\\ - -This package supports computations with total and partial derivatives of -formal function objects. Such computations can be useful in the context -of differential equations or power series expansions. -\end{Package} - -\begin{Package}{DUMMY} -\index{dummy variable} -Author: Alain Dresse\\ - -This package allows a user to find the canonical form of expressions -involving dummy variables. In that way, the simplification of -polynomial expressions can be fully done. The indeterminates are general -operator objects endowed with as few properties as possible. In that way -the package may be used in a large spectrum of applications. -\end{Package} - -\begin{Package}{EXCALC} -\index{exterior calculus}\index{differential calculus} -\index{differential form} -Author: Eberhard Schruefer\\ - -The \name{excalc} package is designed for easy use by all who are familiar -with the calculus of Modern Differential Geometry. The program is currently -able to handle scalar-valued exterior forms, vectors and operations between -them, as well as non-scalar valued forms (indexed forms). It is thus an ideal -tool for studying differential equations, doing calculations in general -relativity and field theories, or doing simple things such as calculating the -Laplacian of a tensor field for an arbitrary given frame. -\end{Package} - -\begin{Package}{FPS} -\index{power series} \index{Laurent-Puiseux series} -Authors: Wolfram Koepf, Winfried Neun\\ - -This package can expand a specific class of functions into their -corresponding Laurent-Puiseux series. -\end{Package} - -\begin{Package}{FIDE} -Author: Richard Liska\\ - -This package performs automation of the process of numerically -solving partial differential equations systems (PDES) by means of -computer algebra. For PDES solving, the finite difference method is applied. -The computer algebra system REDUCE and the numerical programming -language FORTRAN are used in the presented methodology. The main aim of -this methodology is to speed up the process of preparing numerical -programs for solving PDES. This process is quite often, especially for -complicated systems, a tedious and time consuming task. -\end{Package} - -\begin{Package}{GENTRAN} -\index{code generation}\index{FORTRAN}\index{C} -Author: Barbara L. Gates\\ - -This package is an automatic code GENerator and TRANslator. It constructs -complete numerical programs based on sets of algorithmic specifications and -symbolic expressions. Formatted FORTRAN, RATFOR or C code can be generated -through a series of interactive commands or under the control of a template -processing routine. Large expressions can be automatically segmented into -subexpressions of manageable size, and a special file-handling mechanism -maintains stacks of open I/O channels to allow output to be sent to any -number of files simultaneously and to facilitate recursive invocation of the -whole code generation process. -\end{Package} - -\begin{Package}{IDEALS} -\index{polynomial}\index{Groebner}\index{commutative algebra} -\index{ideal} -Author: Herbert Melenk\\ - -This package implements the basic arithmetic for polynomial ideals by -exploiting the Groebner bases package of REDUCE. In order to save -computing time all intermediate Groebner bases are stored internally such -that time consuming repetitions are inhibited. -\end{Package} - -\begin{Package}{INEQ} -\index{inequality} -Author: Herbert Melenk\\ - -This package supports the operator \name{ineq\_solve} that -tries to solves single inequalities and sets of coupled inequalities. -\end{Package} - -\begin{Package}{INVBASE} -Authors: A.Yu. Zharkov and Yu.A. Blinkov\\ - -Involutive bases are a new tool for solving problems in connection with -multivariate polynomials, such as solving systems of polynomial equations -and analyzing polynomial ideals. An involutive basis of polynomial ideal -is nothing but a special form of a redundant Groebner basis. The -construction of involutive bases reduces the problem of solving polynomial -systems to simple linear algebra. -\end{Package} - -\begin{Package}{LAPLACE} -\index{transform} -Authors: C. Kazasov, M. Spiridonova, V. Tomov\\ - -This package can calculate ordinary and inverse Laplace transforms of -expressions. Documentation is in plain text. -\end{Package} - -\begin{Package}{LIE} -Authors: Carsten and Franziska Sch{\"o}bel\\ - -\name{Lie} is a package of functions for the classification of real -n-dimensional Lie algebras. It consists of two modules: \name{liendmc1} -and \name{lie1234}. With the help of the functions in the \name{liendmcl} -module, real n-dimensional Lie algebras $L$ with a derived algebra -$L^{(1)}$ of dimension 1 can be classified. -\end{Package} - -\begin{Package}{MODSR} -\index{modular polynomial} -Author: Herbert Melenk\\ - -This package supports solve (M\_SOLVE) and roots (M\_ROOTS) operators for -modular polynomials and modular polynomial systems. The moduli need not -be primes. M\_SOLVE requires a modulus to be set. M\_ROOTS takes the -modulus as a second argument. For example: - -\begin{verbatim} -on modular; setmod 8; -m_solve(2x=4); -> {{X=2},{X=6}} -m_solve({x^2-y^3=3}); - -> {{X=0,Y=5}, {X=2,Y=1}, {X=4,Y=5}, {X=6,Y=1}} -m_solve({x=2,x^2-y^3=3}); -> {{X=2,Y=1}} -off modular; -m_roots(x^2-1,8); -> {1,3,5,7} -m_roots(x^3-x,7); -> {0,1,6} -\end{verbatim} -\end{Package} - -\begin{Package}{NCPOLY} -\index{non-commutativity} -Authors: Herbert Melenk, Joachim Apel\\ - -This package allows the user to set up automatically a consistent -environment for computing in an algebra where the non--commutativity is -defined by Lie-bracket commutators. The package uses the REDUCE -\name{noncom} mechanism for elementary polynomial arithmetic; the commutator -rules are automatically computed from the Lie brackets. -\end{Package} - -\begin{Package}{ORTHOVEC} -\index{vector algebra}\index{vector calculus}\index{Laplacian}\index{Taylor} -\index{cross product}\index{dot product}\index{div}\index{grad}\index{curl} -Author: James W. Eastwood\\ - -\name{orthovec} is a collection of REDUCE procedures and operations which -provide a simple-to-use environment for the manipulation of scalars and -vectors. Operations include addition, subtraction, dot and cross -products, division, modulus, div, grad, curl, laplacian, differentiation, -integration, and Taylor expansion. -\end{Package} - -\begin{Package}{PHYSOP} -Author: Mathias Warns\\ - -This package has been designed to meet the requirements of theoretical -physicists looking for a computer algebra tool to perform complicated -calculations in quantum theory with expressions containing operators. -These operations consist mainly of the calculation of commutators between -operator expressions and in the evaluations of operator matrix elements in -some abstract space. -\end{Package} - -\begin{Package}{PM} -\index{pattern matching} -Author: Kevin McIsaac\\ - -PM is a general pattern matcher similar in style to those found in systems -such as SMP and Mathematica, and is based on the pattern matcher described -in Kevin McIsaac, ``Pattern Matching Algebraic Identities'', SIGSAM Bulletin, -19 (1985), 4-13. -\end{Package} - -\begin{Package}{RANDPOLY} -\index{random polynomial} -Author: Francis J. Wright\\ - -This package is based on a port of the Maple random polynomial -generator together with some support facilities for the generation -of random numbers and anonymous procedures. -\end{Package} - -\begin{Package}{REACTEQN} -\index{chemical reaction} -Author: Herbert Melenk\\ - -This package allows a user to transform chemical reaction systems into -ordinary differential equation systems (ODE) corresponding to the laws of -pure mass action. -\end{Package} - -\begin{Package}{RESET} -Author: John Fitch\\ - -This package defines a command command RESETREDUCE that works through the -history of previous commands, and clears any values which have been -assigned, plus any rules, arrays and the like. It also sets the various -switches to their initial values. It is not complete, but does work for -most things that cause a gradual loss of space. It would be relatively -easy to make it interactive, so allowing for selective resetting. -\end{Package} - -\begin{Package}{RESIDUE} -Author: Wolfram Koepf\\ - -This package supports the calculation of residues of arbitrary -expressions. -\end{Package} - -\begin{Package}{RLFI} -\index{output}\index{TEX} -Author: Richard Liska\\ - -This package -adds \begin{TEX}\LaTeX \end{TEX}\begin{INFO}LaTeX \end{INFO} syntax -to REDUCE. Text generated by REDUCE in this mode can be directly -used in \begin{TEX}\LaTeX \end{TEX} \begin{INFO}LaTeX \end{INFO} source -documents. Various -mathematical constructions are supported by the interface including -subscripts, superscripts, font changing, Greek letters, divide-bars, -integral and sum signs, derivatives, and so on. -\end{Package} - -\begin{Package}{SCOPE} -\index{code generation}\index{optimization} -Author: J.A. van Hulzen\\ - -SCOPE is a package for the production of an optimized form of a set of -expressions. It applies an heuristic search for common (sub)expressions -to almost any set of proper REDUCE assignment statements. The output is -obtained as a sequence of assignment statements. \name{gentran} is used to -facilitate expression output. -\end{Package} - -\begin{Package}{SETS} -Author: Francis J. Wright\\ - -The SETS package provides algebraic-mode support for set operations on -lists regarded as sets (or representing explicit sets) and on implicit -sets represented by identifiers. -\end{Package} - -\begin{Package}{SPDE} -\index{differential equation}\index{Lie symmetry} -Author: Fritz Schwartz \\ - -The package \name{spde} provides a set of functions which may be used to -determine the symmetry group of Lie- or point-symmetries of a given system of -partial differential equations. In many cases the determining system is -solved completely automatically. In other cases the user has to provide -additional input information for the solution algorithm to terminate. -\end{Package} - -\begin{Package}{SYMMETRY} -Author: Karin Gatermann\\ - -This package computes symmetry-adapted bases and block diagonal forms of -matrices which have the symmetry of a group. The package is the -implementation of the theory of linear representations for small finite -groups such as the dihedral groups. -\end{Package} - - -\begin{Package}{TPS} -\index{power series}\index{Taylor series} -Authors: Alan Barnes, Julian Padget\\ - -This package implements formal Laurent series expansions in one variable -using the domain mechanism of REDUCE. This means that power series -objects can be added, multiplied, differentiated etc., like other first -class objects in the system. A lazy evaluation scheme is used and thus -terms of the series are not evaluated until they are required for printing -or for use in calculating terms in other power series. The series are -extendible giving the user the impression that the full infinite series is -being manipulated. The errors that can sometimes occur using series that -are truncated at some fixed depth (for example when a term in the required -series depends on terms of an intermediate series beyond the truncation -depth) are thus avoided. -\end{Package} - -\begin{Package}{TRI} -\index{output}\index{TEX} -Author: Werner Antweiler\\ - -This package provides facilities written in REDUCE-Lisp for typesetting -REDUCE formulas -using \begin{TEX}\TeX. \end{TEX} \begin{INFO}TeX. \end{INFO} The -TeX-REDUCE-Interface incorporates three levels -of \begin{TEX}\TeX \end{TEX} \begin{INFO}TeX \end{INFO} output: -without line breaking, with line breaking, and -with line breaking plus indentation. -\end{Package} - -\begin{Package}{TRIGSIMP} -\index{simplification} -Author: Wolfram Koepf\\ -TRIGSIMP is a useful tool for all kinds of trigonometric and hyperbolic -simplification and factorization. There are three procedures included in -TRIGSIMP: \name{trigsimp}, \name{trigfactorize} and \name{triggcd}. The -first is for finding simplifications of trigonometric or hyperbolic -expressions with many options, the second for factorizing them and the -third for finding the greatest common divisor of two trigonometric or -hyperbolic polynomials. -\end{Package} - -\begin{Package}{XCOLOR} -\index{high energy physics} -Author: A. Kryukov\\ - -This package calculates the color factor in non-abelian gauge field -theories using an algorithm due to Cvitanovich. -\end{Package} - -\begin{Package}{XIDEAL} -\index{Groebner basis} -Author: David Hartley\\ - -\name{xideal} constructs Groebner bases for solving the left ideal -membership problem: Groebner left ideal bases or GLIBs. For graded -ideals, where each form is homogeneous in degree, the distinction between -left and right ideals vanishes. Furthermore, if the generating forms are -all homogeneous, then the Groebner bases for the non-graded and graded -ideals are identical. In this case, \name{xideal} is able to save time by -truncating the Groebner basis at some maximum degree if desired. -\end{Package} - -\begin{Package}{WU} -\index{polynomial}\index{Wu-Wen-Tsun algorithm} -Author: Russell Bradford\\ - -This is a simple implementation of the Wu algorithm implemented in REDUCE -working directly from ``A Zero Structure Theorem for -Polynomial-Equations-Solving,'' Wu Wen-tsun, Institute of Systems Science, -Academia Sinica, Beijing. -\end{Package} - -\begin{Package}{ZEILBERG} -\index{summation} -Authors: Gregor St{\"o}lting and Wolfram Koepf\\ - -This package is a careful implementation of the Gosper and Zeilberger -algorithms for indefinite and definite summation of hypergeometric terms, -respectively. Extensions of these algorithms are also included that are -valid for ratios of products of powers, -factorials,\begin{TEX}$\Gamma$ \end{TEX} \begin{INFO}gamma \end{INFO}function -terms, binomial coefficients, and shifted factorials that are -rational-linear in their arguments. -\end{Package} - -\begin{Package}{ZTRANS} -Authors: Wolfram Koepf, Lisa Temme\\ - -This package is an implementation of the Z-transform of a sequence. -This is the discrete analogue of the Laplace Transform. -\end{Package} - +\section{Miscellaneous Packages} + +\begin{Introduction}{Miscellaneous Packages} +REDUCE includes a large number of packages that have been contributed by +users from various fields. Some of these, together with their relevant +commands, switches and so on (e.g., the NUMERIC package), have +been described elsewhere. This section describes those packages for which +no separate help material exists. Each has its own switches, commands, +and operators, and some redefine special characters to aid in their +notation. However, the brief descriptions given here do not include all +such information. Readers are referred to the general package +documentation in this case, which can be found, along with the source +code, under the subdirectories \name{doc} and \name{src} in the +\name{reduce} directory. The \nameref{load_package} command is used to +load the files you wish into your system. There will be a short delay +while the package is loaded. A package cannot be {\it unloaded}. Once it +is in your system, it stays there until you end the session. Each package +also has a test file, which you will find under its name in the +\name{\$reduce/xmpl} directory. + +Finally, it should be mentioned that such user-contributed packages are +unsupported; any questions or problems should be directed to their +authors. + +\end{Introduction} + +\begin{Package}{ALGINT} +\index{integration}\index{integration of square roots} +Author: James H. Davenport \\ + +The \name{algint} package provides indefinite integration of square roots. +This package, which is an extension of the basic integration package +distributed with REDUCE, will analytically integrate a wide range of +expressions involving square roots. The \nameref{algint} switch provides for +the use of the facilities given by the package, and is automatically turned +on when the package is loaded. If you want to return to the standard +integration algorithms, turn \nameref{algint} off. An error message is given +if you try to turn the \nameref{algint} switch on when its package is not +loaded. +\end{Package} + +\begin{Package}{APPLYSYM} +\index{differential equations} \index{symmetries} +Author: Thomas Wolf \\ + +This package provides programs APPLYSYM, QUASILINPDE and DETRAFO for +computing with infinitesimal symmetries of differential equations. +\end{Package} + +\begin{Package}{ARNUM} +\index{algebraic numbers} +Author: Eberhard Schruefer\\ + +This package provides facilities for handling algebraic numbers as polynomial +coefficients in REDUCE calculations. It includes facilities for introducing +indeterminates to represent algebraic numbers, for calculating splitting +fields, and for factoring and finding greatest common divisors in such +domains. +\end{Package} + +\begin{Package}{ASSIST} +\index{utilities} +Author: Hubert Caprasse\\ + +ASSIST contains a large number of additional general purpose functions +that allow a user to better adapt REDUCE to various calculational +strategies and to make the programming task more straightforward and more +efficient. +\end{Package} + +\begin{Package}{AVECTOR} +\index{vector algebra}\index{cross product}\index{dot product} +Author: David Harper\\ + +This package provides REDUCE with the ability to perform vector algebra +using the same notation as scalar algebra. The basic algebraic operations +are supported, as are differentiation and integration of vectors with +respect to scalar variables, cross product and dot product, component +manipulation and application of scalar functions (e.g. cosine) to a vector +to yield a vector result. +\end{Package} + +\begin{Package}{BOOLEAN} +\index{boolean expressions} +Author: Herbert Melenk\\ + +This package supports the computation with boolean expressions in the +propositional calculus. The data objects are composed from algebraic +expressions connected by the infix boolean operators {\bf and}, {\bf or}, +{\bf implies}, {\bf equiv}, and the unary prefix operator {\bf not}. +{\bf Boolean} allows you to simplify expressions built from these +operators, and to test properties like equivalence, subset property etc. +\end{Package} + +\begin{Package}{CALI} +\index{polynomial}\index{Groebner}\index{commutative algebra} +Author: Hans-Gert Gr{\"a}be \\ + +This package contains algorithms for computations in commutative algebra +closely related to the Groebner algorithm for ideals and modules. Its +heart is a new implementation of the Groebner algorithm that also allows +for the computation of syzygies. This implementation is also applicable to +submodules of free modules with generators represented as rows of a matrix. +\end{Package} + +\begin{Package}{CAMAL} +\index{celestial mechanics}\index{Fourier series} +Author: John P. Fitch\\ + +This packages implements in REDUCE the Fourier transform procedures of the +CAMAL package for celestial mechanics. +\end{Package} + +\begin{Package}{CHANGEVR} +Author: G. Ucoluk\\ + +This package provides facilities for changing the independent variables in +a differential equation. It is basically the application of the chain rule. +\end{Package} + +\begin{Package}{COMPACT} +\index{simplification} +Author: Anthony C. Hearn\\ + +COMPACT is a package of functions for the reduction of a polynomial in the +presence of side relations. COMPACT applies the side relations to the +polynomial so that an equivalent expression results with as few terms as +possible. For example, the evaluation of + +\begin{verbatim} + compact(s*(1-sin x^2)+c*(1-cos x^2)+sin x^2+cos x^2, + {cos x^2+sin x^2=1}); + +\end{verbatim} +yields the result +\begin{verbatim} + + 2 2 + SIN(X) *C + COS(X) *S + 1 +\end{verbatim} + +The first argument to the operator \name{compact} is the expression +and the second is a list of side relations that can be +equations or simple expressions (implicitly equated to zero). The +kernels in the side relations may also be free variables with the +same meaning as in rules, e.g. +\begin{verbatim} + sin_cos_identity := {cos ~w^2+sin ~w^2=1}$ + compact(u,in_cos_identity); +\end{verbatim} +Also the full rule syntax with the replacement operator is allowed here. +\end{Package} + +\begin{Package}{CONTFR} +\index{continued fraction} +Author: Herbert Melenk\\ + +This package provides for the simultaneous approximation of a real number +by a continued fraction and a rational number with optional user +controlled precision (an upper bound for the denominator). + +To use this package, the \name{misc} package should be loaded. One can then +use the operator \name{continued\_fraction} to approximate the real +number by a continued fraction. This operator has one or two arguments, the +number to be converted and an optional precision. The result is a list of +two elements: the first is the rational value of the approximation and the +second the list of terms of the continued fraction that represent the same +value according to the definition \verb&t0 +1/(t1 + 1/(t2 + ...))&. The +second optional parameter \name{size} is an upper bound on the absolute +value of the result denominator. If omitted, the approximation is performed +up to the current system precision. + +\begin{Examples} +continued\_fraction pi; & +\begin{multilineoutput}{6cm} + 1146408 +\{---------,\{3,7,15,1,292,1,1,1,2,1\}\} + 364913 +\end{multilineoutput} \\ + +continued\_fraction(pi,100); & +\begin{multilineoutput}{6cm} + 22 +\{----,\{3,7\}\} + 7 +\end{multilineoutput} +\end{Examples} +\end{Package} + +\begin{Package}{CRACK} +\index{differential equation} +Authors: Andreas Brand, Thomas Wolf\\ + +CRACK is a package for solving overdetermined systems of partial or +ordinary differential equations (PDEs, ODEs). Examples of programs which +make use of CRACK for investigating ODEs (finding symmetries, first +integrals, an equivalent Lagrangian or a ``differential factorization'') are +included. +\end{Package} + +\begin{Package}{CVIT} +\index{Dirac algebra} +Authors: V.Ilyin, A.Kryukov, A.Rodionov, A.Taranov\\ + +This package provides an alternative method for computing traces of Dirac +gamma matrices, based on an algorithm by Cvitanovich that treats gamma +matrices as 3-j symbols. +\end{Package} + +\begin{Package}{DEFINT} +\index{definite integration} +Authors: Kerry Gaskell, Stanley M. Kameny, Winfried Neun\\ + +This package finds the definite integral of an expression in a stated +interval. It uses several techniques, including an innovative approach +based on the Meijer G-function, and contour integration. +\end{Package} + +\begin{Package}{DESIR} +\index{differential equation} +Authors: C. Dicrescenzo, F. Richard-Jung, E. Tournier\\ + +This package enables the basis of formal solutions to be computed for an +ordinary homogeneous differential equation with polynomial coefficients +over Q of any order, in the neighborhood of zero (regular or irregular +singular point, or ordinary point). +\end{Package} + +\begin{Package}{DFPART} +\index{partial derivative} +Author: Herbert Melenk\\ + +This package supports computations with total and partial derivatives of +formal function objects. Such computations can be useful in the context +of differential equations or power series expansions. +\end{Package} + +\begin{Package}{DUMMY} +\index{dummy variable} +Author: Alain Dresse\\ + +This package allows a user to find the canonical form of expressions +involving dummy variables. In that way, the simplification of +polynomial expressions can be fully done. The indeterminates are general +operator objects endowed with as few properties as possible. In that way +the package may be used in a large spectrum of applications. +\end{Package} + +\begin{Package}{EXCALC} +\index{exterior calculus}\index{differential calculus} +\index{differential form} +Author: Eberhard Schruefer\\ + +The \name{excalc} package is designed for easy use by all who are familiar +with the calculus of Modern Differential Geometry. The program is currently +able to handle scalar-valued exterior forms, vectors and operations between +them, as well as non-scalar valued forms (indexed forms). It is thus an ideal +tool for studying differential equations, doing calculations in general +relativity and field theories, or doing simple things such as calculating the +Laplacian of a tensor field for an arbitrary given frame. +\end{Package} + +\begin{Package}{FPS} +\index{power series} \index{Laurent-Puiseux series} +Authors: Wolfram Koepf, Winfried Neun\\ + +This package can expand a specific class of functions into their +corresponding Laurent-Puiseux series. +\end{Package} + +\begin{Package}{FIDE} +Author: Richard Liska\\ + +This package performs automation of the process of numerically +solving partial differential equations systems (PDES) by means of +computer algebra. For PDES solving, the finite difference method is applied. +The computer algebra system REDUCE and the numerical programming +language FORTRAN are used in the presented methodology. The main aim of +this methodology is to speed up the process of preparing numerical +programs for solving PDES. This process is quite often, especially for +complicated systems, a tedious and time consuming task. +\end{Package} + +\begin{Package}{GENTRAN} +\index{code generation}\index{FORTRAN}\index{C} +Author: Barbara L. Gates\\ + +This package is an automatic code GENerator and TRANslator. It constructs +complete numerical programs based on sets of algorithmic specifications and +symbolic expressions. Formatted FORTRAN, RATFOR or C code can be generated +through a series of interactive commands or under the control of a template +processing routine. Large expressions can be automatically segmented into +subexpressions of manageable size, and a special file-handling mechanism +maintains stacks of open I/O channels to allow output to be sent to any +number of files simultaneously and to facilitate recursive invocation of the +whole code generation process. +\end{Package} + +\begin{Package}{IDEALS} +\index{polynomial}\index{Groebner}\index{commutative algebra} +\index{ideal} +Author: Herbert Melenk\\ + +This package implements the basic arithmetic for polynomial ideals by +exploiting the Groebner bases package of REDUCE. In order to save +computing time all intermediate Groebner bases are stored internally such +that time consuming repetitions are inhibited. +\end{Package} + +\begin{Package}{INEQ} +\index{inequality} +Author: Herbert Melenk\\ + +This package supports the operator \name{ineq\_solve} that +tries to solves single inequalities and sets of coupled inequalities. +\end{Package} + +\begin{Package}{INVBASE} +Authors: A.Yu. Zharkov and Yu.A. Blinkov\\ + +Involutive bases are a new tool for solving problems in connection with +multivariate polynomials, such as solving systems of polynomial equations +and analyzing polynomial ideals. An involutive basis of polynomial ideal +is nothing but a special form of a redundant Groebner basis. The +construction of involutive bases reduces the problem of solving polynomial +systems to simple linear algebra. +\end{Package} + +\begin{Package}{LAPLACE} +\index{transform} +Authors: C. Kazasov, M. Spiridonova, V. Tomov\\ + +This package can calculate ordinary and inverse Laplace transforms of +expressions. Documentation is in plain text. +\end{Package} + +\begin{Package}{LIE} +Authors: Carsten and Franziska Sch{\"o}bel\\ + +\name{Lie} is a package of functions for the classification of real +n-dimensional Lie algebras. It consists of two modules: \name{liendmc1} +and \name{lie1234}. With the help of the functions in the \name{liendmcl} +module, real n-dimensional Lie algebras $L$ with a derived algebra +$L^{(1)}$ of dimension 1 can be classified. +\end{Package} + +\begin{Package}{MODSR} +\index{modular polynomial} +Author: Herbert Melenk\\ + +This package supports solve (M\_SOLVE) and roots (M\_ROOTS) operators for +modular polynomials and modular polynomial systems. The moduli need not +be primes. M\_SOLVE requires a modulus to be set. M\_ROOTS takes the +modulus as a second argument. For example: + +\begin{verbatim} +on modular; setmod 8; +m_solve(2x=4); -> {{X=2},{X=6}} +m_solve({x^2-y^3=3}); + -> {{X=0,Y=5}, {X=2,Y=1}, {X=4,Y=5}, {X=6,Y=1}} +m_solve({x=2,x^2-y^3=3}); -> {{X=2,Y=1}} +off modular; +m_roots(x^2-1,8); -> {1,3,5,7} +m_roots(x^3-x,7); -> {0,1,6} +\end{verbatim} +\end{Package} + +\begin{Package}{NCPOLY} +\index{non-commutativity} +Authors: Herbert Melenk, Joachim Apel\\ + +This package allows the user to set up automatically a consistent +environment for computing in an algebra where the non--commutativity is +defined by Lie-bracket commutators. The package uses the REDUCE +\name{noncom} mechanism for elementary polynomial arithmetic; the commutator +rules are automatically computed from the Lie brackets. +\end{Package} + +\begin{Package}{ORTHOVEC} +\index{vector algebra}\index{vector calculus}\index{Laplacian}\index{Taylor} +\index{cross product}\index{dot product}\index{div}\index{grad}\index{curl} +Author: James W. Eastwood\\ + +\name{orthovec} is a collection of REDUCE procedures and operations which +provide a simple-to-use environment for the manipulation of scalars and +vectors. Operations include addition, subtraction, dot and cross +products, division, modulus, div, grad, curl, laplacian, differentiation, +integration, and Taylor expansion. +\end{Package} + +\begin{Package}{PHYSOP} +Author: Mathias Warns\\ + +This package has been designed to meet the requirements of theoretical +physicists looking for a computer algebra tool to perform complicated +calculations in quantum theory with expressions containing operators. +These operations consist mainly of the calculation of commutators between +operator expressions and in the evaluations of operator matrix elements in +some abstract space. +\end{Package} + +\begin{Package}{PM} +\index{pattern matching} +Author: Kevin McIsaac\\ + +PM is a general pattern matcher similar in style to those found in systems +such as SMP and Mathematica, and is based on the pattern matcher described +in Kevin McIsaac, ``Pattern Matching Algebraic Identities'', SIGSAM Bulletin, +19 (1985), 4-13. +\end{Package} + +\begin{Package}{RANDPOLY} +\index{random polynomial} +Author: Francis J. Wright\\ + +This package is based on a port of the Maple random polynomial +generator together with some support facilities for the generation +of random numbers and anonymous procedures. +\end{Package} + +\begin{Package}{REACTEQN} +\index{chemical reaction} +Author: Herbert Melenk\\ + +This package allows a user to transform chemical reaction systems into +ordinary differential equation systems (ODE) corresponding to the laws of +pure mass action. +\end{Package} + +\begin{Package}{RESET} +Author: John Fitch\\ + +This package defines a command command RESETREDUCE that works through the +history of previous commands, and clears any values which have been +assigned, plus any rules, arrays and the like. It also sets the various +switches to their initial values. It is not complete, but does work for +most things that cause a gradual loss of space. It would be relatively +easy to make it interactive, so allowing for selective resetting. +\end{Package} + +\begin{Package}{RESIDUE} +Author: Wolfram Koepf\\ + +This package supports the calculation of residues of arbitrary +expressions. +\end{Package} + +\begin{Package}{RLFI} +\index{output}\index{TEX} +Author: Richard Liska\\ + +This package +adds \begin{TEX}\LaTeX \end{TEX}\begin{INFO}LaTeX \end{INFO} syntax +to REDUCE. Text generated by REDUCE in this mode can be directly +used in \begin{TEX}\LaTeX \end{TEX} \begin{INFO}LaTeX \end{INFO} source +documents. Various +mathematical constructions are supported by the interface including +subscripts, superscripts, font changing, Greek letters, divide-bars, +integral and sum signs, derivatives, and so on. +\end{Package} + +\begin{Package}{SCOPE} +\index{code generation}\index{optimization} +Author: J.A. van Hulzen\\ + +SCOPE is a package for the production of an optimized form of a set of +expressions. It applies an heuristic search for common (sub)expressions +to almost any set of proper REDUCE assignment statements. The output is +obtained as a sequence of assignment statements. \name{gentran} is used to +facilitate expression output. +\end{Package} + +\begin{Package}{SETS} +Author: Francis J. Wright\\ + +The SETS package provides algebraic-mode support for set operations on +lists regarded as sets (or representing explicit sets) and on implicit +sets represented by identifiers. +\end{Package} + +\begin{Package}{SPDE} +\index{differential equation}\index{Lie symmetry} +Author: Fritz Schwartz \\ + +The package \name{spde} provides a set of functions which may be used to +determine the symmetry group of Lie- or point-symmetries of a given system of +partial differential equations. In many cases the determining system is +solved completely automatically. In other cases the user has to provide +additional input information for the solution algorithm to terminate. +\end{Package} + +\begin{Package}{SYMMETRY} +Author: Karin Gatermann\\ + +This package computes symmetry-adapted bases and block diagonal forms of +matrices which have the symmetry of a group. The package is the +implementation of the theory of linear representations for small finite +groups such as the dihedral groups. +\end{Package} + + +\begin{Package}{TPS} +\index{power series}\index{Taylor series} +Authors: Alan Barnes, Julian Padget\\ + +This package implements formal Laurent series expansions in one variable +using the domain mechanism of REDUCE. This means that power series +objects can be added, multiplied, differentiated etc., like other first +class objects in the system. A lazy evaluation scheme is used and thus +terms of the series are not evaluated until they are required for printing +or for use in calculating terms in other power series. The series are +extendible giving the user the impression that the full infinite series is +being manipulated. The errors that can sometimes occur using series that +are truncated at some fixed depth (for example when a term in the required +series depends on terms of an intermediate series beyond the truncation +depth) are thus avoided. +\end{Package} + +\begin{Package}{TRI} +\index{output}\index{TEX} +Author: Werner Antweiler\\ + +This package provides facilities written in REDUCE-Lisp for typesetting +REDUCE formulas +using \begin{TEX}\TeX. \end{TEX} \begin{INFO}TeX. \end{INFO} The +TeX-REDUCE-Interface incorporates three levels +of \begin{TEX}\TeX \end{TEX} \begin{INFO}TeX \end{INFO} output: +without line breaking, with line breaking, and +with line breaking plus indentation. +\end{Package} + +\begin{Package}{TRIGSIMP} +\index{simplification} +Author: Wolfram Koepf\\ +TRIGSIMP is a useful tool for all kinds of trigonometric and hyperbolic +simplification and factorization. There are three procedures included in +TRIGSIMP: \name{trigsimp}, \name{trigfactorize} and \name{triggcd}. The +first is for finding simplifications of trigonometric or hyperbolic +expressions with many options, the second for factorizing them and the +third for finding the greatest common divisor of two trigonometric or +hyperbolic polynomials. +\end{Package} + +\begin{Package}{XCOLOR} +\index{high energy physics} +Author: A. Kryukov\\ + +This package calculates the color factor in non-abelian gauge field +theories using an algorithm due to Cvitanovich. +\end{Package} + +\begin{Package}{XIDEAL} +\index{Groebner basis} +Author: David Hartley\\ + +\name{xideal} constructs Groebner bases for solving the left ideal +membership problem: Groebner left ideal bases or GLIBs. For graded +ideals, where each form is homogeneous in degree, the distinction between +left and right ideals vanishes. Furthermore, if the generating forms are +all homogeneous, then the Groebner bases for the non-graded and graded +ideals are identical. In this case, \name{xideal} is able to save time by +truncating the Groebner basis at some maximum degree if desired. +\end{Package} + +\begin{Package}{WU} +\index{polynomial}\index{Wu-Wen-Tsun algorithm} +Author: Russell Bradford\\ + +This is a simple implementation of the Wu algorithm implemented in REDUCE +working directly from ``A Zero Structure Theorem for +Polynomial-Equations-Solving,'' Wu Wen-tsun, Institute of Systems Science, +Academia Sinica, Beijing. +\end{Package} + +\begin{Package}{ZEILBERG} +\index{summation} +Authors: Gregor St{\"o}lting and Wolfram Koepf\\ + +This package is a careful implementation of the Gosper and Zeilberger +algorithms for indefinite and definite summation of hypergeometric terms, +respectively. Extensions of these algorithms are also included that are +valid for ratios of products of powers, +factorials,\begin{TEX}$\Gamma$ \end{TEX} \begin{INFO}gamma \end{INFO}function +terms, binomial coefficients, and shifted factorials that are +rational-linear in their arguments. +\end{Package} + +\begin{Package}{ZTRANS} +Authors: Wolfram Koepf, Lisa Temme\\ + +This package is an implementation of the Z-transform of a sequence. +This is the discrete analogue of the Laplace Transform. +\end{Package} +  Index: r36/help/pk-specf.tex ================================================================== --- r36/help/pk-specf.tex +++ r36/help/pk-specf.tex @@ -1,1600 +1,1600 @@ -\section{Special Functions} -\begin{Introduction}{Special Function Package} -The REDUCE \name{Special Function Package} supplies extended -algebraic and numeric support for a wide class of objects. -This package was released together with REDUCE 3.5 (October 1993) -for the first time, a major update is released with REDUCE 3.6.\\ -\\ - -The functions included in this package are in most cases (unless otherwise -stated) defined and named like in the book by Abramowitz and Stegun: -Handbook of Mathematical Functions, Dover Publications.\\ - \\ - -The aim is to collect as much information on the special functions -and simplification capabilities as possible, -i.e. algebraic simplifications and numeric (rounded mode) code, limits -of the functions together -with the definitions of the functions, which are in most cases a power -series, a (definite) integral and/or a differential equation.\\ - \\ - -\em{What can be found:} Some famous constants, a variety of Bessel functions, -special polynomials, -the Gamma function, the (Riemann) Zeta function, Elliptic Functions, Elliptic -Integrals, 3J symbols (Clebsch-Gordan coefficients) and integral functions.\\ - \\ - -\em{What is missing:} Mathieu functions, LerchPhi, etc.. -The information about the special functions which solve certain -differential equation is very limited. -In several cases numerical approximation is restricted to real -arguments or is missing completely.\\ - \\ - -The implementation of this package uses REDUCE rule sets to a large extent, -which guarantees a high 'readability' of the functions definitions in the -source file directory. It makes extensions to the special -functions code easy in most cases too. To look at these rules -it may be convenient to use the showrules operator e.g.\\ - \\ - \nameref{showrules} Besseli;\\ -.\\ - -Some evaluations are improved if the special function package is loaded, -e.g. some (infinite) sums and products leading to expressions including -special functions are known in this case.\\ -\\ - -Note: The special function package has to be loaded explicitly by calling -\begin{verbatim} - load_package specfn; -\end{verbatim} -The functions \nameref{MeijerG} and \nameref{hypergeometric} require -additionally -\begin{verbatim} - load_package specfn2; -\end{verbatim} - -\end{Introduction} - -\begin{Concept}{Constants} -\index{Euler's constant}\index{Catalan's constant}\index{Khinchin's constant} -\index{Golden_Ratio} - -There are a few constants known to the special function package, namely\\ -\\ -\name{Euler's constant} (which can be computed as -\nameref{Psi}(1)) and \\ -\name{Khinchin's constant} (which is defined in Khinchin's book \\ - ``Continued Fractions'') and \\ -\name{Golden_Ratio} (which can be computed as (1 + sqrt 5)/2) and \\ -\name{Catalan's constant} (which is known as an infinite sum of reciprocal -powers) - -\begin{Examples} -on rounded; -Euler_Gamma; & 0.577215664902 \\ -Khinchin; & 2.68545200107 \\ -Catalan & 0.915965594177 \\ -Golden_Ratio & 1.61803398875 -\end{Examples} - -\end{Concept} - -\subsection{Bernoulli Euler Zeta} - -\begin{Operator}{BERNOULLI} -The \name{bernoulli} operator returns the nth Bernoulli number. - -\begin{Syntax} - -\name{Bernoulli}\(\meta{integer}\) - -\end{Syntax} - -\begin{Examples} -bernoulli 20; & - 174611 / 330 \\ -bernoulli 17; & 0 -\end{Examples} - -\begin{Comments} -All Bernoulli numbers with odd indices except for 1 are zero. -\end{Comments} -\end{Operator} - -\begin{Operator}{BERNOULLIP} -The \name{BernoulliP} operator returns the nth Bernoulli Polynomial -evaluated at x. - -\begin{Syntax} - -\name{BernoulliP}\(\meta{integer},\meta{expression}\) - -\end{Syntax} - -\begin{Examples} -BernoulliP(3,z); & z*(2*z^2 - 3*z + 1)/2\\ - -BernoulliP(10,3); & 338585 / 66 -\end{Examples} - -\begin{Comments} -The value of the nth Bernoulli Polynomial at 0 is the nth Bernoulli number. -\end{Comments} -\end{Operator} - -\begin{Operator}{EULER} -The \name{EULER} operator returns the nth Euler number. - -\begin{Syntax} -\name{Euler}\(\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Euler 20; & 370371188237525 \\ -Euler 0; & 1 -\end{Examples} - -\begin{Comments} -The \name{Euler} numbers are evaluated by a recursive algorithm which -makes it hard to compute Euler numbers above say 200. - -Euler numbers appear in the coefficients of the power series -representation of 1/cos(z). -\end{Comments} -\end{Operator} - -\begin{Operator}{EULERP} -The \name{EulerP} operator returns the nth Euler Polynomial. - -\begin{Syntax} -\name{EulerP}\(\meta{integer},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -EulerP(2,xx); & xx*(xx - 1) \\ -EulerP(10,3); & 2046 -\end{Examples} - -\begin{Comments} -The Euler numbers are the values of the Euler Polynomials at 1/2 -multiplied by 2**n. -\end{Comments} -\end{Operator} - -\begin{Operator}{ZETA} -The \name{Zeta} operator returns Riemann's Zeta function, - - Zeta (z) := sum(1/(k**z),k,1,infinity) - -\begin{Syntax} -\name{Zeta}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -Zeta(2); & pi^2 / 6 \\ -on rounded; \\ -Zeta 1.01; & 100.577943338 -\end{Examples} - -\begin{Comments} -Numerical computation for the Zeta function for arguments close to 1 are -tedious, because the series is converging very slowly. In this case a formula -(e.g. found in Bender/Orzag: Advanced Mathematical Methods for -Scientists and Engineers, McGraw-Hill) is used. - -No numerical approximation for complex arguments is done. -\end{Comments} - -\end{Operator} -\subsection{Bessel Functions} - -\begin{Operator}{BESSELJ} -The \name{BesselJ} operator returns the Bessel function of the first kind. - -\begin{Syntax} -\name{BesselJ}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -BesselJ(1/2,pi); & 0 \\ -on rounded; \\ -BesselJ(0,1); & 0.765197686558 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{BESSELY} -\index{Weber's function} -The \name{BesselY} operator returns the Bessel function of the second kind. -\begin{Syntax} -\name{BesselY}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -BesselY (1/2,pi); & - sqrt(2) / pi \\ -on rounded; \\ -BesselY (1,3); & 0.324674424792 -\end{Examples} - -\begin{Comments} -The operator \name{BesselY} is also called Weber's function. -\end{Comments} -\end{Operator} - -\begin{Operator}{HANKEL1} -The \name{Hankel1} operator returns the Hankel function of the first kind. - -\begin{Syntax} -\name{Hankel1}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -on complex; \\ -Hankel1 (1/2,pi); & - i * sqrt(2) / pi \\ -Hankel1 (1,pi); & besselj(1,pi) + i*bessely(1,pi) - -\end{Examples} - -\begin{Comments} -The operator \name{Hankel1} is also called Bessel function of the third kind. -There is currently no numeric evaluation of Hankel functions. -\end{Comments} -\end{Operator} - -\begin{Operator}{HANKEL2} -The \name{Hankel2} operator returns the Hankel function of the second kind. - -\begin{Syntax} -\name{Hankel2}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -on complex; \\ -Hankel2 (1/2,pi); & - i * sqrt(2) / pi \\ -Hankel2 (1,pi); & besselj(1,pi) - i*bessely(1,pi) -\end{Examples} - -\begin{Comments} -The operator \name{Hankel2} is also called Bessel function of the third kind. -There is currently no numeric evaluation of Hankel functions. -\end{Comments} -\end{Operator} - -\begin{Operator}{BESSELI} -The \name{BesselI} operator returns the modified Bessel function I. - -\begin{Syntax} -\name{BesselI}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -on rounded; \\ -Besseli (1,1); & 0.565159103992 -\end{Examples} - -\begin{Comments} -The knowledge about the operator \name{BesselI} is currently fairly limited. -\end{Comments} -\end{Operator} - -\begin{Operator}{BESSELK} -The \name{BesselK} operator returns the modified Bessel function K. - -\begin{Syntax} -\name{BesselK}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -df(besselk(0,x),x); & - besselk(1,x) -\end{Examples} - -\begin{Comments} -There is currently no numeric support for the operator \name{BesselK}. -\end{Comments} -\end{Operator} - -\begin{Operator}{StruveH} -The \name{StruveH} operator returns Struve's H function. - -\begin{Syntax} -\name{StruveH}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -struveh(-3/2,x); & - besselj(3/2,x) / i -\end{Examples} - -\end{Operator} - -\begin{Operator}{StruveL} -The \name{StruveL} operator returns the modified Struve L function . - -\begin{Syntax} -\name{StruveL}\(\meta{order},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -struvel(-3/2,x); & besseli(3/2,x) -\end{Examples} - -\end{Operator} - -\begin{Operator}{KummerM} -\index{Confluent Hypergeometric function} -The \name{KummerM} operator returns Kummer's M function. - -\begin{Syntax} -\name{KummerM}\(\meta{parameter},\meta{parameter},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -kummerm(1,1,x); & e^x \\ -on rounded; \\ -kummerm(1,3,1.3); & 1.62046942914 -\end{Examples} - -\begin{Comments} -Kummer's M function is one of the Confluent Hypergeometric functions. -For reference see the \nameref{hypergeometric} operator. -\end{Comments} -\end{Operator} - -\begin{Operator}{KummerU} -\index{Confluent Hypergeometric function} -The \name{KummerU} operator returns Kummer's U function. - -\begin{Syntax} -\name{KummerU}\(\meta{parameter},\meta{parameter},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -df(kummeru(1,1,x),x) & - kummeru(2,2,x) -\end{Examples} - -\begin{Comments} -Kummer's U function is one of the Confluent Hypergeometric functions. -For reference see the \nameref{hypergeometric} operator. -\end{Comments} -\end{Operator} - -\begin{Operator}{WhittakerW} -\index{Confluent Hypergeometric function} -The \name{WhittakerW} operator returns Whittaker's W function. - -\begin{Syntax} -\name{WhittakerW}\(\meta{parameter},\meta{parameter},\meta{argument}\) -\end{Syntax} - -\begin{Examples} -WhittakerW(2,2,2); & \rfrac{4*sqrt(2)*kummeru(\rfrac{1}{2},5,2)}{e} -\end{Examples} - -\begin{Comments} -Whittaker's W function is one of the Confluent Hypergeometric functions. -For reference see the \nameref{hypergeometric} operator. -\end{Comments} -\end{Operator} - -\subsection{Airy Functions} - -\begin{Operator}{Airy_Ai} -The \name{Airy\_Ai} operator returns the Airy Ai function for a given argument. - -\begin{Syntax} -\name{Airy\_Ai}\(\meta{argument}\) -\end{Syntax} - -\begin{Examples} -on complex; -on rounded; -Airy_Ai(0); & 0.355028053888 \\ -Airy_Ai(3.45 + 17.97i); & - 5.5561528511e+9 - 8.80397899932e+9*i \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{Airy_Bi} -The \name{Airy\_Bi} operator returns the Airy Bi function for a given -argument. - -\begin{Syntax} -\name{Airy\_Bi}\(\meta{argument}\) -\end{Syntax} - -\begin{Examples} -Airy_Bi(0); & 0.614926627446 \\ -Airy_Bi(3.45 + 17.97i); & 8.80397899932e+9 - 5.5561528511e+9*i \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{Airy_Aiprime} -The \name{Airy\_Aiprime} operator returns the Airy Aiprime function for a -given argument. - -\begin{Syntax} -\name{Airy\_Aiprime}\(\meta{argument}\) -\end{Syntax} - -\begin{Examples} -Airy_Aiprime(0); & - 0.258819403793 \\ -Airy_Aiprime(3.45+17.97i);& - 3.83386421824e+19 + 2.16608828136e+19*i \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{Airy_Biprime} -The \name{Airy\_Biprime} operator returns the Airy Biprime function for a -given argument. - -\begin{Syntax} -\name{Airy\_Biprime}\(\meta{argument}\) -\end{Syntax} - -\begin{Examples} -Airy_Biprime(0); & \\ -Airy_Biprime(3.45 + 17.97i); & 3.84251916792e+19 - 2.18006297399e+19*i\\ -\end{Examples} - -\end{Operator} - -\subsection{Jacobi's Elliptic Functions and Elliptic Integrals} - -\begin{Operator}{JacobiSN} -The \name{Jacobisn} operator returns the Jacobi Elliptic function sn. - -\begin{Syntax} -\name{Jacobisn}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobisn(0.672, 0.36) & 0.609519691792 \\ -Jacobisn(1,0.9) & 0.770085724907881 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiCN} -The \name{Jacobicn} operator returns the Jacobi Elliptic function cn. - -\begin{Syntax} -\name{Jacobicn}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobicn(7.2, 0.6) & 0.837288298482018 \\ -Jacobicn(0.11, 19) & 0.994403862690043 - 1.6219006985556e-16*i \\ -\end{Examples} - -\end{Operator} - - -\begin{Operator}{JacobiDN} -The \name{Jacobidn} operator returns the Jacobi Elliptic function dn. - -\begin{Syntax} -\name{Jacobidn}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobidn(15, 0.683) & 0.640574162024592 \\ -Jacobidn(0,0) & 1 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiCD} -The \name{Jacobicd} operator returns the Jacobi Elliptic function cd. - -\begin{Syntax} -\name{Jacobicd}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobicd(1, 0.34) & 0.657683337805273 \\ -Jacobicd(0.8,0.8) & 0.925587311582301 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiSD} -The \name{Jacobisd} operator returns the Jacobi Elliptic function sd. - -\begin{Syntax} -\name{Jacobisd}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobisd(12, 0.4) & 0.357189729437272 \\ -Jacobisd(0.35,1) & - 1.17713873203043 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiND} -The \name{Jacobind} operator returns the Jacobi Elliptic function nd. - -\begin{Syntax} -\name{Jacobind}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobind(0.2, 17) & 1.46553203037507 + 0.0000000000334032759313703*i \\ -Jacobind(30, 0.001) & 1.00048958438 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiDC} -The \name{Jacobidc} operator returns the Jacobi Elliptic function dc. - -\begin{Syntax} -\name{Jacobidc}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobidc(0.003,1) & 1 \\ -Jacobidc(2, 0.75) & 6.43472885111 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiNC} -The \name{Jacobinc} operator returns the Jacobi Elliptic function nc. - -\begin{Syntax} -\name{Jacobinc}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobinc(1,0) & 1.85081571768093 \\ -Jacobinc(56, 0.4387) & 39.304842663512 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiSC} -The \name{Jacobisc} operator returns the Jacobi Elliptic function sc. - -\begin{Syntax} -\name{Jacobisc}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobisc(9, 0.88) & - 1.16417697982095 \\ -Jacobisc(0.34, 7) & 0.305851938390775 - 9.8768100944891e-12*i \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiNS} -The \name{Jacobins} operator returns the Jacobi Elliptic function ns. - -\begin{Syntax} -\name{Jacobins}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobins(3, 0.9) & 1.00945801599785 \\ -Jacobins(0.887, 15) & 0.683578280513975 - 0.85023411082469*i \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiDS} -The \name{Jacobisn} operator returns the Jacobi Elliptic function ds. - -\begin{Syntax} -\name{Jacobids}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobids(98,0.223) & - 1.061253961477 \\ -Jacobids(0.36,0.6) & 2.76693172243692 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiCS} -The \name{Jacobics} operator returns the Jacobi Elliptic function cs. - -\begin{Syntax} -\name{Jacobics}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Jacobics(0, 0.767) & infinity \\ -Jacobics(1.43, 0) & 0.141734127352112 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{JacobiAMPLITUDE} -The \name{JacobiAmplitude} operator returns the amplitude of u. -\begin{Syntax} -\name{JacobiAmplitude}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -JacobiAmplitude(7.239, 0.427) & 0.0520978301448978 \\ -JacobiAmplitude(0,0.1) & 0 \\ -\end{Examples} - -\begin{Comments} -Amplitude u = asin(\name{Jacobisn(u,m)}) -\end{Comments} -\end{Operator} - - -\begin{Operator}{AGM_FUNCTION} -The \name{AGM_function} operator returns a list of (N, AGM, - list of aNtoa0, list of bNtob0, list of cNtoc0) where a0, b0 and c0 -are the initial values; N is the index number of the last term -used to generate the AGM. AGM is the Arithmetic Geometric Mean. - -\begin{Syntax} -\name{AGM_function}\(\meta{integer},\meta{integer},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -AGM_function(1,1,1) & {1,1,{1,1},{1,1},{0,1}} \\ -AGM_function(1, 0.1, 1.3) & -\begin{multilineoutput}{6cm} -\{6, - 2.27985615996629, - \{2.27985615996629, 2.27985615996629, - 2.2798561599706, 2.2798624278857, - 2.28742283656583, 2.55, 1\}, - \{2.27985615996629, 2.27985615996629, - 2.27985615996198, 2.2798498920555, - 2.27230201920557, 2.02484567313166, 4.1\}, - \{0, 4.30803136219904e-12, 0.0000062679151007581, - 0.00756040868012758, 0.262577163434171, - 1.55, 5.9\}\} -\end{multilineoutput} \\ -\end{Examples} - -\begin{Comments} -The other Jacobi functions use this function with initial values -a0=1, b0=sqrt(1-m), c0=sqrt(m). -\end{Comments} -\end{Operator} - -\begin{Operator}{LANDENTRANS} -The \name{landentrans} operator generates the descending landen -transformation of the given imput values, returning a list of these -values; initial to final in each case. -\begin{Syntax} -\name{landentrans}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -landentrans(0,0.1) & \{\{0,0,0,0,0\},\{0.1,0.0025041751943776, \\ - & 0.00000156772498954046,6.1444078 9914461e-13,0\}\} \\ -\end{Examples} - -\begin{Comments} -The first list ascends in value, and the second descends in value. -\end{Comments} -\end{Operator} - - -\begin{Operator}{EllipticF} -The \name{EllipticF} operator returns the Elliptic Integral of the -First Kind. -\begin{Syntax} -\name{EllitpicF}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticF(0.3, 8.222) & 0.3 \\ -EllipticF(7.396, 0.1) & 7.58123216114307 \\ -\end{Examples} - -\begin{Comments} -The Complete Elliptic Integral of the First Kind can be found by -putting the first argument to pi/2 or by using \name{EllipticK} -and the second argument. -\end{Comments} -\end{Operator} - - -\begin{Operator}{EllipticK} -The \name{EllipticK} operator returns the Elliptic value K. - -\begin{Syntax} -\name{EllipticK}\(\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticK(0.2) & 1.65962359861053 \\ -EllipticK(4.3) & 0.808442364282734 - 1.05562492399206*i \\ -EllipticK(0.000481) & 1.57098526617635 \\ -\end{Examples} - -\begin{Comments} -The \name{EllipticK} function is the Complete Elliptic Integral of -the First Kind. -\end{Comments} -\end{Operator} - -\begin{Operator}{EllipticKprime} -The \name{EllipticK'} operator returns the Elliptic value K(m). - -\begin{Syntax} -\name{EllipticKprime}\(\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticKprime(0.2) & 2.25720532682085 \\ -EllipticKprime(4.3) & 1.05562492399206 \\ -EllipticKprime(0.000481) & 5.206621921966 \\ -\end{Examples} - -\begin{Comments} -The \name{EllipticKprime} function is the Complete Elliptic Integral of -the First Kind of (1-m). -\end{Comments} -\end{Operator} - - -\begin{Operator}{EllipticE} -The \name{EllipticE} operator used with two arguments -returns the Elliptic Integral of the Second Kind. -\begin{Syntax} -\name{EllipticE}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticE(1.2,0.22) & 1.15094019180949 \\ -EllipticE(0,4.35) & 0 \\ -EllipticE(9,0.00719) & 8.98312465929145 \\ -\end{Examples} - -\begin{Comments} -The Complete Elliptic Integral of the Second Kind can be obtained by -using just the second argument, or by using pi/2 as the first argument. -\end{Comments} - -The \name{EllipticE} operator used with one argument -returns the Elliptic value E. -\begin{Syntax} -\name{EllipticE}\(\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticE(0.22) & 1.48046637439519 \\ -EllipticE(pi/2, 0.22) & 1.48046637439519 \\ -\end{Examples} - -\end{Operator} - -\begin{Operator}{EllipticTHETA} -The \name{EllipticTheta} operator returns one of the four Theta -functions. It cannot except any number other than 1,2,3 or 4 as -its first argument. - -\begin{Syntax} -\name{EllipticTheta}\(\meta{integer},\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -EllipticTheta(1, 1.4, 0.72) & 0.91634775373 \\ -EllipticTheta(2, 3.9, 6.1 ) & -48.0202736969 + 20.9881034377 i \\ -EllipticTheta(3, 0.67, 0.2) & 1.0083077448 \\ -EllipticTheta(4, 8, 0.75) & 0.894963369304 \\ -EllipticTheta(5, 1, 0.1) & ***** In EllipticTheta(a,u,m); a = 1,2,3 or 4. - \\ -\end{Examples} - -\begin{Comments} -Theta functions are important because every one of the Jacobian -Elliptic functions can be expressed as the ratio of two theta functions. -\end{Comments} -\end{Operator} - -\begin{Operator}{JacobiZETA} -The \name{JacobiZeta} operator returns the Jacobian function Zeta. - -\begin{Syntax} -\name{JacobiZeta}\(\meta{expression},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -JacobiZeta(3.2, 0.8) & - 0.254536403439 \\ -JacobiZeta(0.2, 1.6) & 0.171766095970451 - 0.0717028569800147*i \\ -\end{Examples} - -\begin{Comments} -The Jacobian function Zeta is related to the Jacobian function Theta. -But it is significantly different from Riemann's Zeta Function \nameref{Zeta}. -\end{Comments} -\end{Operator} - -\subsection{Gamma and Related Functions} -\begin{Operator}{POCHHAMMER} - -The \name{Pochhammer} operator implements the Pochhammer notation -(shifted factorial). - -\begin{Syntax} -\name{Pochhammer}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -pochhammer(17,4); & 116280 \\ - -pochhammer(1/2,z); & - \rfrac{factorial(2*z)}{(2^{2*z}*factorial(z))} -\end{Examples} - -\begin{Comments} -A number of complex rules for \name{Pochhammer} are inactive, because they -cause a huge system load in algebraic mode. If one wants to use more rules -for the simplification of Pochhammer's notation, one can do: -\\ -let special!*pochhammer!*rules; - -\end{Comments} -\end{Operator} - -\begin{Operator}{GAMMA} -The \name{Gamma} operator returns the Gamma function. - -\begin{Syntax} - -\name{Gamma}\(\meta{expression}\) - -\end{Syntax} - -\begin{Examples} -gamma(10); & 362880 \\ -gamma(1/2); & sqrt(pi) -\end{Examples} -\end{Operator} - -\begin{Operator}{BETA} -The \name{Beta} operator returns the Beta function defined by - - Beta (z,w) := defint(t**(z-1)* (1 - t)**(w-1),t,0,1) . - -\begin{Syntax} - -\name{Beta}\(\meta{expression},\meta{expression}\) - -\end{Syntax} - -\begin{Examples} -Beta(2,2); & 1 / 6 \\ -Beta(x,y); & gamma(x)*gamma(y) / gamma(x + y) -\end{Examples} - -\begin{Comments} -The operator \name{Beta} is simplified towards the \nameref{GAMMA} operator. -\end{Comments} -\end{Operator} - -\begin{Operator}{PSI} -\index{Euler's constant} -The \name{Psi} operator returns the Psi (or DiGamma) function. - - Psi(x) := df(Gamma(z),z)/ Gamma (z) - -\begin{Syntax} - -\name{Gamma}\(\meta{expression}\) - -\end{Syntax} - -\begin{Examples} -Psi(3); & (2*log(2) + psi(1/2) + psi(1) + 3)/2 \\ -on rounded; \\ -- Psi(1); & 0.577215664902 -\end{Examples} - -\begin{Comments} -Euler's constant can be found as - Psi(1). -\end{Comments} -\end{Operator} - -\begin{Operator}{POLYGAMMA} -The \name{Polygamma} operator returns the Polygamma function. - - Polygamma(n,x) := df(Psi(z),z,n); - -\begin{Syntax} -\name{Polygamma}\(\meta{integer},\meta{expression}\) -\end{Syntax} - -\begin{Examples} - Polygamma(1,2); & (pi^2 - 6) / 6\\ -on rounded; \\ -Polygamma(1,2.35); & 0.52849689109 -\end{Examples} - -\begin{Comments} -The Polygamma function is used for simplification of the \nameref{ZETA} -function for some arguments. -\end{Comments} -\end{Operator} - -\subsection{Miscellaneous Functions} - -\begin{Operator}{DILOG extended} -\index{Spence's Integral} -The package \name{specfn} supplies an extended support for the -\nameref{dilog} operator which implements the \nameindex{dilogarithm function}. - -dilog(x) := - defint(log(t)/(t - 1),t,1,x); - -\begin{Syntax} -\name{Dilog}\(\meta{order},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -defint(log(t)/(t - 1),t,1,x); & - dilog (x) \\ -dilog 2; & - pi^2 /12 \\ - -on rounded; \\ -Dilog 20; & - 5.92783972438 -\end{Examples} - -\begin{Comments} -The operator \name{Dilog} is sometimes called Spence's Integral for n = 2. -\end{Comments} -\end{Operator} - -\begin{Operator}{Lambert_W function} -Lambert's W function is the inverse of the function w * e^w. -It is used in the \nameref{solve} package for equations containing -exponentials and logarithms. - -\begin{Syntax} -\name{Lambert\_W}\(\meta{z}\) -\end{Syntax} - -\begin{Examples} -Lambert_W(-1/e); & -1 \\ -solve(w + log(w),w); & {w=lambert\_w(1)}\\ -on rounded; \\ -Lambert_W(-0.05); & - 0.0527059835515 -\end{Examples} - -\begin{Comments} -The current implementation will compute the principal branch in -rounded mode only. -\end{Comments} -\end{Operator} - -\subsection{Orthogonal Polynomials} - -\begin{Operator}{ChebyshevT} -The \name{ChebyshevT} operator computes the nth Chebyshev T Polynomial (of the -first kind). - -\begin{Syntax} -\name{ChebyshevT}\(\meta{integer},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -ChebyshevT(3,xx); & xx*(4*xx^2 - 3) \\ - -ChebyshevT(3,4); & 244 -\end{Examples} - -\begin{Comments} -Chebyshev's T polynomials are computed using the recurrence relation: - -ChebyshevT(n,x) := 2x*ChebyshevT(n-1,x) - ChebyshevT(n-2,x) with \\ -ChebyshevT(0,x) := 0 and ChebyshevT(1,x) := x -\end{Comments} -\end{Operator} - -\begin{Operator}{ChebyshevU} -The \name{ChebyshevU} operator returns the nth Chebyshev U Polynomial (of the -second kind). - -\begin{Syntax} -\name{ChebyshevU}\(\meta{integer},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -ChebyshevU(3,xx); & 4*x*(2*x^2 - 1) \\ - -ChebyshevU(3,4); & 496 -\end{Examples} - -\begin{Comments} -Chebyshev's U polynomials are computed using the recurrence relation: - -ChebyshevU(n,x) := 2x*ChebyshevU(n-1,x) - ChebyshevU(n-2,x) with \\ -ChebyshevU(0,x) := 0 and ChebyshevU(1,x) := 2x - -\end{Comments} -\end{Operator} - -\begin{Operator}{HermiteP} -The \name{HermiteP} operator returns the nth Hermite Polynomial. - -\begin{Syntax} -\name{HermiteP}\(\meta{integer},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -HermiteP(3,xx); & 4*xx*(2*xx^2 - 3) \\ -HermiteP(3,4); & 464 -\end{Examples} - -\begin{Comments} -Hermite polynomials are computed using the recurrence relation: - \\ -HermiteP(n,x) := 2x*HermiteP(n-1,x) - 2*(n-1)*HermiteP(n-2,x) with \\ -HermiteP(0,x) := 1 and HermiteP(1,x) := 2x - -\end{Comments} -\end{Operator} - - -\begin{Operator}{LaguerreP} -The \name{LaguerreP} operator computes the nth Laguerre Polynomial. -The two argument call of LaguerreP is a (common) abbreviation of -LaguerreP(n,0,x). - -\begin{Syntax} -\name{LaguerreP}\(\meta{integer},\meta{expression}\) or\\ -\name{LaguerreP}\(\meta{integer},\meta{expression},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -LaguerreP(3,xx); & (- xx^3 + 9*xx^2 - 18*xx + 6)/6\\ - -LaguerreP(2,3,4); & -2 -\end{Examples} - -\begin{Comments} -Laguerre polynomials are computed using the recurrence relation: - -LaguerreP(n,a,x) := (2n+a-1-x)/n*LaguerreP(n-1,a,x) - - (n+a-1) * LaguerreP(n-2,a,x) with \\ - \\ -LaguerreP(0,a,x) := 1 and LaguerreP(2,a,x) := -x+1+a -\end{Comments} -\end{Operator} - -\begin{Operator}{LegendreP} -The binary \name{LegendreP} operator computes the nth Legendre -Polynomial which is -a special case of the nth Jacobi Polynomial with \\ - \\ -LegendreP(n,x) := JacobiP(n,0,0,x)\\ - \\ -The ternary form returns the associated Legendre Polynomial (see below). - -\begin{Syntax} -\name{LegendreP}\(\meta{integer},\meta{expression}\) or\\ -\name{LegendreP}\(\meta{integer},\meta{expression},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -LegendreP(3,xx); &\rfrac{xx*(5*xx^2 - 3)}{2}\\ - -LegendreP(3,2,xx); &15*xx*( - xx^2 + 1) -\end{Examples} - -\begin{Comments} -The ternary form of the operator \name{LegendreP} is the associated -Legendre Polynomial defined as \\ -\\ - P(n,m,x) = (-1)**m * (1-x**2)**(m/2) * df(LegendreP(n,x),x,m) -\end{Comments} -\end{Operator} - -\begin{Operator}{JacobiP} -The \name{JacobiP} operator computes the nth Jacobi Polynomial. - -\begin{Syntax} -\name{JacobiP}\(\meta{integer},\meta{expression},\meta{expression}, - \meta{expression}\) -\end{Syntax} - -\begin{Examples} -JacobiP(3,4,5,xx); & \rfrac{7*(65*xx^3 - 13*xx^2 - 13*xx + 1)}{8}\\ - -JacobiP(3,4,5,6); & 94465/8 -\end{Examples} - -\end{Operator} - -\begin{Operator}{GegenbauerP} -\index{ultraspherical polynomials} -The \name{GegenbauerP} operator computes Gegenbauer's (ultraspherical) -polynomials. - -\begin{Syntax} -\name{GegenbauerP}\(\meta{integer},\meta{expression},\meta{expression}\) -\end{Syntax} - -\begin{Examples} -GegenbauerP(3,2,xx); & 4*xx*(8*xx^2 - 3)\\ - -GegenbauerP(3,2,4); & 2000 -\end{Examples} - -\end{Operator} - -\begin{Operator}{SolidHarmonicY} -\index{Solid harmonic polynomials} -The \name{SolidHarmonicY} operator computes Solid harmonic (Laplace) -polynomials. - -\begin{Syntax} - -\name{SolidHarmonicY}\(\meta{integer},\meta{integer}, -\meta{expression},\meta{expression},\meta{expression},\meta{expression}\) - -\end{Syntax} - -\begin{Examples} - -SolidHarmonicY(3,-2,x,y,z,r2); & - -\rfrac{sqrt(105)*z*(-2*i*x*y + x^2 - y^2)}{4*sqrt(pi)*sqrt(2)}\\ - -\end{Examples} - -\end{Operator} - -\begin{Operator}{SphericalHarmonicY} -\index{Spherical harmonic polynomials} -The \name{SphericalHarmonicY} operator computes Spherical harmonic (Laplace) -polynomials. These are special cases of the -solid harmonic polynomials, \nameref{SolidHarmonicY}. - -\begin{Syntax} - -\name{SphericalHarmonicY}\(\meta{integer},\meta{integer}, -\meta{expression},\meta{expression}\) - -\end{Syntax} - -\begin{Examples} -SphericalHarmonicY(3,2,theta,phi); & - -\rfrac{sqrt(105)*cos(theta)*sin(theta)^2*(cos(phi)^2+2*cos(phi)*sin(phi)*i- -sin(phi)^2)}{4*sqrt(pi)*sqrt(2)}\\ - -\end{Examples} - -\end{Operator} - - -\subsection{Integral Functions} -\index{sine integral function} -\begin{Operator}{Si} -\index{Sine integral function}\index{integral function} -The \name{Si} operator returns the Sine Integral function. - -\begin{Syntax} -\name{Si}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -limit(Si(x),x,infinity); & pi / 2 \\ -on rounded; \\ -Si(0.35); & 0.347626790989 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{Si} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{Shi} -\index{hyperbolic sine integral function}\index{integral function} -The \name{Shi} operator returns the hyperbolic Sine Integral function. - -\begin{Syntax} -\name{Shi}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -df(shi(x),x); & sinh(x) / x \\ -on rounded; \\ -Shi(0.35); & 0.352390716351 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{Shi} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{s_i} -\index{sine integral function}\index{integral function} -The \name{s_i} operator returns the Sine Integral function si. - -\begin{Syntax} -\name{s_i}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -s_i(xx); & (2*Si(xx) - pi) / 2 \\ -df(s_i(x),x); & sin(x) / x -\end{Examples} - -\begin{Comments} -The operator name \name{s_i} is simplified towards \nameref{SI}. -Since REDUCE is not case sensitive by default the name ``si'' can't be -used. -\end{Comments} -\end{Operator} - -\begin{Operator}{Ci} -\index{cosine integral function} -The \name{Ci} operator returns the Cosine Integral function. - -\begin{Syntax} -\name{Ci}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -defint(cos(t)/t,t,x,infinity); & - ci (x) \\ -on rounded; \\ -Ci(0.35); & - 0.50307556932 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{Ci} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{Chi} -\index{hyperbolic cosine integral function}\index{integral function} -The \name{Chi} operator returns the Hyperbolic Cosine Integral function. - -\begin{Syntax} -\name{Chi}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -defint((cosh(t)-1)/t,t,0,x); & - log(x) + psi(1) + chi(x)\\ -on rounded; \\ -Chi(0.35); & - 0.44182471827 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{Chi} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{ERF extended} -\index{error function} -The special function package supplies an extended support for the -\nameref{erf} operator which implements the \nameindex{error function} \\ - \\ - defint(e**(-x**2),x,0,infinity) * 2/sqrt(pi) \\ -.\\ -\begin{Syntax} -\name{erf}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -erf(-x); & - erf(x)\\ -on rounded; \\ -erf(0.35); & 0.379382053562 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{erf} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{erfc} -\index{error function}\index{complementary error function} -The \name{erfc} operator returns the complementary Error function\\ - \\ - 1 - defint(e**(-x**2),x,0,infinity) * 2/sqrt(pi) \\ -.\\ -\begin{Syntax} -\name{erfc}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -erfc(xx); & - erf(xx) + 1 -\end{Examples} - -\begin{Comments} -The operator \name{erfc} is simplified towards the \nameref{erf} operator. -\end{Comments} -\end{Operator} - -\begin{Operator}{Ei} -\index{exponential integral function} -The \name{Ei} operator returns the Exponential Integral function. - -\begin{Syntax} -\name{Ei}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -df(ei(x),x); & \rfrac{e^x}{x}\\ -on rounded; \\ -Ei(0.35); & - 0.0894340019184 -\end{Examples} - -\begin{Comments} -The numeric values for the operator \name{Ei} are computed via the -power series representation, which limits the argument range. -\end{Comments} -\end{Operator} - -\begin{Operator}{Fresnel_C} -The \name{Fresnel_C} operator represents Fresnel's Cosine function. - -\begin{Syntax} -\name{Fresnel_C}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -int(cos(t^2*pi/2),t,0,x); & fresnel\_c(x) \\ -on rounded; \\ -fresnel_c(2.1); & 0.581564135061 -\end{Examples} - -\begin{Comments} -The operator \name{Fresnel_C} has a limited numeric evaluation of -large values of its argument. -\end{Comments} -\end{Operator} - -\begin{Operator}{Fresnel_S} -The \name{Fresnel_S} operator represents Fresnel's Sine Integral function. - -\begin{Syntax} -\name{Fresnel_S}\(\meta{expression}\) -\end{Syntax} - -\begin{Examples} -int(sin(t^2*pi/2),t,0,x); & fresnel\_s(x) \\ -on rounded; \\ -fresnel_s(2.1); & 0.374273359378 -\end{Examples} - -\begin{Comments} -The operator \name{Fresnel_S} has a limited numeric evaluation of -large values of its argument. -\end{Comments} -\end{Operator} - -\subsection{Combinatorial Operators} - -\begin{Operator}{BINOMIAL} -The \name{Binomial} operator returns the Binomial coefficient if both -parameter are integer and expressions involving the Gamma function otherwise. - -\begin{Syntax} - -\name{Binomial}\(\meta{integer},\meta{integer}\) - -\end{Syntax} - -\begin{Examples} -Binomial(49,6); & 13983816 \\ - -Binomial(n,3); & \rfrac{gamma(n + 1)}{6*gamma(n - 2)} -\end{Examples} - -\begin{Comments} -The operator \name{Binomial} evaluates the Binomial coefficients from -the explicit form and therefore it is not the best algorithm if you -want to compute many binomial coefficients with big indices in which -case a recursive algorithm is preferable. -\end{Comments} -\end{Operator} - -\begin{Operator}{STIRLING1} -The \name{Stirling1} operator returns the Stirling Numbers S(n,m) of the first -kind, i.e. the number of permutations of n symbols which have exactly m cycles -(divided by (-1)**(n-m)). - -\begin{Syntax} -\name{Stirling1}\(\meta{integer},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Stirling1 (17,4); & -87077748875904 \\ -Stirling1 (n,n-1); & \rfrac{-gamma(n+1)}{2*gamma(n-1)} -\end{Examples} - -\begin{Comments} -The operator \name{Stirling1} evaluates the Stirling numbers of the -first kind by rulesets for special cases or by a computing the closed -form, which is a series involving the operators \nameref{BINOMIAL} -and \nameref{STIRLING2}. -\end{Comments} -\end{Operator} - -\begin{Operator}{STIRLING2} -The \name{Stirling1} operator returns the Stirling Numbers S(n,m) of the -second kind, i.e. the number of ways of partitioning a set of n elements -into m non-empty subsets. - -\begin{Syntax} -\name{Stirling2}\(\meta{integer},\meta{integer}\) -\end{Syntax} - -\begin{Examples} -Stirling2 (17,4); & 694337290 \\ -Stirling2 (n,n-1); & \rfrac{gamma(n+1)}{2*gamma(n-1)} -\end{Examples} - -\begin{Comments} -The operator \name{Stirling2} evaluates the Stirling numbers of the -second kind by rulesets for special cases or by a computing the closed -form. -\end{Comments} -\end{Operator} - -\subsection{3j and 6j symbols} - -\begin{Operator}{ThreejSymbol} -The \name{ThreejSymbol} operator implements the 3j symbol. - -\begin{Syntax} - -\name{ThreejSymbol}\(\meta{list of j1,m1},\meta{list of j2,m2}, -\meta{list of j3,m3}\) - -\end{Syntax} - -\begin{Examples} - -ThreejSymbol({j+1,m},{j+1,-m},{1,0}); & - -\rfrac{( - 1)^j *(abs(j - m + 1) - abs(j + m + 1))} - { 2*sqrt(2*j^3 + 9*j^2 + 13*j + 6)*( - 1)^m}\\ - -\end{Examples} -\end{Operator} - -\begin{Operator}{Clebsch_Gordan} -The \name{Clebsch\_Gordan} operator implements the Clebsch\_Gordan -coefficients. This is closely related to the \nameref{Threejsymbol}. - -\begin{Syntax} - -\name{Clebsch\_Gordan}\(\meta{list of j1,m1},\meta{list of j2,m2}, -\meta{list of j3,m3}\) - -\end{Syntax} - -\begin{Examples} - Clebsch_Gordan({2,0},{2,0},{2,0}); & \rfrac{-2}{sqrt(14)}\\ -\end{Examples} -\end{Operator} - -\begin{Operator}{SixjSymbol} -The \name{SixjSymbol} operator implements the 6j symbol. -\begin{Syntax} - -\name{SixjSymbol}\(\meta{list of j1,j2,j3},\meta{list of l1,l2,l3}\) - -\end{Syntax} -\begin{Examples} - -SixjSymbol({7,6,3},{2,4,6}); & \rfrac{1}{14*sqrt(858)}\\ - -\end{Examples} - -\begin{Comments} -The operator \name{SixjSymbol} uses the \nameref{ineq} package in order -to find minima and maxima for the summation index. -\end{Comments} -\end{Operator} - -\subsection{Miscellaneous} - - -\begin{Operator}{HYPERGEOMETRIC} -\index{hypergeometric function} -\index{generalized hypergeometric function} -The \name{Hypergeometric} operator provides simplifications for the -generalized hypergeometric functions. -The \name{Hypergeometric} operator is included in the package specfn2. - -\begin{Syntax} -\name{hypergeometric}\(\meta{list of parameters},\meta{list of parameters}, - \meta{argument}\) -\end{Syntax} - -\begin{Examples} -load specfn2;\\ -hypergeometric ({1/2,1},{3/2},-x^2); & \rfrac{atan(x)}{x}\\ -hypergeometric ({},{},z); & e^z -\end{Examples} - -\begin{Comments} -The special case where the length of the first list is equal to 2 and -the length of the second list is equal to 1 is often called -``the hypergeometric function'' (notated as 2F1(a1,a2,b;x)). -\end{Comments} -\end{Operator} - -\begin{Operator}{MeijerG} -The \name{MeijerG} operator provides simplifications for Meijer's G -function. The simplifications are performed towards polynomials, -elementary or -special functions or (generalized) \nameref{hypergeometric} functions. - -The \name{MeijerG} operator is included in the package specfn2. - -\begin{Syntax} -\name{MeijerG}\(\meta{list of parameters},\meta{list of parameters}, - \meta{argument}\) -\end{Syntax} -The first element of the lists has to be the list containing the -first group (mostly called ``m'' and ``n'') of parameters. This passes -the four parameters of a Meijer's G function implicitly via the -length of the lists. - -\begin{Examples} -load specfn2;\\ -MeijerG({{},1},{{0}},x); & heaviside(-x+1)\\ -MeijerG({{}},{{1+1/4},1-1/4},(x^2)/4) * sqrt pi; - & \rfrac{sqrt(2)*sin(x)*x^2}{4*sqrt(x)} -\end{Examples} - -\begin{Comments} -Many well-known functions can be written as G functions, -e.g. exponentials, logarithms, trigonometric functions, Bessel functions -and hypergeometric functions. -The formulae can be found e.g. in \\ -A.P.Prudnikov, Yu.A.Brychkov, O.I.Marichev: -Integrals and Series, Volume 3: More special functions, -Gordon and Breach Science Publishers (1990). -\end{Comments} -\end{Operator} - -\begin{Operator}{Heaviside} - -The \name{Heaviside} operator returns the Heaviside function. \\ - -Heaviside(~w) => if (w < 0) then 0 else 1 \\ - when numberp w; - -\begin{Syntax} -\name{Heaviside}\(\meta{argument}\) -\end{Syntax} - -\begin{Comments} -This operator is often included in the result of the simplification -of a generalized \nameref{hypergeometric} function or a -\nameref{MeijerG} function. - -No simplification is done for this function. -\end{Comments} -\end{Operator} - -\begin{Operator}{erfi} - -The \name{erfi} operator returns the error function of an imaginary argument. - -erfi(~x) => 2/sqrt(pi) * defint(e**(t**2),t,0,x); - -\begin{Syntax} -\name{erfi}\(\meta{argument}\) -\end{Syntax} - -\begin{Comments} -This operator is sometimes included in the result of the simplification -of a generalized \nameref{hypergeometric} function or a -\nameref{MeijerG} function. - -No simplification is done for this function. -\end{Comments} -\end{Operator} - +\section{Special Functions} +\begin{Introduction}{Special Function Package} +The REDUCE \name{Special Function Package} supplies extended +algebraic and numeric support for a wide class of objects. +This package was released together with REDUCE 3.5 (October 1993) +for the first time, a major update is released with REDUCE 3.6.\\ +\\ + +The functions included in this package are in most cases (unless otherwise +stated) defined and named like in the book by Abramowitz and Stegun: +Handbook of Mathematical Functions, Dover Publications.\\ + \\ + +The aim is to collect as much information on the special functions +and simplification capabilities as possible, +i.e. algebraic simplifications and numeric (rounded mode) code, limits +of the functions together +with the definitions of the functions, which are in most cases a power +series, a (definite) integral and/or a differential equation.\\ + \\ + +\em{What can be found:} Some famous constants, a variety of Bessel functions, +special polynomials, +the Gamma function, the (Riemann) Zeta function, Elliptic Functions, Elliptic +Integrals, 3J symbols (Clebsch-Gordan coefficients) and integral functions.\\ + \\ + +\em{What is missing:} Mathieu functions, LerchPhi, etc.. +The information about the special functions which solve certain +differential equation is very limited. +In several cases numerical approximation is restricted to real +arguments or is missing completely.\\ + \\ + +The implementation of this package uses REDUCE rule sets to a large extent, +which guarantees a high 'readability' of the functions definitions in the +source file directory. It makes extensions to the special +functions code easy in most cases too. To look at these rules +it may be convenient to use the showrules operator e.g.\\ + \\ + \nameref{showrules} Besseli;\\ +.\\ + +Some evaluations are improved if the special function package is loaded, +e.g. some (infinite) sums and products leading to expressions including +special functions are known in this case.\\ +\\ + +Note: The special function package has to be loaded explicitly by calling +\begin{verbatim} + load_package specfn; +\end{verbatim} +The functions \nameref{MeijerG} and \nameref{hypergeometric} require +additionally +\begin{verbatim} + load_package specfn2; +\end{verbatim} + +\end{Introduction} + +\begin{Concept}{Constants} +\index{Euler's constant}\index{Catalan's constant}\index{Khinchin's constant} +\index{Golden_Ratio} + +There are a few constants known to the special function package, namely\\ +\\ +\name{Euler's constant} (which can be computed as -\nameref{Psi}(1)) and \\ +\name{Khinchin's constant} (which is defined in Khinchin's book \\ + ``Continued Fractions'') and \\ +\name{Golden_Ratio} (which can be computed as (1 + sqrt 5)/2) and \\ +\name{Catalan's constant} (which is known as an infinite sum of reciprocal +powers) + +\begin{Examples} +on rounded; +Euler_Gamma; & 0.577215664902 \\ +Khinchin; & 2.68545200107 \\ +Catalan & 0.915965594177 \\ +Golden_Ratio & 1.61803398875 +\end{Examples} + +\end{Concept} + +\subsection{Bernoulli Euler Zeta} + +\begin{Operator}{BERNOULLI} +The \name{bernoulli} operator returns the nth Bernoulli number. + +\begin{Syntax} + +\name{Bernoulli}\(\meta{integer}\) + +\end{Syntax} + +\begin{Examples} +bernoulli 20; & - 174611 / 330 \\ +bernoulli 17; & 0 +\end{Examples} + +\begin{Comments} +All Bernoulli numbers with odd indices except for 1 are zero. +\end{Comments} +\end{Operator} + +\begin{Operator}{BERNOULLIP} +The \name{BernoulliP} operator returns the nth Bernoulli Polynomial +evaluated at x. + +\begin{Syntax} + +\name{BernoulliP}\(\meta{integer},\meta{expression}\) + +\end{Syntax} + +\begin{Examples} +BernoulliP(3,z); & z*(2*z^2 - 3*z + 1)/2\\ + +BernoulliP(10,3); & 338585 / 66 +\end{Examples} + +\begin{Comments} +The value of the nth Bernoulli Polynomial at 0 is the nth Bernoulli number. +\end{Comments} +\end{Operator} + +\begin{Operator}{EULER} +The \name{EULER} operator returns the nth Euler number. + +\begin{Syntax} +\name{Euler}\(\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Euler 20; & 370371188237525 \\ +Euler 0; & 1 +\end{Examples} + +\begin{Comments} +The \name{Euler} numbers are evaluated by a recursive algorithm which +makes it hard to compute Euler numbers above say 200. + +Euler numbers appear in the coefficients of the power series +representation of 1/cos(z). +\end{Comments} +\end{Operator} + +\begin{Operator}{EULERP} +The \name{EulerP} operator returns the nth Euler Polynomial. + +\begin{Syntax} +\name{EulerP}\(\meta{integer},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +EulerP(2,xx); & xx*(xx - 1) \\ +EulerP(10,3); & 2046 +\end{Examples} + +\begin{Comments} +The Euler numbers are the values of the Euler Polynomials at 1/2 +multiplied by 2**n. +\end{Comments} +\end{Operator} + +\begin{Operator}{ZETA} +The \name{Zeta} operator returns Riemann's Zeta function, + + Zeta (z) := sum(1/(k**z),k,1,infinity) + +\begin{Syntax} +\name{Zeta}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +Zeta(2); & pi^2 / 6 \\ +on rounded; \\ +Zeta 1.01; & 100.577943338 +\end{Examples} + +\begin{Comments} +Numerical computation for the Zeta function for arguments close to 1 are +tedious, because the series is converging very slowly. In this case a formula +(e.g. found in Bender/Orzag: Advanced Mathematical Methods for +Scientists and Engineers, McGraw-Hill) is used. + +No numerical approximation for complex arguments is done. +\end{Comments} + +\end{Operator} +\subsection{Bessel Functions} + +\begin{Operator}{BESSELJ} +The \name{BesselJ} operator returns the Bessel function of the first kind. + +\begin{Syntax} +\name{BesselJ}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +BesselJ(1/2,pi); & 0 \\ +on rounded; \\ +BesselJ(0,1); & 0.765197686558 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{BESSELY} +\index{Weber's function} +The \name{BesselY} operator returns the Bessel function of the second kind. +\begin{Syntax} +\name{BesselY}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +BesselY (1/2,pi); & - sqrt(2) / pi \\ +on rounded; \\ +BesselY (1,3); & 0.324674424792 +\end{Examples} + +\begin{Comments} +The operator \name{BesselY} is also called Weber's function. +\end{Comments} +\end{Operator} + +\begin{Operator}{HANKEL1} +The \name{Hankel1} operator returns the Hankel function of the first kind. + +\begin{Syntax} +\name{Hankel1}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +on complex; \\ +Hankel1 (1/2,pi); & - i * sqrt(2) / pi \\ +Hankel1 (1,pi); & besselj(1,pi) + i*bessely(1,pi) + +\end{Examples} + +\begin{Comments} +The operator \name{Hankel1} is also called Bessel function of the third kind. +There is currently no numeric evaluation of Hankel functions. +\end{Comments} +\end{Operator} + +\begin{Operator}{HANKEL2} +The \name{Hankel2} operator returns the Hankel function of the second kind. + +\begin{Syntax} +\name{Hankel2}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +on complex; \\ +Hankel2 (1/2,pi); & - i * sqrt(2) / pi \\ +Hankel2 (1,pi); & besselj(1,pi) - i*bessely(1,pi) +\end{Examples} + +\begin{Comments} +The operator \name{Hankel2} is also called Bessel function of the third kind. +There is currently no numeric evaluation of Hankel functions. +\end{Comments} +\end{Operator} + +\begin{Operator}{BESSELI} +The \name{BesselI} operator returns the modified Bessel function I. + +\begin{Syntax} +\name{BesselI}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +on rounded; \\ +Besseli (1,1); & 0.565159103992 +\end{Examples} + +\begin{Comments} +The knowledge about the operator \name{BesselI} is currently fairly limited. +\end{Comments} +\end{Operator} + +\begin{Operator}{BESSELK} +The \name{BesselK} operator returns the modified Bessel function K. + +\begin{Syntax} +\name{BesselK}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +df(besselk(0,x),x); & - besselk(1,x) +\end{Examples} + +\begin{Comments} +There is currently no numeric support for the operator \name{BesselK}. +\end{Comments} +\end{Operator} + +\begin{Operator}{StruveH} +The \name{StruveH} operator returns Struve's H function. + +\begin{Syntax} +\name{StruveH}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +struveh(-3/2,x); & - besselj(3/2,x) / i +\end{Examples} + +\end{Operator} + +\begin{Operator}{StruveL} +The \name{StruveL} operator returns the modified Struve L function . + +\begin{Syntax} +\name{StruveL}\(\meta{order},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +struvel(-3/2,x); & besseli(3/2,x) +\end{Examples} + +\end{Operator} + +\begin{Operator}{KummerM} +\index{Confluent Hypergeometric function} +The \name{KummerM} operator returns Kummer's M function. + +\begin{Syntax} +\name{KummerM}\(\meta{parameter},\meta{parameter},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +kummerm(1,1,x); & e^x \\ +on rounded; \\ +kummerm(1,3,1.3); & 1.62046942914 +\end{Examples} + +\begin{Comments} +Kummer's M function is one of the Confluent Hypergeometric functions. +For reference see the \nameref{hypergeometric} operator. +\end{Comments} +\end{Operator} + +\begin{Operator}{KummerU} +\index{Confluent Hypergeometric function} +The \name{KummerU} operator returns Kummer's U function. + +\begin{Syntax} +\name{KummerU}\(\meta{parameter},\meta{parameter},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +df(kummeru(1,1,x),x) & - kummeru(2,2,x) +\end{Examples} + +\begin{Comments} +Kummer's U function is one of the Confluent Hypergeometric functions. +For reference see the \nameref{hypergeometric} operator. +\end{Comments} +\end{Operator} + +\begin{Operator}{WhittakerW} +\index{Confluent Hypergeometric function} +The \name{WhittakerW} operator returns Whittaker's W function. + +\begin{Syntax} +\name{WhittakerW}\(\meta{parameter},\meta{parameter},\meta{argument}\) +\end{Syntax} + +\begin{Examples} +WhittakerW(2,2,2); & \rfrac{4*sqrt(2)*kummeru(\rfrac{1}{2},5,2)}{e} +\end{Examples} + +\begin{Comments} +Whittaker's W function is one of the Confluent Hypergeometric functions. +For reference see the \nameref{hypergeometric} operator. +\end{Comments} +\end{Operator} + +\subsection{Airy Functions} + +\begin{Operator}{Airy_Ai} +The \name{Airy\_Ai} operator returns the Airy Ai function for a given argument. + +\begin{Syntax} +\name{Airy\_Ai}\(\meta{argument}\) +\end{Syntax} + +\begin{Examples} +on complex; +on rounded; +Airy_Ai(0); & 0.355028053888 \\ +Airy_Ai(3.45 + 17.97i); & - 5.5561528511e+9 - 8.80397899932e+9*i \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{Airy_Bi} +The \name{Airy\_Bi} operator returns the Airy Bi function for a given +argument. + +\begin{Syntax} +\name{Airy\_Bi}\(\meta{argument}\) +\end{Syntax} + +\begin{Examples} +Airy_Bi(0); & 0.614926627446 \\ +Airy_Bi(3.45 + 17.97i); & 8.80397899932e+9 - 5.5561528511e+9*i \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{Airy_Aiprime} +The \name{Airy\_Aiprime} operator returns the Airy Aiprime function for a +given argument. + +\begin{Syntax} +\name{Airy\_Aiprime}\(\meta{argument}\) +\end{Syntax} + +\begin{Examples} +Airy_Aiprime(0); & - 0.258819403793 \\ +Airy_Aiprime(3.45+17.97i);& - 3.83386421824e+19 + 2.16608828136e+19*i \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{Airy_Biprime} +The \name{Airy\_Biprime} operator returns the Airy Biprime function for a +given argument. + +\begin{Syntax} +\name{Airy\_Biprime}\(\meta{argument}\) +\end{Syntax} + +\begin{Examples} +Airy_Biprime(0); & \\ +Airy_Biprime(3.45 + 17.97i); & 3.84251916792e+19 - 2.18006297399e+19*i\\ +\end{Examples} + +\end{Operator} + +\subsection{Jacobi's Elliptic Functions and Elliptic Integrals} + +\begin{Operator}{JacobiSN} +The \name{Jacobisn} operator returns the Jacobi Elliptic function sn. + +\begin{Syntax} +\name{Jacobisn}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobisn(0.672, 0.36) & 0.609519691792 \\ +Jacobisn(1,0.9) & 0.770085724907881 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiCN} +The \name{Jacobicn} operator returns the Jacobi Elliptic function cn. + +\begin{Syntax} +\name{Jacobicn}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobicn(7.2, 0.6) & 0.837288298482018 \\ +Jacobicn(0.11, 19) & 0.994403862690043 - 1.6219006985556e-16*i \\ +\end{Examples} + +\end{Operator} + + +\begin{Operator}{JacobiDN} +The \name{Jacobidn} operator returns the Jacobi Elliptic function dn. + +\begin{Syntax} +\name{Jacobidn}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobidn(15, 0.683) & 0.640574162024592 \\ +Jacobidn(0,0) & 1 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiCD} +The \name{Jacobicd} operator returns the Jacobi Elliptic function cd. + +\begin{Syntax} +\name{Jacobicd}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobicd(1, 0.34) & 0.657683337805273 \\ +Jacobicd(0.8,0.8) & 0.925587311582301 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiSD} +The \name{Jacobisd} operator returns the Jacobi Elliptic function sd. + +\begin{Syntax} +\name{Jacobisd}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobisd(12, 0.4) & 0.357189729437272 \\ +Jacobisd(0.35,1) & - 1.17713873203043 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiND} +The \name{Jacobind} operator returns the Jacobi Elliptic function nd. + +\begin{Syntax} +\name{Jacobind}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobind(0.2, 17) & 1.46553203037507 + 0.0000000000334032759313703*i \\ +Jacobind(30, 0.001) & 1.00048958438 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiDC} +The \name{Jacobidc} operator returns the Jacobi Elliptic function dc. + +\begin{Syntax} +\name{Jacobidc}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobidc(0.003,1) & 1 \\ +Jacobidc(2, 0.75) & 6.43472885111 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiNC} +The \name{Jacobinc} operator returns the Jacobi Elliptic function nc. + +\begin{Syntax} +\name{Jacobinc}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobinc(1,0) & 1.85081571768093 \\ +Jacobinc(56, 0.4387) & 39.304842663512 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiSC} +The \name{Jacobisc} operator returns the Jacobi Elliptic function sc. + +\begin{Syntax} +\name{Jacobisc}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobisc(9, 0.88) & - 1.16417697982095 \\ +Jacobisc(0.34, 7) & 0.305851938390775 - 9.8768100944891e-12*i \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiNS} +The \name{Jacobins} operator returns the Jacobi Elliptic function ns. + +\begin{Syntax} +\name{Jacobins}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobins(3, 0.9) & 1.00945801599785 \\ +Jacobins(0.887, 15) & 0.683578280513975 - 0.85023411082469*i \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiDS} +The \name{Jacobisn} operator returns the Jacobi Elliptic function ds. + +\begin{Syntax} +\name{Jacobids}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobids(98,0.223) & - 1.061253961477 \\ +Jacobids(0.36,0.6) & 2.76693172243692 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiCS} +The \name{Jacobics} operator returns the Jacobi Elliptic function cs. + +\begin{Syntax} +\name{Jacobics}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Jacobics(0, 0.767) & infinity \\ +Jacobics(1.43, 0) & 0.141734127352112 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{JacobiAMPLITUDE} +The \name{JacobiAmplitude} operator returns the amplitude of u. +\begin{Syntax} +\name{JacobiAmplitude}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +JacobiAmplitude(7.239, 0.427) & 0.0520978301448978 \\ +JacobiAmplitude(0,0.1) & 0 \\ +\end{Examples} + +\begin{Comments} +Amplitude u = asin(\name{Jacobisn(u,m)}) +\end{Comments} +\end{Operator} + + +\begin{Operator}{AGM_FUNCTION} +The \name{AGM_function} operator returns a list of (N, AGM, + list of aNtoa0, list of bNtob0, list of cNtoc0) where a0, b0 and c0 +are the initial values; N is the index number of the last term +used to generate the AGM. AGM is the Arithmetic Geometric Mean. + +\begin{Syntax} +\name{AGM_function}\(\meta{integer},\meta{integer},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +AGM_function(1,1,1) & {1,1,{1,1},{1,1},{0,1}} \\ +AGM_function(1, 0.1, 1.3) & +\begin{multilineoutput}{6cm} +\{6, + 2.27985615996629, + \{2.27985615996629, 2.27985615996629, + 2.2798561599706, 2.2798624278857, + 2.28742283656583, 2.55, 1\}, + \{2.27985615996629, 2.27985615996629, + 2.27985615996198, 2.2798498920555, + 2.27230201920557, 2.02484567313166, 4.1\}, + \{0, 4.30803136219904e-12, 0.0000062679151007581, + 0.00756040868012758, 0.262577163434171, - 1.55, 5.9\}\} +\end{multilineoutput} \\ +\end{Examples} + +\begin{Comments} +The other Jacobi functions use this function with initial values +a0=1, b0=sqrt(1-m), c0=sqrt(m). +\end{Comments} +\end{Operator} + +\begin{Operator}{LANDENTRANS} +The \name{landentrans} operator generates the descending landen +transformation of the given imput values, returning a list of these +values; initial to final in each case. +\begin{Syntax} +\name{landentrans}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +landentrans(0,0.1) & \{\{0,0,0,0,0\},\{0.1,0.0025041751943776, \\ + & 0.00000156772498954046,6.1444078 9914461e-13,0\}\} \\ +\end{Examples} + +\begin{Comments} +The first list ascends in value, and the second descends in value. +\end{Comments} +\end{Operator} + + +\begin{Operator}{EllipticF} +The \name{EllipticF} operator returns the Elliptic Integral of the +First Kind. +\begin{Syntax} +\name{EllitpicF}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticF(0.3, 8.222) & 0.3 \\ +EllipticF(7.396, 0.1) & 7.58123216114307 \\ +\end{Examples} + +\begin{Comments} +The Complete Elliptic Integral of the First Kind can be found by +putting the first argument to pi/2 or by using \name{EllipticK} +and the second argument. +\end{Comments} +\end{Operator} + + +\begin{Operator}{EllipticK} +The \name{EllipticK} operator returns the Elliptic value K. + +\begin{Syntax} +\name{EllipticK}\(\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticK(0.2) & 1.65962359861053 \\ +EllipticK(4.3) & 0.808442364282734 - 1.05562492399206*i \\ +EllipticK(0.000481) & 1.57098526617635 \\ +\end{Examples} + +\begin{Comments} +The \name{EllipticK} function is the Complete Elliptic Integral of +the First Kind. +\end{Comments} +\end{Operator} + +\begin{Operator}{EllipticKprime} +The \name{EllipticK'} operator returns the Elliptic value K(m). + +\begin{Syntax} +\name{EllipticKprime}\(\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticKprime(0.2) & 2.25720532682085 \\ +EllipticKprime(4.3) & 1.05562492399206 \\ +EllipticKprime(0.000481) & 5.206621921966 \\ +\end{Examples} + +\begin{Comments} +The \name{EllipticKprime} function is the Complete Elliptic Integral of +the First Kind of (1-m). +\end{Comments} +\end{Operator} + + +\begin{Operator}{EllipticE} +The \name{EllipticE} operator used with two arguments +returns the Elliptic Integral of the Second Kind. +\begin{Syntax} +\name{EllipticE}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticE(1.2,0.22) & 1.15094019180949 \\ +EllipticE(0,4.35) & 0 \\ +EllipticE(9,0.00719) & 8.98312465929145 \\ +\end{Examples} + +\begin{Comments} +The Complete Elliptic Integral of the Second Kind can be obtained by +using just the second argument, or by using pi/2 as the first argument. +\end{Comments} + +The \name{EllipticE} operator used with one argument +returns the Elliptic value E. +\begin{Syntax} +\name{EllipticE}\(\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticE(0.22) & 1.48046637439519 \\ +EllipticE(pi/2, 0.22) & 1.48046637439519 \\ +\end{Examples} + +\end{Operator} + +\begin{Operator}{EllipticTHETA} +The \name{EllipticTheta} operator returns one of the four Theta +functions. It cannot except any number other than 1,2,3 or 4 as +its first argument. + +\begin{Syntax} +\name{EllipticTheta}\(\meta{integer},\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +EllipticTheta(1, 1.4, 0.72) & 0.91634775373 \\ +EllipticTheta(2, 3.9, 6.1 ) & -48.0202736969 + 20.9881034377 i \\ +EllipticTheta(3, 0.67, 0.2) & 1.0083077448 \\ +EllipticTheta(4, 8, 0.75) & 0.894963369304 \\ +EllipticTheta(5, 1, 0.1) & ***** In EllipticTheta(a,u,m); a = 1,2,3 or 4. + \\ +\end{Examples} + +\begin{Comments} +Theta functions are important because every one of the Jacobian +Elliptic functions can be expressed as the ratio of two theta functions. +\end{Comments} +\end{Operator} + +\begin{Operator}{JacobiZETA} +The \name{JacobiZeta} operator returns the Jacobian function Zeta. + +\begin{Syntax} +\name{JacobiZeta}\(\meta{expression},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +JacobiZeta(3.2, 0.8) & - 0.254536403439 \\ +JacobiZeta(0.2, 1.6) & 0.171766095970451 - 0.0717028569800147*i \\ +\end{Examples} + +\begin{Comments} +The Jacobian function Zeta is related to the Jacobian function Theta. +But it is significantly different from Riemann's Zeta Function \nameref{Zeta}. +\end{Comments} +\end{Operator} + +\subsection{Gamma and Related Functions} +\begin{Operator}{POCHHAMMER} + +The \name{Pochhammer} operator implements the Pochhammer notation +(shifted factorial). + +\begin{Syntax} +\name{Pochhammer}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +pochhammer(17,4); & 116280 \\ + +pochhammer(1/2,z); & + \rfrac{factorial(2*z)}{(2^{2*z}*factorial(z))} +\end{Examples} + +\begin{Comments} +A number of complex rules for \name{Pochhammer} are inactive, because they +cause a huge system load in algebraic mode. If one wants to use more rules +for the simplification of Pochhammer's notation, one can do: +\\ +let special!*pochhammer!*rules; + +\end{Comments} +\end{Operator} + +\begin{Operator}{GAMMA} +The \name{Gamma} operator returns the Gamma function. + +\begin{Syntax} + +\name{Gamma}\(\meta{expression}\) + +\end{Syntax} + +\begin{Examples} +gamma(10); & 362880 \\ +gamma(1/2); & sqrt(pi) +\end{Examples} +\end{Operator} + +\begin{Operator}{BETA} +The \name{Beta} operator returns the Beta function defined by + + Beta (z,w) := defint(t**(z-1)* (1 - t)**(w-1),t,0,1) . + +\begin{Syntax} + +\name{Beta}\(\meta{expression},\meta{expression}\) + +\end{Syntax} + +\begin{Examples} +Beta(2,2); & 1 / 6 \\ +Beta(x,y); & gamma(x)*gamma(y) / gamma(x + y) +\end{Examples} + +\begin{Comments} +The operator \name{Beta} is simplified towards the \nameref{GAMMA} operator. +\end{Comments} +\end{Operator} + +\begin{Operator}{PSI} +\index{Euler's constant} +The \name{Psi} operator returns the Psi (or DiGamma) function. + + Psi(x) := df(Gamma(z),z)/ Gamma (z) + +\begin{Syntax} + +\name{Gamma}\(\meta{expression}\) + +\end{Syntax} + +\begin{Examples} +Psi(3); & (2*log(2) + psi(1/2) + psi(1) + 3)/2 \\ +on rounded; \\ +- Psi(1); & 0.577215664902 +\end{Examples} + +\begin{Comments} +Euler's constant can be found as - Psi(1). +\end{Comments} +\end{Operator} + +\begin{Operator}{POLYGAMMA} +The \name{Polygamma} operator returns the Polygamma function. + + Polygamma(n,x) := df(Psi(z),z,n); + +\begin{Syntax} +\name{Polygamma}\(\meta{integer},\meta{expression}\) +\end{Syntax} + +\begin{Examples} + Polygamma(1,2); & (pi^2 - 6) / 6\\ +on rounded; \\ +Polygamma(1,2.35); & 0.52849689109 +\end{Examples} + +\begin{Comments} +The Polygamma function is used for simplification of the \nameref{ZETA} +function for some arguments. +\end{Comments} +\end{Operator} + +\subsection{Miscellaneous Functions} + +\begin{Operator}{DILOG extended} +\index{Spence's Integral} +The package \name{specfn} supplies an extended support for the +\nameref{dilog} operator which implements the \nameindex{dilogarithm function}. + +dilog(x) := - defint(log(t)/(t - 1),t,1,x); + +\begin{Syntax} +\name{Dilog}\(\meta{order},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +defint(log(t)/(t - 1),t,1,x); & - dilog (x) \\ +dilog 2; & - pi^2 /12 \\ + +on rounded; \\ +Dilog 20; & - 5.92783972438 +\end{Examples} + +\begin{Comments} +The operator \name{Dilog} is sometimes called Spence's Integral for n = 2. +\end{Comments} +\end{Operator} + +\begin{Operator}{Lambert_W function} +Lambert's W function is the inverse of the function w * e^w. +It is used in the \nameref{solve} package for equations containing +exponentials and logarithms. + +\begin{Syntax} +\name{Lambert\_W}\(\meta{z}\) +\end{Syntax} + +\begin{Examples} +Lambert_W(-1/e); & -1 \\ +solve(w + log(w),w); & {w=lambert\_w(1)}\\ +on rounded; \\ +Lambert_W(-0.05); & - 0.0527059835515 +\end{Examples} + +\begin{Comments} +The current implementation will compute the principal branch in +rounded mode only. +\end{Comments} +\end{Operator} + +\subsection{Orthogonal Polynomials} + +\begin{Operator}{ChebyshevT} +The \name{ChebyshevT} operator computes the nth Chebyshev T Polynomial (of the +first kind). + +\begin{Syntax} +\name{ChebyshevT}\(\meta{integer},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +ChebyshevT(3,xx); & xx*(4*xx^2 - 3) \\ + +ChebyshevT(3,4); & 244 +\end{Examples} + +\begin{Comments} +Chebyshev's T polynomials are computed using the recurrence relation: + +ChebyshevT(n,x) := 2x*ChebyshevT(n-1,x) - ChebyshevT(n-2,x) with \\ +ChebyshevT(0,x) := 0 and ChebyshevT(1,x) := x +\end{Comments} +\end{Operator} + +\begin{Operator}{ChebyshevU} +The \name{ChebyshevU} operator returns the nth Chebyshev U Polynomial (of the +second kind). + +\begin{Syntax} +\name{ChebyshevU}\(\meta{integer},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +ChebyshevU(3,xx); & 4*x*(2*x^2 - 1) \\ + +ChebyshevU(3,4); & 496 +\end{Examples} + +\begin{Comments} +Chebyshev's U polynomials are computed using the recurrence relation: + +ChebyshevU(n,x) := 2x*ChebyshevU(n-1,x) - ChebyshevU(n-2,x) with \\ +ChebyshevU(0,x) := 0 and ChebyshevU(1,x) := 2x + +\end{Comments} +\end{Operator} + +\begin{Operator}{HermiteP} +The \name{HermiteP} operator returns the nth Hermite Polynomial. + +\begin{Syntax} +\name{HermiteP}\(\meta{integer},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +HermiteP(3,xx); & 4*xx*(2*xx^2 - 3) \\ +HermiteP(3,4); & 464 +\end{Examples} + +\begin{Comments} +Hermite polynomials are computed using the recurrence relation: + \\ +HermiteP(n,x) := 2x*HermiteP(n-1,x) - 2*(n-1)*HermiteP(n-2,x) with \\ +HermiteP(0,x) := 1 and HermiteP(1,x) := 2x + +\end{Comments} +\end{Operator} + + +\begin{Operator}{LaguerreP} +The \name{LaguerreP} operator computes the nth Laguerre Polynomial. +The two argument call of LaguerreP is a (common) abbreviation of +LaguerreP(n,0,x). + +\begin{Syntax} +\name{LaguerreP}\(\meta{integer},\meta{expression}\) or\\ +\name{LaguerreP}\(\meta{integer},\meta{expression},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +LaguerreP(3,xx); & (- xx^3 + 9*xx^2 - 18*xx + 6)/6\\ + +LaguerreP(2,3,4); & -2 +\end{Examples} + +\begin{Comments} +Laguerre polynomials are computed using the recurrence relation: + +LaguerreP(n,a,x) := (2n+a-1-x)/n*LaguerreP(n-1,a,x) - + (n+a-1) * LaguerreP(n-2,a,x) with \\ + \\ +LaguerreP(0,a,x) := 1 and LaguerreP(2,a,x) := -x+1+a +\end{Comments} +\end{Operator} + +\begin{Operator}{LegendreP} +The binary \name{LegendreP} operator computes the nth Legendre +Polynomial which is +a special case of the nth Jacobi Polynomial with \\ + \\ +LegendreP(n,x) := JacobiP(n,0,0,x)\\ + \\ +The ternary form returns the associated Legendre Polynomial (see below). + +\begin{Syntax} +\name{LegendreP}\(\meta{integer},\meta{expression}\) or\\ +\name{LegendreP}\(\meta{integer},\meta{expression},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +LegendreP(3,xx); &\rfrac{xx*(5*xx^2 - 3)}{2}\\ + +LegendreP(3,2,xx); &15*xx*( - xx^2 + 1) +\end{Examples} + +\begin{Comments} +The ternary form of the operator \name{LegendreP} is the associated +Legendre Polynomial defined as \\ +\\ + P(n,m,x) = (-1)**m * (1-x**2)**(m/2) * df(LegendreP(n,x),x,m) +\end{Comments} +\end{Operator} + +\begin{Operator}{JacobiP} +The \name{JacobiP} operator computes the nth Jacobi Polynomial. + +\begin{Syntax} +\name{JacobiP}\(\meta{integer},\meta{expression},\meta{expression}, + \meta{expression}\) +\end{Syntax} + +\begin{Examples} +JacobiP(3,4,5,xx); & \rfrac{7*(65*xx^3 - 13*xx^2 - 13*xx + 1)}{8}\\ + +JacobiP(3,4,5,6); & 94465/8 +\end{Examples} + +\end{Operator} + +\begin{Operator}{GegenbauerP} +\index{ultraspherical polynomials} +The \name{GegenbauerP} operator computes Gegenbauer's (ultraspherical) +polynomials. + +\begin{Syntax} +\name{GegenbauerP}\(\meta{integer},\meta{expression},\meta{expression}\) +\end{Syntax} + +\begin{Examples} +GegenbauerP(3,2,xx); & 4*xx*(8*xx^2 - 3)\\ + +GegenbauerP(3,2,4); & 2000 +\end{Examples} + +\end{Operator} + +\begin{Operator}{SolidHarmonicY} +\index{Solid harmonic polynomials} +The \name{SolidHarmonicY} operator computes Solid harmonic (Laplace) +polynomials. + +\begin{Syntax} + +\name{SolidHarmonicY}\(\meta{integer},\meta{integer}, +\meta{expression},\meta{expression},\meta{expression},\meta{expression}\) + +\end{Syntax} + +\begin{Examples} + +SolidHarmonicY(3,-2,x,y,z,r2); & + +\rfrac{sqrt(105)*z*(-2*i*x*y + x^2 - y^2)}{4*sqrt(pi)*sqrt(2)}\\ + +\end{Examples} + +\end{Operator} + +\begin{Operator}{SphericalHarmonicY} +\index{Spherical harmonic polynomials} +The \name{SphericalHarmonicY} operator computes Spherical harmonic (Laplace) +polynomials. These are special cases of the +solid harmonic polynomials, \nameref{SolidHarmonicY}. + +\begin{Syntax} + +\name{SphericalHarmonicY}\(\meta{integer},\meta{integer}, +\meta{expression},\meta{expression}\) + +\end{Syntax} + +\begin{Examples} +SphericalHarmonicY(3,2,theta,phi); & + +\rfrac{sqrt(105)*cos(theta)*sin(theta)^2*(cos(phi)^2+2*cos(phi)*sin(phi)*i- +sin(phi)^2)}{4*sqrt(pi)*sqrt(2)}\\ + +\end{Examples} + +\end{Operator} + + +\subsection{Integral Functions} +\index{sine integral function} +\begin{Operator}{Si} +\index{Sine integral function}\index{integral function} +The \name{Si} operator returns the Sine Integral function. + +\begin{Syntax} +\name{Si}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +limit(Si(x),x,infinity); & pi / 2 \\ +on rounded; \\ +Si(0.35); & 0.347626790989 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{Si} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{Shi} +\index{hyperbolic sine integral function}\index{integral function} +The \name{Shi} operator returns the hyperbolic Sine Integral function. + +\begin{Syntax} +\name{Shi}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +df(shi(x),x); & sinh(x) / x \\ +on rounded; \\ +Shi(0.35); & 0.352390716351 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{Shi} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{s_i} +\index{sine integral function}\index{integral function} +The \name{s_i} operator returns the Sine Integral function si. + +\begin{Syntax} +\name{s_i}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +s_i(xx); & (2*Si(xx) - pi) / 2 \\ +df(s_i(x),x); & sin(x) / x +\end{Examples} + +\begin{Comments} +The operator name \name{s_i} is simplified towards \nameref{SI}. +Since REDUCE is not case sensitive by default the name ``si'' can't be +used. +\end{Comments} +\end{Operator} + +\begin{Operator}{Ci} +\index{cosine integral function} +The \name{Ci} operator returns the Cosine Integral function. + +\begin{Syntax} +\name{Ci}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +defint(cos(t)/t,t,x,infinity); & - ci (x) \\ +on rounded; \\ +Ci(0.35); & - 0.50307556932 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{Ci} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{Chi} +\index{hyperbolic cosine integral function}\index{integral function} +The \name{Chi} operator returns the Hyperbolic Cosine Integral function. + +\begin{Syntax} +\name{Chi}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +defint((cosh(t)-1)/t,t,0,x); & - log(x) + psi(1) + chi(x)\\ +on rounded; \\ +Chi(0.35); & - 0.44182471827 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{Chi} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{ERF extended} +\index{error function} +The special function package supplies an extended support for the +\nameref{erf} operator which implements the \nameindex{error function} \\ + \\ + defint(e**(-x**2),x,0,infinity) * 2/sqrt(pi) \\ +.\\ +\begin{Syntax} +\name{erf}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +erf(-x); & - erf(x)\\ +on rounded; \\ +erf(0.35); & 0.379382053562 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{erf} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{erfc} +\index{error function}\index{complementary error function} +The \name{erfc} operator returns the complementary Error function\\ + \\ + 1 - defint(e**(-x**2),x,0,infinity) * 2/sqrt(pi) \\ +.\\ +\begin{Syntax} +\name{erfc}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +erfc(xx); & - erf(xx) + 1 +\end{Examples} + +\begin{Comments} +The operator \name{erfc} is simplified towards the \nameref{erf} operator. +\end{Comments} +\end{Operator} + +\begin{Operator}{Ei} +\index{exponential integral function} +The \name{Ei} operator returns the Exponential Integral function. + +\begin{Syntax} +\name{Ei}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +df(ei(x),x); & \rfrac{e^x}{x}\\ +on rounded; \\ +Ei(0.35); & - 0.0894340019184 +\end{Examples} + +\begin{Comments} +The numeric values for the operator \name{Ei} are computed via the +power series representation, which limits the argument range. +\end{Comments} +\end{Operator} + +\begin{Operator}{Fresnel_C} +The \name{Fresnel_C} operator represents Fresnel's Cosine function. + +\begin{Syntax} +\name{Fresnel_C}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +int(cos(t^2*pi/2),t,0,x); & fresnel\_c(x) \\ +on rounded; \\ +fresnel_c(2.1); & 0.581564135061 +\end{Examples} + +\begin{Comments} +The operator \name{Fresnel_C} has a limited numeric evaluation of +large values of its argument. +\end{Comments} +\end{Operator} + +\begin{Operator}{Fresnel_S} +The \name{Fresnel_S} operator represents Fresnel's Sine Integral function. + +\begin{Syntax} +\name{Fresnel_S}\(\meta{expression}\) +\end{Syntax} + +\begin{Examples} +int(sin(t^2*pi/2),t,0,x); & fresnel\_s(x) \\ +on rounded; \\ +fresnel_s(2.1); & 0.374273359378 +\end{Examples} + +\begin{Comments} +The operator \name{Fresnel_S} has a limited numeric evaluation of +large values of its argument. +\end{Comments} +\end{Operator} + +\subsection{Combinatorial Operators} + +\begin{Operator}{BINOMIAL} +The \name{Binomial} operator returns the Binomial coefficient if both +parameter are integer and expressions involving the Gamma function otherwise. + +\begin{Syntax} + +\name{Binomial}\(\meta{integer},\meta{integer}\) + +\end{Syntax} + +\begin{Examples} +Binomial(49,6); & 13983816 \\ + +Binomial(n,3); & \rfrac{gamma(n + 1)}{6*gamma(n - 2)} +\end{Examples} + +\begin{Comments} +The operator \name{Binomial} evaluates the Binomial coefficients from +the explicit form and therefore it is not the best algorithm if you +want to compute many binomial coefficients with big indices in which +case a recursive algorithm is preferable. +\end{Comments} +\end{Operator} + +\begin{Operator}{STIRLING1} +The \name{Stirling1} operator returns the Stirling Numbers S(n,m) of the first +kind, i.e. the number of permutations of n symbols which have exactly m cycles +(divided by (-1)**(n-m)). + +\begin{Syntax} +\name{Stirling1}\(\meta{integer},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Stirling1 (17,4); & -87077748875904 \\ +Stirling1 (n,n-1); & \rfrac{-gamma(n+1)}{2*gamma(n-1)} +\end{Examples} + +\begin{Comments} +The operator \name{Stirling1} evaluates the Stirling numbers of the +first kind by rulesets for special cases or by a computing the closed +form, which is a series involving the operators \nameref{BINOMIAL} +and \nameref{STIRLING2}. +\end{Comments} +\end{Operator} + +\begin{Operator}{STIRLING2} +The \name{Stirling1} operator returns the Stirling Numbers S(n,m) of the +second kind, i.e. the number of ways of partitioning a set of n elements +into m non-empty subsets. + +\begin{Syntax} +\name{Stirling2}\(\meta{integer},\meta{integer}\) +\end{Syntax} + +\begin{Examples} +Stirling2 (17,4); & 694337290 \\ +Stirling2 (n,n-1); & \rfrac{gamma(n+1)}{2*gamma(n-1)} +\end{Examples} + +\begin{Comments} +The operator \name{Stirling2} evaluates the Stirling numbers of the +second kind by rulesets for special cases or by a computing the closed +form. +\end{Comments} +\end{Operator} + +\subsection{3j and 6j symbols} + +\begin{Operator}{ThreejSymbol} +The \name{ThreejSymbol} operator implements the 3j symbol. + +\begin{Syntax} + +\name{ThreejSymbol}\(\meta{list of j1,m1},\meta{list of j2,m2}, +\meta{list of j3,m3}\) + +\end{Syntax} + +\begin{Examples} + +ThreejSymbol({j+1,m},{j+1,-m},{1,0}); & + +\rfrac{( - 1)^j *(abs(j - m + 1) - abs(j + m + 1))} + { 2*sqrt(2*j^3 + 9*j^2 + 13*j + 6)*( - 1)^m}\\ + +\end{Examples} +\end{Operator} + +\begin{Operator}{Clebsch_Gordan} +The \name{Clebsch\_Gordan} operator implements the Clebsch\_Gordan +coefficients. This is closely related to the \nameref{Threejsymbol}. + +\begin{Syntax} + +\name{Clebsch\_Gordan}\(\meta{list of j1,m1},\meta{list of j2,m2}, +\meta{list of j3,m3}\) + +\end{Syntax} + +\begin{Examples} + Clebsch_Gordan({2,0},{2,0},{2,0}); & \rfrac{-2}{sqrt(14)}\\ +\end{Examples} +\end{Operator} + +\begin{Operator}{SixjSymbol} +The \name{SixjSymbol} operator implements the 6j symbol. +\begin{Syntax} + +\name{SixjSymbol}\(\meta{list of j1,j2,j3},\meta{list of l1,l2,l3}\) + +\end{Syntax} +\begin{Examples} + +SixjSymbol({7,6,3},{2,4,6}); & \rfrac{1}{14*sqrt(858)}\\ + +\end{Examples} + +\begin{Comments} +The operator \name{SixjSymbol} uses the \nameref{ineq} package in order +to find minima and maxima for the summation index. +\end{Comments} +\end{Operator} + +\subsection{Miscellaneous} + + +\begin{Operator}{HYPERGEOMETRIC} +\index{hypergeometric function} +\index{generalized hypergeometric function} +The \name{Hypergeometric} operator provides simplifications for the +generalized hypergeometric functions. +The \name{Hypergeometric} operator is included in the package specfn2. + +\begin{Syntax} +\name{hypergeometric}\(\meta{list of parameters},\meta{list of parameters}, + \meta{argument}\) +\end{Syntax} + +\begin{Examples} +load specfn2;\\ +hypergeometric ({1/2,1},{3/2},-x^2); & \rfrac{atan(x)}{x}\\ +hypergeometric ({},{},z); & e^z +\end{Examples} + +\begin{Comments} +The special case where the length of the first list is equal to 2 and +the length of the second list is equal to 1 is often called +``the hypergeometric function'' (notated as 2F1(a1,a2,b;x)). +\end{Comments} +\end{Operator} + +\begin{Operator}{MeijerG} +The \name{MeijerG} operator provides simplifications for Meijer's G +function. The simplifications are performed towards polynomials, +elementary or +special functions or (generalized) \nameref{hypergeometric} functions. + +The \name{MeijerG} operator is included in the package specfn2. + +\begin{Syntax} +\name{MeijerG}\(\meta{list of parameters},\meta{list of parameters}, + \meta{argument}\) +\end{Syntax} +The first element of the lists has to be the list containing the +first group (mostly called ``m'' and ``n'') of parameters. This passes +the four parameters of a Meijer's G function implicitly via the +length of the lists. + +\begin{Examples} +load specfn2;\\ +MeijerG({{},1},{{0}},x); & heaviside(-x+1)\\ +MeijerG({{}},{{1+1/4},1-1/4},(x^2)/4) * sqrt pi; + & \rfrac{sqrt(2)*sin(x)*x^2}{4*sqrt(x)} +\end{Examples} + +\begin{Comments} +Many well-known functions can be written as G functions, +e.g. exponentials, logarithms, trigonometric functions, Bessel functions +and hypergeometric functions. +The formulae can be found e.g. in \\ +A.P.Prudnikov, Yu.A.Brychkov, O.I.Marichev: +Integrals and Series, Volume 3: More special functions, +Gordon and Breach Science Publishers (1990). +\end{Comments} +\end{Operator} + +\begin{Operator}{Heaviside} + +The \name{Heaviside} operator returns the Heaviside function. \\ + +Heaviside(~w) => if (w < 0) then 0 else 1 \\ + when numberp w; + +\begin{Syntax} +\name{Heaviside}\(\meta{argument}\) +\end{Syntax} + +\begin{Comments} +This operator is often included in the result of the simplification +of a generalized \nameref{hypergeometric} function or a +\nameref{MeijerG} function. + +No simplification is done for this function. +\end{Comments} +\end{Operator} + +\begin{Operator}{erfi} + +The \name{erfi} operator returns the error function of an imaginary argument. + +erfi(~x) => 2/sqrt(pi) * defint(e**(t**2),t,0,x); + +\begin{Syntax} +\name{erfi}\(\meta{argument}\) +\end{Syntax} + +\begin{Comments} +This operator is sometimes included in the result of the simplification +of a generalized \nameref{hypergeometric} function or a +\nameref{MeijerG} function. + +No simplification is done for this function. +\end{Comments} +\end{Operator} + Index: r36/help/rdebug.tex ================================================================== --- r36/help/rdebug.tex +++ r36/help/rdebug.tex @@ -1,381 +1,381 @@ -\begin{document} - -\begin{Introduction}{Debugging} - -The package \name{RDEBUG} helps you to find bugs in algebraic -REDUCE programs by making the functions of the PSL package -\name{DEBUG} available for algebraic mode. -The following facilities are available: - -Entry-exit trace (\nameref{tr}, \nameref{untr}): -visualize every call of -explicitly declared functions, printing their arguments and -results. - -Assignment trace (\nameref{trst}, \nameref{untrst}): -report all assignments which -are executed inside explicitly declared functions. This facility -is not available for compiled functions. - -Breakpoint (\nameref{br}, \nameref{unbr}): -interrupt the program execution at -entry and exit of explicitly declared functions, invoking -a \nameref{breakloop}. - -Conditional trace (\nameref{trwhen}, \nameref{untrwhen}) -or break (\nameref{brwhen},\nameref{unbrwhen}). - -Rule trace (\nameref{trrl}, \nameref{untrrl}): -report the arguments and results of a rule whenever it fires. - -You can control the debug output using the operator \nameref{trout} -and the variable \nameref{trlimit}. - -\end{Introduction} - -%============================================================= - -\begin{Concept}{breakloop} -\index{debug} -A \name{break loop} is an interrupt of the program execution -where control is given temporarily to the terminal for -entering commands in a standard command - evaluate - print loop. -When a break occurs, you can inspect the current - environment or even alter it, and the -interrupted computation may be terminated or continued. -A break can be caused - -- by an internal error when the switch \nameref{break} is on, - -- by an explicit call of \name{lisp break()}, - -- at entry and exit time of a procedure which has been - declared by \nameref{br}. - -In a break situation the evaluation is stopped temporarily -and the control returns to the terminal with a special prompt: -\name{break[1]1:}. -The number in square brackets counts the break level - it is -increased when a break occurs inside a break; the normal -REDUCE statement counter follows. Each break loop supports its -own statement numbers and input and output buffers. -After terminating of a break loop the -previous statement counters and buffers are restored. - -In a break loop all REDUCE commands can be -entered. Additionally, there is a set of single character commands -which allow you to control the break environment. All these -begin with an underscore character: - - -\name{\_a;} terminate break and return to the top REDUCE level - -\name{\_c;} continue execution of interrupted procedure - -\name{\_i;} print a backtrace (list of procedures in the - call hierarchy) - -\name{\_l} \meta{var}; (local) read the content of the local variable - \meta{var} - -\name{\_m;} print the last (LISP-) error message - -\name{\_q;} terminate the break loop and return to the next - higher level. - - -Global variables can be accessed as usual in the REDUCE language. -They can also be set to different values in the break loop. -The inspect values assigned to dummy arguments and scalar variables of -procedures in the actual call hierarchy, you need a special command -\name{\_l}. These values cannot be altered in the break loop. -\begin{Examples} - procedure p1(x); \\ - begin scalar y1; y1:=x^2; return p2(y1); end;\\ - procedure p2(q); q^2;\\ - br p2;\\ - x:=22;\\ - p1(alpha);\\ -p2 being entered\\ - - q: alpha**2$\\ -Break before entering `p2'\\ -break[1]1: x; & 22\\ -break[1]2: _l x; & alpha\\ -break[1]3: _l y1; & alpha^2 \\ -break[1]4: _l q;& alpha^2 \\ -break[1]6: _c;\\ -Break after call `p2', value `(expt (expt alpha 2) 2)'\\ -break[1]1: _c;\\ -&alpha^4\\ -\end{Examples} -In the corresponding break loop caused by calling \name{p2} -indirectly via \name{p1}, you can access the global \name{x}, the -locals \name{x} and \name{y1} of \name{p1} and the \name{q} of -\name{p2}. -\end{Concept} - -%========================================================= - -\begin{Operator}{tr} -\index{trace}\index{debug} -The command \name{tr} puts one or several procedures to -under trace. Every time such a function is executed, a message -is printed during the procedure entry and another one is generated -at the return time. The entry message records the -actual procedure arguments equated to the dummy parameter -names, and at the exit time the procedure value is printed. -Recursive calls are marked by an indentation and a level number. - -\begin{Syntax} - \name{tr}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -Here \meta{proc1},\meta{proc2},...,\meta{procn} -are names of procedures -to be added to the set of traced procedures. See also -\nameref{trst},\nameref{trwhen}. -\end{Operator} - -\begin{Operator}{untr} -\index{trace}\index{debug} -Tracing is stopped for one or several functions by the -command \name{untr}: -\begin{Syntax} - \name{untr}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -\end{Operator} - -%======================================================== - -\begin{Operator}{trst} -\index{trace}\index{assignment-trace}\index{debug} -Sometimes one needs detailed information about the inner behavior of -a procedure, especially if it is a longer piece of code. -For a procedure declared in a \name{trst} command -an extended trace is performed: -all executed explicit assignments and all passed labels -are reported at run time. - -\begin{Syntax} - \name{trst}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -Here \meta{proc1},\meta{proc2},...,\meta{procn} -are names of procedures -to be added to the set of traced procedures. - -When your program contains a \nameref{for} loop, -REDUCE translates this to a sequential piece of -LISP instructions. When using \name{trst}, the printout -is driven by the unfolded code. When the code contains a -\name{for-each-in} statement, the name of the control variable is -internally used to keep the remainder of the list during the loop -control, and you will see the corresponding assignments -in the printout rather than the individual values in the -loop steps. -\end{Operator} - -\begin{Operator}{untrst} -\index{trace}\index{assignment-trace}\index{debug} -Extended tracing is stopped for one or several functions by the -command \name{untrst}: -\begin{Syntax} - \name{untrst}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -\end{Operator} - -%========================================================= - -\begin{Operator}{trwhen} -\index{trace}\index{debug} -The trace output can be tunrned on or off automatically by -a boolean expression which is linked to a traced procedure -by the command \name{trwhen}: -\begin{Syntax} - trwhen \meta{name},\meta{booleanexpr}; -\end{Syntax} -The boolean expression must follow -standard REDUCE syntax. It may contain references -to global values and to -the actual parameters of the procedure. As long as the -procedure is not compiled, the original names of the dummy arguments -are used. For a compiled procedure the original names -are not available; instead the names \name{a1}, \name{a2}, ... -must be used. Example: the following procedure produces trace -output only if the main variable of its argument is \name{x}: -\begin{Examples} - procedure hugo(u); otto(u);\\ - tr hugo;\\ - trwhen hugo,mainvar(u)=x;\\ -\end{Examples} -Note: for a symbolic procedure, the \name{trwhen} command -must be given in symbolic mode or with prefix $symbolic$. - -\end{Operator} - -\begin{Operator}{untrwhen} -\index{trace}\index{debug} -Conditional trace is stopped for a procedure by calling -\begin{Syntax} - untrwhen \meta{name}; -\end{Syntax} -\end{Operator} - -%======================================================== - -\begin{Switch}{break} -\index{debug} - -When the switch \name{break} is set on, every -evaluation error causes a \nameref{breakloop}. Most of these -breaks are non-continuable; however, you have the -opportunity to read the actual values of local variables -in the environment which caused the error. -\end{Switch} - -%========================================================= - -\begin{Operator}{br} -\index{break}\index{debug} -The command \name{br} declares one or several procedures -as breakpoints. When executing such a function, the -computation is interrupted by a \nameref{breakloop} -at function enter and return times. - -\begin{Syntax} - \name{br}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -Here \meta{proc1},\meta{proc2},...,\meta{procn} -are names of procedures -to be added to the set of break points. -See also \nameref{brwhen}. -\end{Operator} - -\begin{Operator}{unbr} -\index{break}\index{debug} -The break property -can be removed by the command \name{unbr}: -\begin{Syntax} - \name{unbr}\meta{proc1},\meta{proc2},...,\meta{procn}; -\end{Syntax} -\end{Operator} - -% ============================================================= - -\begin{Operator}{brwhen} -\index{break}\index{debug} -The break point (see \nameref{br}) - can be tunrned on or off automatically by -a boolean expression which is linked to a breakpoint procedure -by the command \name{brwhen}: -\begin{Syntax} - brwhen \meta{name},\meta{booleanexpr}; -\end{Syntax} -The boolean expression must follow -standard REDUCE syntax. It may contain references -to global values and to -the actual parameters of the procedure. As long as the -procedure is not compiled, the original names of the dummy arguments -are used. For a compiled procedure the original names -are not available; instead the names \name{a1}, \name{a2}, ... -must be used. Example: the following procedure is broken -only if the main variable of its argument is \name{x}: -\begin{Examples} - procedure hugo(u); otto(u);\\ - br hugo;\\ - brwhen hugo,mainvar(u)=x;\\ -\end{Examples} -Note: for a symbolic procedure, the \name{brwhen} command -must be given in symbolic mode or with prefix $symbolic$. - -\end{Operator} - -\begin{Operator}{unbrwhen} -\index{break}\index{debug} -Conditional break is removed for a procedure by calling -\begin{Syntax} - unbrwhen \meta{name}; -\end{Syntax} -\end{Operator} - -% ============================================================== - -\begin{Operator}{trrl} -\index{debug}\index{rule}\index{ruleset} -The command \name{trrl} allows you to trace individual rules -or rule sets when they fire. -\begin{Syntax} - trrl \meta{rs1},\meta{rs2},...,\meta{rsn}; -\end{Syntax} -where each of the \meta{rsi} is - -- a rule or a rule set, - -- a name of a rule or rule set (that is a non--indexed variable which - is bound to a rule or rule list), - -- an operator name, representing the rules assigned to this - operator. - -The specified rules are (re-) activated in REDUCE in -a style that each of them prints a report every time if fires. -The report is composed of the name or the rule or the -name of the rule set plus the number of the rule in the set, -the form matching the left hand side and the -resulting right hand side. -For an explicitly given rule, \name{trrl} assigns a generated name. -\end{Operator} - -\begin{Operator}{untrrl} -\index{debug}\index{rule}\index{ruleset} -With \name{untrrl} you can remove the tracing from rules -\begin{Syntax} - untrrl \meta{rs1},\meta{rs2},...,\meta{rsn}; -\end{Syntax} -The rules are reactivated in their original form. Alternatively -you can use the command \nameref{clearrules} to remove the -rules totally from the system. Please do not modify the -rules between \name{trrl} and \name{untrrl} -- the result -may be unpredictable. -\end{Operator} - -%============================================================== - -\begin{Operator}{trout} -\index{debug}\index{io} -The trace output can be redirected to a separate file -by using the command \name{trout}, followed -by a file name in string quotes. A second call of \name{trout} -closes the actual output file and assigns a new one. -The file name NIL (without string quotes) causes the trace output -to be redirected to the standard output device. - -Remark: under Windows a file name starting with "win:" causes -a new window to be opened which receives the complete -output of the debugging services. -\end{Operator} - -%============================================================== - -\begin{Variable}{trlimit} -\index{debug}\index{io} -The integer valued share variable \name{trlimit} defines -an upper limit for the number of items printed in formula -collections. The -initial value is 5. A different value can be assigned to -increase or lower the output size. -\begin{Examples} - trlimit:=7;\\ -\end{Examples} -\end{Variable} - -%============================================================== - -\begin{Variable}{trprinter} -\index{debug}\index{io} -If you want to select LISP style printing instead of -algebraic printing during trace, set \name{trprinter!*} -to \name{printx}: -\begin{Syntax} - lisp(trprinter!* := 'printx); -\end{syntax} -\end{Variable} +\begin{document} + +\begin{Introduction}{Debugging} + +The package \name{RDEBUG} helps you to find bugs in algebraic +REDUCE programs by making the functions of the PSL package +\name{DEBUG} available for algebraic mode. +The following facilities are available: + +Entry-exit trace (\nameref{tr}, \nameref{untr}): +visualize every call of +explicitly declared functions, printing their arguments and +results. + +Assignment trace (\nameref{trst}, \nameref{untrst}): +report all assignments which +are executed inside explicitly declared functions. This facility +is not available for compiled functions. + +Breakpoint (\nameref{br}, \nameref{unbr}): +interrupt the program execution at +entry and exit of explicitly declared functions, invoking +a \nameref{breakloop}. + +Conditional trace (\nameref{trwhen}, \nameref{untrwhen}) +or break (\nameref{brwhen},\nameref{unbrwhen}). + +Rule trace (\nameref{trrl}, \nameref{untrrl}): +report the arguments and results of a rule whenever it fires. + +You can control the debug output using the operator \nameref{trout} +and the variable \nameref{trlimit}. + +\end{Introduction} + +%============================================================= + +\begin{Concept}{breakloop} +\index{debug} +A \name{break loop} is an interrupt of the program execution +where control is given temporarily to the terminal for +entering commands in a standard command - evaluate - print loop. +When a break occurs, you can inspect the current + environment or even alter it, and the +interrupted computation may be terminated or continued. +A break can be caused + +- by an internal error when the switch \nameref{break} is on, + +- by an explicit call of \name{lisp break()}, + +- at entry and exit time of a procedure which has been + declared by \nameref{br}. + +In a break situation the evaluation is stopped temporarily +and the control returns to the terminal with a special prompt: +\name{break[1]1:}. +The number in square brackets counts the break level - it is +increased when a break occurs inside a break; the normal +REDUCE statement counter follows. Each break loop supports its +own statement numbers and input and output buffers. +After terminating of a break loop the +previous statement counters and buffers are restored. + +In a break loop all REDUCE commands can be +entered. Additionally, there is a set of single character commands +which allow you to control the break environment. All these +begin with an underscore character: + + +\name{\_a;} terminate break and return to the top REDUCE level + +\name{\_c;} continue execution of interrupted procedure + +\name{\_i;} print a backtrace (list of procedures in the + call hierarchy) + +\name{\_l} \meta{var}; (local) read the content of the local variable + \meta{var} + +\name{\_m;} print the last (LISP-) error message + +\name{\_q;} terminate the break loop and return to the next + higher level. + + +Global variables can be accessed as usual in the REDUCE language. +They can also be set to different values in the break loop. +The inspect values assigned to dummy arguments and scalar variables of +procedures in the actual call hierarchy, you need a special command +\name{\_l}. These values cannot be altered in the break loop. +\begin{Examples} + procedure p1(x); \\ + begin scalar y1; y1:=x^2; return p2(y1); end;\\ + procedure p2(q); q^2;\\ + br p2;\\ + x:=22;\\ + p1(alpha);\\ +p2 being entered\\ + + q: alpha**2$\\ +Break before entering `p2'\\ +break[1]1: x; & 22\\ +break[1]2: _l x; & alpha\\ +break[1]3: _l y1; & alpha^2 \\ +break[1]4: _l q;& alpha^2 \\ +break[1]6: _c;\\ +Break after call `p2', value `(expt (expt alpha 2) 2)'\\ +break[1]1: _c;\\ +&alpha^4\\ +\end{Examples} +In the corresponding break loop caused by calling \name{p2} +indirectly via \name{p1}, you can access the global \name{x}, the +locals \name{x} and \name{y1} of \name{p1} and the \name{q} of +\name{p2}. +\end{Concept} + +%========================================================= + +\begin{Operator}{tr} +\index{trace}\index{debug} +The command \name{tr} puts one or several procedures to +under trace. Every time such a function is executed, a message +is printed during the procedure entry and another one is generated +at the return time. The entry message records the +actual procedure arguments equated to the dummy parameter +names, and at the exit time the procedure value is printed. +Recursive calls are marked by an indentation and a level number. + +\begin{Syntax} + \name{tr}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +Here \meta{proc1},\meta{proc2},...,\meta{procn} +are names of procedures +to be added to the set of traced procedures. See also +\nameref{trst},\nameref{trwhen}. +\end{Operator} + +\begin{Operator}{untr} +\index{trace}\index{debug} +Tracing is stopped for one or several functions by the +command \name{untr}: +\begin{Syntax} + \name{untr}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +\end{Operator} + +%======================================================== + +\begin{Operator}{trst} +\index{trace}\index{assignment-trace}\index{debug} +Sometimes one needs detailed information about the inner behavior of +a procedure, especially if it is a longer piece of code. +For a procedure declared in a \name{trst} command +an extended trace is performed: +all executed explicit assignments and all passed labels +are reported at run time. + +\begin{Syntax} + \name{trst}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +Here \meta{proc1},\meta{proc2},...,\meta{procn} +are names of procedures +to be added to the set of traced procedures. + +When your program contains a \nameref{for} loop, +REDUCE translates this to a sequential piece of +LISP instructions. When using \name{trst}, the printout +is driven by the unfolded code. When the code contains a +\name{for-each-in} statement, the name of the control variable is +internally used to keep the remainder of the list during the loop +control, and you will see the corresponding assignments +in the printout rather than the individual values in the +loop steps. +\end{Operator} + +\begin{Operator}{untrst} +\index{trace}\index{assignment-trace}\index{debug} +Extended tracing is stopped for one or several functions by the +command \name{untrst}: +\begin{Syntax} + \name{untrst}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +\end{Operator} + +%========================================================= + +\begin{Operator}{trwhen} +\index{trace}\index{debug} +The trace output can be tunrned on or off automatically by +a boolean expression which is linked to a traced procedure +by the command \name{trwhen}: +\begin{Syntax} + trwhen \meta{name},\meta{booleanexpr}; +\end{Syntax} +The boolean expression must follow +standard REDUCE syntax. It may contain references +to global values and to +the actual parameters of the procedure. As long as the +procedure is not compiled, the original names of the dummy arguments +are used. For a compiled procedure the original names +are not available; instead the names \name{a1}, \name{a2}, ... +must be used. Example: the following procedure produces trace +output only if the main variable of its argument is \name{x}: +\begin{Examples} + procedure hugo(u); otto(u);\\ + tr hugo;\\ + trwhen hugo,mainvar(u)=x;\\ +\end{Examples} +Note: for a symbolic procedure, the \name{trwhen} command +must be given in symbolic mode or with prefix $symbolic$. + +\end{Operator} + +\begin{Operator}{untrwhen} +\index{trace}\index{debug} +Conditional trace is stopped for a procedure by calling +\begin{Syntax} + untrwhen \meta{name}; +\end{Syntax} +\end{Operator} + +%======================================================== + +\begin{Switch}{break} +\index{debug} + +When the switch \name{break} is set on, every +evaluation error causes a \nameref{breakloop}. Most of these +breaks are non-continuable; however, you have the +opportunity to read the actual values of local variables +in the environment which caused the error. +\end{Switch} + +%========================================================= + +\begin{Operator}{br} +\index{break}\index{debug} +The command \name{br} declares one or several procedures +as breakpoints. When executing such a function, the +computation is interrupted by a \nameref{breakloop} +at function enter and return times. + +\begin{Syntax} + \name{br}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +Here \meta{proc1},\meta{proc2},...,\meta{procn} +are names of procedures +to be added to the set of break points. +See also \nameref{brwhen}. +\end{Operator} + +\begin{Operator}{unbr} +\index{break}\index{debug} +The break property +can be removed by the command \name{unbr}: +\begin{Syntax} + \name{unbr}\meta{proc1},\meta{proc2},...,\meta{procn}; +\end{Syntax} +\end{Operator} + +% ============================================================= + +\begin{Operator}{brwhen} +\index{break}\index{debug} +The break point (see \nameref{br}) + can be tunrned on or off automatically by +a boolean expression which is linked to a breakpoint procedure +by the command \name{brwhen}: +\begin{Syntax} + brwhen \meta{name},\meta{booleanexpr}; +\end{Syntax} +The boolean expression must follow +standard REDUCE syntax. It may contain references +to global values and to +the actual parameters of the procedure. As long as the +procedure is not compiled, the original names of the dummy arguments +are used. For a compiled procedure the original names +are not available; instead the names \name{a1}, \name{a2}, ... +must be used. Example: the following procedure is broken +only if the main variable of its argument is \name{x}: +\begin{Examples} + procedure hugo(u); otto(u);\\ + br hugo;\\ + brwhen hugo,mainvar(u)=x;\\ +\end{Examples} +Note: for a symbolic procedure, the \name{brwhen} command +must be given in symbolic mode or with prefix $symbolic$. + +\end{Operator} + +\begin{Operator}{unbrwhen} +\index{break}\index{debug} +Conditional break is removed for a procedure by calling +\begin{Syntax} + unbrwhen \meta{name}; +\end{Syntax} +\end{Operator} + +% ============================================================== + +\begin{Operator}{trrl} +\index{debug}\index{rule}\index{ruleset} +The command \name{trrl} allows you to trace individual rules +or rule sets when they fire. +\begin{Syntax} + trrl \meta{rs1},\meta{rs2},...,\meta{rsn}; +\end{Syntax} +where each of the \meta{rsi} is + +- a rule or a rule set, + +- a name of a rule or rule set (that is a non--indexed variable which + is bound to a rule or rule list), + +- an operator name, representing the rules assigned to this + operator. + +The specified rules are (re-) activated in REDUCE in +a style that each of them prints a report every time if fires. +The report is composed of the name or the rule or the +name of the rule set plus the number of the rule in the set, +the form matching the left hand side and the +resulting right hand side. +For an explicitly given rule, \name{trrl} assigns a generated name. +\end{Operator} + +\begin{Operator}{untrrl} +\index{debug}\index{rule}\index{ruleset} +With \name{untrrl} you can remove the tracing from rules +\begin{Syntax} + untrrl \meta{rs1},\meta{rs2},...,\meta{rsn}; +\end{Syntax} +The rules are reactivated in their original form. Alternatively +you can use the command \nameref{clearrules} to remove the +rules totally from the system. Please do not modify the +rules between \name{trrl} and \name{untrrl} -- the result +may be unpredictable. +\end{Operator} + +%============================================================== + +\begin{Operator}{trout} +\index{debug}\index{io} +The trace output can be redirected to a separate file +by using the command \name{trout}, followed +by a file name in string quotes. A second call of \name{trout} +closes the actual output file and assigns a new one. +The file name NIL (without string quotes) causes the trace output +to be redirected to the standard output device. + +Remark: under Windows a file name starting with "win:" causes +a new window to be opened which receives the complete +output of the debugging services. +\end{Operator} + +%============================================================== + +\begin{Variable}{trlimit} +\index{debug}\index{io} +The integer valued share variable \name{trlimit} defines +an upper limit for the number of items printed in formula +collections. The +initial value is 5. A different value can be assigned to +increase or lower the output size. +\begin{Examples} + trlimit:=7;\\ +\end{Examples} +\end{Variable} + +%============================================================== + +\begin{Variable}{trprinter} +\index{debug}\index{io} +If you want to select LISP style printing instead of +algebraic printing during trace, set \name{trprinter!*} +to \name{printx}: +\begin{Syntax} + lisp(trprinter!* := 'printx); +\end{syntax} +\end{Variable} Index: r36/help/redref1.tex ================================================================== --- r36/help/redref1.tex +++ r36/help/redref1.tex @@ -1,186 +1,186 @@ -%%% -%%% The tree structure for the information browser is -%%% given by the \section, \subsection, \subsubsection commands -%%% - -\section{System interaction} - -%%% -%%% Environments like Switch serve a triple purpose: -%%% - the node is defined -%%% - an index entry "demo switch" is generated -%%% - a cross reference with symbolic name "switch:demo" is generated. -%%% This can be used used the \ref, \pageref, \nameref, -%%% and \see commands. -%%% Additional \index entries or cross reference keys can be generated -%%% with the \index and \label commands. -%%% - -\begin{Switch}{demo} - The \name{demo} switch is used for interactive files, causing - the system to pause after each command in the file until you type a - \key{Return}. Default is \name{off}. - -%%% -%%% The parts of a node are given as environments. Defined are: -%%% Comments, Examples, Related -%%% - \begin{Comments} - The switch \name{demo} has no effect on top level interactive - statements. Use it when you want to slow down operations in a file - so you can see what is happening. - - You can either include the \name{on demo} command in the file, - or enter it from the top level before bringing in any file. Unlike - the \name{pause} command, \name{on demo} does not permit you to - interrupt the file for questions of your own. - \end{Comments} -%%% -%%% The Related environment points to related information. It should -%%% also use a cross ref, but that is not yet implemented -%%% - \begin{Related} - \item [\name{in} command] Reading from files. - \item [\name{echo} switch] Seeing what is read in. - \end{Related} -\end{Switch} - -\section{Polynomials} - -\subsection{Polynomial operators} - -\begin{Operator}{den} - The {den} operator returns the denominator of its argument. -%%% -%%% The syntax description needs perhaps a bit more work. -%%% \name and \arg are purely for printing (i.e. selecting a different -%%% typeface -%%% - \begin{Syntax} - \name{den}\(\arg{expression}\) - \end{Syntax} - \arg{expression} is ordinarily a rational expression, but may be - any valid scalar \REDUCE\ expression. - \begin{Examples} - a := x**3 + 3*x**2 + 12*x; & A := X*(X^2 + 3*X + 12) \\ - b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ - den(a/b); & SIN(X) + 4*Y \\ - den(a/4 + b/5); & 20 \\ - den(100/6); & 3 \\ - den(sin(x)); & 1 \\ - for i := 1:3 sum part(firstlis,i)*part(secondlis,i); & - A*X + B*Y + C*Z - \end{Examples} -\end{Operator} -\begin{Comments} - \name{den} returns the denominator of the expression after it has - been simplified by \REDUCE. As seen in the examples, this includes - putting sums of rational expressions over a common denominator, and - reducing common factors where possible. If the expression does not - have any other denominator, $1$ is returned. - - Switch settings, such as \name{mcd} or \name{rational}, have an - effect on the denominator of an expression. -\end{Comments} - -\subsection{Dependency information} - -\begin{Declaration}{depend} - \name{depend} declares that its first argument depends on the rest - of its arguments. - \begin{Syntax} - \name{depend} \arg{kernel}\{,\arg{kernel}\}\repeated - \end{Syntax} - \arg{kernel} must be a legal variable name or a prefix operator - \see{kernel}). - \begin{Examples} - depend y,x; \\ - df(y**2,x); & 2*DF(Y,X)*Y \\ - depend z,cos(x),y; \\ - df(sin(z),cos(x)); & COS(Z)*DF(Z,COS(X)) \\ - df(z**2,x); & 2*DF(Z,X)*Z \\ - nodepend z,y; \\ - df(z**2,x); & 2*DF(Z,X)*Z \\ - cc := df(y**2,x); & CC := 2*DF(Y,x)*Y \\ - y := tan x; & Y := TAN(X) \\ - cc; & 2*TAN(X)*(TAN(X)^{2} + 1) - \end{Examples} - \begin{Comments} - Dependencies can be removed by using the declaration - \nameref{nodepend}. The differentiation opeartor uses this - information, as shown in the examples above. Linear operators alos - use knowledge of dependencies (see \nameref{linear}). Note that - dependencies can be nested: Having declared $y$ to depend on $x$, - and $z$ to depend on $y$, we see that the chain rule was applied - to the derivative of a function of $z$ with respect to $x$. If the - explicit function of the dependencyis later entered into the - system, terms with \name{DF(Y,X)}, for example, are expanded when - they are displayed again, as shown in the last example. - \end{Comments} -\end{Declaration} - -\section{The Taylor package} - -\begin{Operator}{taylor} - The \name{taylor} operator is used for expansion in power - series\index{series}. - \begin{Syntax} - \name{taylor}\(\arg{expression},% - \{\arg{kernel},\arg{expression},\arg{integer}\}% - \repeated\) - \end{Syntax} - This returns the expansion of the first argument with respect to - \arg{kernel} about \arg{expression} to order \arg{integer}. - \begin{Examples} - taylor(e^(x^2+y^2),x,0,2,y,0,2); & - 1 + Y^2 + X^2 + Y^2*X^2 + O(X^{3},Y^{3})\\ - taylor(log(1+x),x,0,2); & X - \rfrac{1}{2}*X^{2} + O(X^{3}) - \end{Examples} - \begin{Comments} - The expansion is performed variable per variable, i.e.\ in the - example above by first expanding $\exp(x^{2}+y^{2})$ with respect - to $x$ and then expanding every coefficient with respect to $y$. - - If the switch \nameref{taylorkeeporiginal} is set to \name{on} the - original expression is kept for later reference. - - Printing is controlled by the variable \nameref{taylorprintterms}. - - \end{Comments} - \begin{Related} - \item[tps] Truncated Power Series. - \item[Koepf] Complete power series - \end{Related} -\end{Operator} - -\subsection{Controlling the package} - -\begin{Switch}{taylorkeeporiginal} - The \name{taylorkeeporiginal} switch determines whether the - \nameref{taylor} operator keeps the expression to be expanded for - later use. Default is \name{on}. -\end{Switch} - -\begin{Operator}{taylororiginal} - \name{taylororiginal} extracts the original expression from a Taylor - kernel. - \begin{Syntax} - \name{taylororiginal}\(\arg{taylor\_kernel}\) - \end{Syntax} - If the argument is not a Taylor kernel, or if the expression was not - kept, an error is signaled. -\end{Operator} - -\begin{Variable}{taylorprintterms} - - Only a certain number of (non-zero) coefficients of a Taylor - kernel are printed usually. If there are more, \verb|...| is - printed as part of the expression to indicate this. The number of - terms printed is given by the value of the shared algebraic - variable \nameref{taylorprintterms}. Allowed values are integers - and the special identifier \name{all}. The latter setting - specifies that all terms are to be printed. The default setting is - $5$. - -\end{Variable} - +%%% +%%% The tree structure for the information browser is +%%% given by the \section, \subsection, \subsubsection commands +%%% + +\section{System interaction} + +%%% +%%% Environments like Switch serve a triple purpose: +%%% - the node is defined +%%% - an index entry "demo switch" is generated +%%% - a cross reference with symbolic name "switch:demo" is generated. +%%% This can be used used the \ref, \pageref, \nameref, +%%% and \see commands. +%%% Additional \index entries or cross reference keys can be generated +%%% with the \index and \label commands. +%%% + +\begin{Switch}{demo} + The \name{demo} switch is used for interactive files, causing + the system to pause after each command in the file until you type a + \key{Return}. Default is \name{off}. + +%%% +%%% The parts of a node are given as environments. Defined are: +%%% Comments, Examples, Related +%%% + \begin{Comments} + The switch \name{demo} has no effect on top level interactive + statements. Use it when you want to slow down operations in a file + so you can see what is happening. + + You can either include the \name{on demo} command in the file, + or enter it from the top level before bringing in any file. Unlike + the \name{pause} command, \name{on demo} does not permit you to + interrupt the file for questions of your own. + \end{Comments} +%%% +%%% The Related environment points to related information. It should +%%% also use a cross ref, but that is not yet implemented +%%% + \begin{Related} + \item [\name{in} command] Reading from files. + \item [\name{echo} switch] Seeing what is read in. + \end{Related} +\end{Switch} + +\section{Polynomials} + +\subsection{Polynomial operators} + +\begin{Operator}{den} + The {den} operator returns the denominator of its argument. +%%% +%%% The syntax description needs perhaps a bit more work. +%%% \name and \arg are purely for printing (i.e. selecting a different +%%% typeface +%%% + \begin{Syntax} + \name{den}\(\arg{expression}\) + \end{Syntax} + \arg{expression} is ordinarily a rational expression, but may be + any valid scalar \REDUCE\ expression. + \begin{Examples} + a := x**3 + 3*x**2 + 12*x; & A := X*(X^2 + 3*X + 12) \\ + b := 4*x*y + x*sin(x); & B := X*(SIN(X) + 4*Y) \\ + den(a/b); & SIN(X) + 4*Y \\ + den(a/4 + b/5); & 20 \\ + den(100/6); & 3 \\ + den(sin(x)); & 1 \\ + for i := 1:3 sum part(firstlis,i)*part(secondlis,i); & + A*X + B*Y + C*Z + \end{Examples} +\end{Operator} +\begin{Comments} + \name{den} returns the denominator of the expression after it has + been simplified by \REDUCE. As seen in the examples, this includes + putting sums of rational expressions over a common denominator, and + reducing common factors where possible. If the expression does not + have any other denominator, $1$ is returned. + + Switch settings, such as \name{mcd} or \name{rational}, have an + effect on the denominator of an expression. +\end{Comments} + +\subsection{Dependency information} + +\begin{Declaration}{depend} + \name{depend} declares that its first argument depends on the rest + of its arguments. + \begin{Syntax} + \name{depend} \arg{kernel}\{,\arg{kernel}\}\repeated + \end{Syntax} + \arg{kernel} must be a legal variable name or a prefix operator + \see{kernel}). + \begin{Examples} + depend y,x; \\ + df(y**2,x); & 2*DF(Y,X)*Y \\ + depend z,cos(x),y; \\ + df(sin(z),cos(x)); & COS(Z)*DF(Z,COS(X)) \\ + df(z**2,x); & 2*DF(Z,X)*Z \\ + nodepend z,y; \\ + df(z**2,x); & 2*DF(Z,X)*Z \\ + cc := df(y**2,x); & CC := 2*DF(Y,x)*Y \\ + y := tan x; & Y := TAN(X) \\ + cc; & 2*TAN(X)*(TAN(X)^{2} + 1) + \end{Examples} + \begin{Comments} + Dependencies can be removed by using the declaration + \nameref{nodepend}. The differentiation opeartor uses this + information, as shown in the examples above. Linear operators alos + use knowledge of dependencies (see \nameref{linear}). Note that + dependencies can be nested: Having declared $y$ to depend on $x$, + and $z$ to depend on $y$, we see that the chain rule was applied + to the derivative of a function of $z$ with respect to $x$. If the + explicit function of the dependencyis later entered into the + system, terms with \name{DF(Y,X)}, for example, are expanded when + they are displayed again, as shown in the last example. + \end{Comments} +\end{Declaration} + +\section{The Taylor package} + +\begin{Operator}{taylor} + The \name{taylor} operator is used for expansion in power + series\index{series}. + \begin{Syntax} + \name{taylor}\(\arg{expression},% + \{\arg{kernel},\arg{expression},\arg{integer}\}% + \repeated\) + \end{Syntax} + This returns the expansion of the first argument with respect to + \arg{kernel} about \arg{expression} to order \arg{integer}. + \begin{Examples} + taylor(e^(x^2+y^2),x,0,2,y,0,2); & + 1 + Y^2 + X^2 + Y^2*X^2 + O(X^{3},Y^{3})\\ + taylor(log(1+x),x,0,2); & X - \rfrac{1}{2}*X^{2} + O(X^{3}) + \end{Examples} + \begin{Comments} + The expansion is performed variable per variable, i.e.\ in the + example above by first expanding $\exp(x^{2}+y^{2})$ with respect + to $x$ and then expanding every coefficient with respect to $y$. + + If the switch \nameref{taylorkeeporiginal} is set to \name{on} the + original expression is kept for later reference. + + Printing is controlled by the variable \nameref{taylorprintterms}. + + \end{Comments} + \begin{Related} + \item[tps] Truncated Power Series. + \item[Koepf] Complete power series + \end{Related} +\end{Operator} + +\subsection{Controlling the package} + +\begin{Switch}{taylorkeeporiginal} + The \name{taylorkeeporiginal} switch determines whether the + \nameref{taylor} operator keeps the expression to be expanded for + later use. Default is \name{on}. +\end{Switch} + +\begin{Operator}{taylororiginal} + \name{taylororiginal} extracts the original expression from a Taylor + kernel. + \begin{Syntax} + \name{taylororiginal}\(\arg{taylor\_kernel}\) + \end{Syntax} + If the argument is not a Taylor kernel, or if the expression was not + kept, an error is signaled. +\end{Operator} + +\begin{Variable}{taylorprintterms} + + Only a certain number of (non-zero) coefficients of a Taylor + kernel are printed usually. If there are more, \verb|...| is + printed as part of the expression to indicate this. The number of + terms printed is given by the value of the shared algebraic + variable \nameref{taylorprintterms}. Allowed values are integers + and the special identifier \name{all}. The latter setting + specifies that all terms are to be printed. The default setting is + $5$. + +\end{Variable} + Index: r36/help/sl.tex ================================================================== --- r36/help/sl.tex +++ r36/help/sl.tex @@ -1,2550 +1,2550 @@ -\begin{document} - - - -\section{Preliminaries} - -\subsection{Primitive Data Types} -\begin{Type}{integer} -Integer numbers: -Integers are also called "fixed" numbers. The magnitude of -an integer is unrestricted. Integers in the LISP input stream are -an arbitrary number of integer digits, eventually preceded by -a plus or minus sign. -\begin{Examples} -22\\ --31415926585\\ -\end{Examples} -\end{Type} - -\begin{Type}{floating} -Floating point numbers: The precision of floating point -numbers is determined solely by the implementation. In BNF floating -point numbers are recognized by the grammar: -\begin{verbatim} - ::= .|.| - . - ::= | - E| - E-| - E+ - ::= | - +|- -\end{verbatim} -\begin{Examples} -3.1415\\ -17.0\\ --22e100\\ -1.1e-5 -\end{Examples} -\end{Type} - -\begin{Type}{id} -An identifier is a string of characters which may have the -following items associated with it. - - - print name: The characters of the identifier. - - flags: An identifier may be tagged with a flag. Access is - by the \nameref{flag}, \nameref{remflag}and - \nameref{flagp} functions. - - properties: An identifier may have an indicator-value pair - associated with it. Access is by the - \nameref{put}, \nameref{get}, and \nameref{remprop} - functions. - - values: An identifier may have a value associated with - it. Access to values is by \nameref{set} \nameref{setq} - The method by which the value - is attached to the identifier is known as the binding - type, being one of - \nameref{Local Binding}, \nameref{Global Binding}, - or \nameref{Fluid Binding}. - - functions: - An identifier may have a function or macro associated with - it. Access is by the - \nameref{putd}, \nameref{getd}, and \nameref{remd} functions. - An identifier may not have both a function and a value - associated with it. - - - \name{oblist} entry: An identifier may be entered and removed from a - structure called the \nameref{oblist}. Its presence on the \name{oblist} - does not directly affect the other properties. Access to - the \name{oblist} is by the - \nameref{intern}, \nameref{remob}, and \nameref{read} - functions. - - The maximum length of a Standard LISP identifier is 24 - characters (excluding occurrences of the escape character !) - but an implementation may allow more. Special characters - (digits in the first position and punctuation) must be prefixed - with an escape character, an ! in Standard LISP. In BNF - identifiers are recognized by the grammar: -\begin{verbatim} - ::= ! - ::= - - A|B|C|D|E|F|G|H|I|J|K|L|M|N|O|P|Q|R|S|T|U|V|W|X|Y|Z| - a|b|c|d|e|f|g|h|i|j|k|l|m|n|o|p|q|r|s|t|u|v|w|x|y|z - ::= | - ::= | - ::= | - - ::= | - - Note: Using lower case letters in identifiers may cause - portability problems. Lower case letters are automatically - converted to upper case when the \nameref{!*RAISE} flag is T. -\end{verbatim} - -\begin{Examples} -a\\ -Hugo\\ -!1!-otto\\ -!*raise\\ -this!-is!-a!-long!-id\\ -!U!P!P!E!R!-and!-!l!o!w!e!r\\ -\end{Examples} -\end{Type} - - -\begin{Type}{string} -A set of characters enclosed in double quotes as -in "THIS IS A STRING". A quote is included by doubling it as in "HE -SAID, ""LISP""". The maximum size of strings is 80 characters but an -implementation may allow more. Strings are not part of the \nameref{oblist} and -are considered constants like \nameref{number}s, \nameref{vector}s, -and \nameref{function-pointer}s. -\end{Type} - -\begin{Type}{dotted-pair} -\index{car}\index{cdr} -A dotted pair is a primitive structure which has a left and right part. -A notation called {\em dot-notation} is used for dotted pairs and -takes the form: -\begin{verbatim} - ( . ) -\end{verbatim} - -The is known as the \nameref{car} portion and the - as the \nameref{cdr} portion. The left and right parts may be of any type. -Spaces are used to resolve ambiguity with floating point numbers. - -When or are dotted-pairs themselves, -the \nameref{list-notation} is often more convenient. -\end{Type} - -\begin{Type}{vector} -A vector is a primitive uniform structure in which -an integer index is used to access random values in the structure. The -individual elements of a vector may be of any type. Access to vectors -is restricted to functions \nameref{putv}, \nameref{getv}, and -\nameref{upbv}. -A notation for vectors, vector-notation, has the -elements of a vector surrounded by square brackets -\begin{verbatim} - ::= | - ::= [] -\end{verbatim} -\begin{Examples} -[1 2 3 5 7 11 13 17 19 23]\\ -[nil (a) (a . a)]\\ -[[1 2 3 4 5][2 4 6 8 10][3 6 9 12 15]]\\ -\end{Examples} -\end{Type} - -\begin{Type}{function-pointer} - - An implementation may have functions which deal - with specific data types other than those listed. The use - of these entities is to be avoided with the exception of a - restricted use of the \name{function-pointer}, an access method to - compiled EXPRs and FEXPRs (see \nameref{Function Types}). - - A particular - \name{function-pointer} must - remain valid throughout execution. Systems which change the - location of a function must use either an indirect reference or - change all occurrences of the associated value. There are two - classes of use of function-pointers, those which are supported - by Standard LISP but are not well defined, and those which are - well defined. -\end{Type} - -\subsection{Classes of Primitive Data Types} -\begin{Introduction}{Type Classes} -The classes of primitive types are a notational convenience for -describing the properties of functions. -\end{Introduction} - -\begin{Type}{boolean} -The set of global variables \{\nameref{T}, \nameref{NIL}\}, or their respective - values, \{T, NIL\}. -\end{Type} - -\begin{Type}{extra-boolean} -Any value in the system. Anything that is not \nameref{NIL} has - the boolean interpretation T. -\end{Type} - -\begin{Type}{ftype} - The class of definable function types. The set of ids \{EXPR, - FEXPR, MACRO\}. See \nameref{Function Types}. -\end{Type} - -\begin{Type}{number} -The set of \{\nameref{integer}, \nameref{floating}\}. -\end{Type} - - -\begin{Type}{constant} -The set of \{\nameref{integer}, \nameref{floating}, \nameref{string}, - \nameref{vector}, \nameref{function-pointer} \}. - Constants evaluate to themselves (see \nameref{eval}) -\end{Type} - -\begin{Type}{any} -The set of \{\nameref{integer}, \nameref{floating}, \nameref{string}, - \nameref{id}, \nameref{dotted-pair}, \nameref{vector}, - \nameref{function-pointer}\}. An S-expression is another term for any. - All Standard LISP entities have some value unless an \nameref{error} - occurs during evaluation or the function causes transfer of - control (such as \nameref{go} and \nameref{return}). -\end{Type} - -\begin{Type}{atom} -The set \nameref{any} - \{\nameref{dotted-pair}\}. Any item wich is not a \name{dotted-pair} -is considered as \name{atom}. -\end{Type} - - -\subsection{Structures} -\begin{Introduction}{Structures} -Structures are entities created out of the primitive types by the -use of dotted-pairs. Lists are structures very commonly required -as actual parameters to functions. Where a list of homogeneous -entities is required by a function this class will be denoted -by where xxx is the name of a class of primitives or -structures. Thus a list of ids is an id-list, a list of integers an -integer-list and so on. -\end{Introduction} - -\begin{Concept}{List-Notation} -A \name{list} is recursively defined as \nameref{nil} or the dotted-pair - (\nameref{any} . list). A special notation called list-notation is used - to represent lists. List-notation eliminates extra parentheses - and dots. The structure (a . (b . (c . nil))) in list notation - - is (a b c). List-notation and dot-notation may be mixed as in - (a b . c) or (a (b . c) d) which are (a . (b . c)) and (a . - ((b . c) . (d . nil))). In BNF lists are recognized by the - grammar: -\begin{verbatim} - ::= ( | - ::= ) | . ) -\end{verbatim} - Note: () is an alternate input representation of nil. -\end{Concept} - -\begin{Concept}{alist} -An association list; each element of the list is a - dotted-pair, the CAR part being a key associated with the value - in the CDR part. -\begin{Examples} -((a . 17)(b . (expt x 2))(q . nil))\\ -\end{Examples} -Here a is associated wity 17 while b is linked to the square of x -and q points to nil. -\end{Concept} - -\begin{Concept}{cond-form} - A cond-form is a list of 2 element lists of the form: - - (ANTECEDENT:any CONSEQUENT:any) - - The first element will henceforth be known as the antecedent - and the second as the consequent. The antecedent must have a - value. The consequent may have a value or an occurrence of - \nameref{go} or \nameref{return}. -\begin{Examples} -((greaterp x 0) 1)\\ -(t 0)\\ -\end{Examples} -\end{Concept} - -\begin{Concept}{lambda} -A LAMBDA expression which must have the form (in list - notation): - - (LAMBDA ). - - is a - list of formal parameters for an S-expression to be - evaluated. The semantics of the evaluation are defined with - the \nameref{eval}. -\begin{Examples} - (lambda(x y)(cons (car x)(cddr y))) -\end{Examples} -\end{Concept} - -\begin{Concept}{function} - - A LAMBDA expression or a function-pointer to a function. A - function is always evaluated as an EVAL, SPREAD form. -(see \nameref{Function Types}). -\end{Concept} - - - -\section{Notation} - -\begin{Introduction}{Function Descriptions} - -Each function is provided with a prototypical header line. Each formal -parameter is given a name and suffixed with its allowed type. Lower -case, italic tokens are names of classes and upper case, bold face, -tokens are parameter names referred to in the definition. The type of -the value returned by the function (if any) is suffixed to the -parameter list. -If it is not commonly used the parameter type -may be a specific set enclosed in brackets {...}. For example: - -\begin{verbatim} -PUTD(FNAME:id, TYPE:ftype, BODY:{lambda, function-pointer}):id -\end{verbatim} - -PUTD is a function with three parameters. The parameter FNAME is -an id to be the name of the function being defined. TYPE is the -type of the function being defined and BODY is a lambda expression -or a function-pointer. PUTD returns the name of the function being -defined. - -Functions which accept formal parameter lists of arbitrary length -have the type class and parameter enclosed in square brackets -indicating that zero or more occurrences of that argument are -permitted. For example: - -\begin{verbatim} -AND([U:any]):extra-boolean -\end{verbatim} - -AND is a function which accepts zero or more arguments which may be -of any type. -\end{Introduction} - -\begin{Introduction}{Function Types} -\index{eval type}\index{noeval type} -\index{spread type}\index{nospread type} -\index{expr type}\index{macro type} - -EVAL type functions are those which are invoked with evaluated -arguments. NOEVAL functions are invoked with unevaluated arguments. -SPREAD type functions have their arguments passed in one-to-one -correspondence with their formal parameters. NOSPREAD functions -receive their arguments as a single list. EVAL, SPREAD functions -are associated with EXPRs and NOEVAL, NOSPREAD functions with -FEXPRs. EVAL, NOSPREAD and NOEVAL, SPREAD functions can be -simulated using NOEVAL, NOSPREAD functions or MACROs. - -EVAL, SPREAD type functions may have a maximum of 15 parameters. -There is no limit on the number of parameters a NOEVAL, NOSPREAD -function or MACRO may have. - -In the context of the description of an EVAL, SPREAD function, then -we speak of the formal parameters we mean their actual values. -However, in a NOEVAL, NOSPREAD function it is the unevaluated actual -parameters. - -A third function type, the MACRO, implements functions which create -S-expressions based on actual parameters. When a macro invocation - -is encountered, the body of the macro, a lambda expression, is -invoked as a NOEVAL, NOSPREAD function with the macro's invocation -bound as a list to the macros single formal parameter. When the -macro has been evaluated the resulting S-expression is reevaluated. -The description of \nameref{eval} and \nameref{expand} provide precise -details. -\end{Introduction} - -\begin{Introduction}{Messages} -\index{error}\index{warning} -Many functions detect errors. The description of such functions -will include these error conditions and suggested formats for -display of the generated error messages. A call on the -\nameref{error} -function is implied but the error number is not specified by -Standard LISP. In some cases a warning message is sufficient. To -distinguish between errors and warnings, errors are prefixed with -five asterisks and warnings with only three. - -Primitive functions check arguments that must be of a certain -primitive type for being of that type and display an error message -if the argument is not correct. The type mismatch error always -takes the form: -\begin{verbatim} -***** PARAMETER not TYPE for FN -\end{verbatim} - -Here PARAMETER is the unacceptable actual parameter, TYPE is the -type that PARAMETER was supposed to be. FN is the name of the -function that detected the error. -\end{Introduction} - -\begin{Introduction}{Comments} - -The character \% signals the start of a comment, text to be ignored during -parsing. A comment is terminated by the end of the line it is on. The -function \nameref{readch}must be able to read a comment one character at a -time. Comments are transparent to the function READ. The percent sign -may occur as a character in identifiers by preceding it with the escape -character. - - (setq a 17) \% this is a comment - -\end{Introduction} - -%----------------------------------------------------------------- -\section{Elementary Predicates} -%----------------------------------------------------------------- - -\begin{Introduction}{Elementary Predicates} -Functions in this section return \nameref{T} when the condition defined is met -and \nameref{NIL} when it is not. Defined are type checking functions and -elementary comparisons. -\end{Introduction} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{atom} -\begin{verbatim} -ATOM(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is not a \nameref{dotted-pair}. -\begin{verbatim} - - EXPR PROCEDURE ATOM(U); - NULL PAIRP U; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{codep} -\begin{verbatim} -CODEP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a \nameref{function-pointer}. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{constantp} -\begin{verbatim} -CONSTANTP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a constant (a \nameref{number}, - \nameref{string}, \nameref{function-pointer}, or \nameref{vector}). -\begin{verbatim} - - EXPR PROCEDURE CONSTANTP(U); - NULL OR(PAIRP U, IDP U); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{eq} -\begin{verbatim} -EQ(U:any, V:any):boolean eval, spread -\end{verbatim} - Returns T if U points to the same object as V. EQ is not a - reliable comparison between numeric arguments. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{eqn} -\begin{verbatim} -EQN(U:any, V:any):boolean eval, spread -\end{verbatim} - Returns T if U and V are EQ or if U and V are - \nameref{number}s and have the same value and type. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{equal} -\begin{verbatim} -EQUAL(U:any, V:any):boolean eval, spread -\end{verbatim} - Returns T if U and V are the same. Dotted-pairs are - compared recursively to the bottom levels of their trees. - Vectors must have identical dimensions and EQUAL values in - all positions. Strings must have identical characters. - Function pointers must have \nameref{eq} values. Other atoms must be - \nameref{eqn} equal. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{fixp} -\begin{verbatim} -FIXP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is an \nameref{integer}. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{floatp} -\begin{verbatim} -FLOATP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a \nameref{floating} point number. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{idp} -\begin{verbatim} -IDP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is an \nameref{id}. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{minusp} -\begin{verbatim} -MINUSP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a number and less than 0. If U is not a - \nameref{number} or is a positive number, NIL is returned. -\begin{verbatim} - - EXPR PROCEDURE MINUSP(U); - IF NUMBERP U THEN LESSP(U, 0) ELSE NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{null} -\begin{verbatim} -NULL(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is NIL. -\begin{verbatim} - - EXPR PROCEDURE NULL(U); - U EQ NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{numberp} -\begin{verbatim} -NUMBERP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a \nameref{number}. -\begin{verbatim} - - EXPR PROCEDURE NUMBERP(U); - IF OR(FIXP U, FLOATP U) THEN T ELSE NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{onep} -\begin{verbatim} -ONEP(U:any):boolean eval, spread. -\end{verbatim} - Returns T if U is a \nameref{number} and has the value 1 or 1.0. - Returns NIL otherwise. -\begin{verbatim} - - - EXPR PROCEDURE ONEP(U); - IF EQN(U,1) OR EQN(U,1.0) THEN T ELSE NIL; -\end{verbatim} - The definition in the published report is incorrect as it - does not return T for U of 1.0. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{pairp} -\begin{verbatim} -PAIRP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a \nameref{dotted-pair}. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{stringp} -\begin{verbatim} -STRINGP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a string. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{vectorp} -\begin{verbatim} -VECTORP(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a vector. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{zerop} -\begin{verbatim} -ZEROP(U:any):boolean eval, spread. -\end{verbatim} - Returns T if U is a number and has the value 0 or 0.0. - Returns NIL otherwise. - - The definition in the published report is incorrect as it - does not return T for U of 0.0. -\end{Function} - -\section{Functions on Dotted-Pairs} -\begin{Introduction}{Function on Dotted-Pairs} -\index{dotted-pair} -The following are elementary functions on dotted-pairs. All functions -in this section which require dotted-pairs as parameters detect a type -mismatch error if the actual parameter is not a dotted-pair. -\end{Introduction} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{car} -\begin{verbatim} -CAR(U:dotted-pair):any eval, spread -\end{verbatim} - CAR(CONS(a, b)) -> a. The left part of U is returned. The - type mismatch error occurs if U is not a dotted-pair. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{cdr} -\begin{verbatim} -CDR(U:dotted-pair):any eval, spread -\end{verbatim} - CDR(CONS(a, b)) -> b. The right part of U is returned. The - type mismatch error occurs if U is not a dotted-pair. - -\end{Function} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{caar} -\index{CAAAAR}\index{CAAAR}\index{CAAADR}\index{CAADR} -\index{CADR}\index{CAADAR}\index{CADAR}\index{CDAR}\index{CAADDR} -\index{CADDR}\index{CDDR}\index{CADAAR}\index{CDAAR}\index{CADADR} -\index{CDADR}\index{CADDAR}\index{CDDAR}\index{CADDDR}\index{CDDDR} -\index{CDAAAR}\index{CDAADR}\index{CDADAR}\index{CDADDR}\index{CDDAAR} -\index{CDDADR}\index{CDDDAR}\index{CDDDDR} -The composites of CAR and CDR are supported up to 4 levels, namely: - -CAAAAR CAAAR CAAR CAAADR CAADR CADR - -CAADAR CADAR CDAR CAADDR CADDR CDDR - -CADAAR CDAAR CADADR CDADR CADDAR CDDAR - -CADDDR CDDDR CDAAAR CDAADR CDADAR CDADDR - -CDDAAR CDDADR CDDDAR CDDDDR - -Here e.g. (cdar x) is equivlaent to (cdr (car x)). - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{cons} -\begin{verbatim} -CONS(U:any, V:any):dotted-pair eval, spread -\end{verbatim} - Returns a dotted-pair which is not \nameref{eq} to anything and has U - as its \nameref{car} part and V as its nameref(cdr) part. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{list} -\begin{verbatim} -LIST([U:any]):list noeval, nospread, or macro -\end{verbatim} - A list of the evaluation of each element of U is returned. - The order of evaluation nead not be first to last as the - following definition implies. -\begin{verbatim} - - FEXPR PROCEDURE LIST(U); - EVLIS U; -\end{verbatim} - The published report's definition implies a specific - ordering. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{rplaca} -\begin{verbatim} -RPLACA(U:dotted-pair, V:any):dotted-pair eval, spread -\end{verbatim} - The \nameref{car} portion of the dotted-pair U is replaced by V. If - dotted-pair U is (a . b) then (V . b) is returned. The type - mismatch error occurs if U is not a dotted-pair. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{rplacd} -\begin{verbatim} -RPLACD(U:dotted-pair, V:any):dotted-pair eval, spread -\end{verbatim} - The \nameref{cdr} portion of the dotted-pair U is replaced by V. If - dotted-pair U is (a . b) then (a . V) is returned. The - type mismatch error occurs if U is not a dotted-pair. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Functions for Identifiers} - -\begin{Concept}{oblist} -The following functions deal with identifiers and the \nameref{oblist}, -the structure of which is not defined. -The \name{oblist} is an internal stucture where \nameref{id}s -are kept. The function of the \name{oblist} is -to provide a symbol table for identifiers created during input. -Identifiers created by \nameref{read} which have the same characters will -therefore refer to the same object (see the \nameref{eq} function). - -Identifiers created by \nameref{gensym} or \nameref{compress} are -not member of the \name{oblist} and therefore they are not -unique even if they are represented by the same character -sequence on output. The function \nameref{intern} is used -to create an equivalent unique \name{id} which then is -member of the \name{oblist}. -\end{Concept} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{compress} -\begin{verbatim} -COMPRESS(U:id-list):{atom-vector} eval, spread -\end{verbatim} - U is a list of single character identifiers which is built - into a Standard LISP entity and returned. Recognized are - \nameref{number}s, \nameref{string}s, - and identifiers (see \nameref{id}) with the \name{escape} character - prefixing special characters. Function pointers - may be compressed but this is an undefined use. If an entity - cannot be parsed out of U or characters are left over after - parsing an error occurs: -\begin{verbatim} - ***** Poorly formed atom in COMPRESS -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{explode} -\begin{verbatim} -EXPLODE(U:{atom}-{vector}):id-list eval, spread -\end{verbatim} - Returned is a list of interned characters representing the - characters to print of the value of U. The primitive data - types have these formats: - - \nameref{integer}: Leading zeroes are suppressed and a minus sign - prefixes the digits if the integer is negative. - - \nameref{floating}: The value appears in the format [-]0.nn...nnE[-]mm - if the magnitude of the number is too large or small to - display in [-]nnnn.nnnn format. The crossover point is - determined by the implementation. - - \nameref{id}: The characters of the print name of the identifier - are produced with special characters prefixed with the - escape character. - - \nameref{string}: The characters of the string are produced surrounded - by double quotes "...". - - \nameref{function-pointer}: The value of the function-pointer is created - as a list of characters conforming to the conventions of - the system site. - - The type mismatch error occurs if U is not a number, - identifier, string, or function-pointer. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{gensym} -\begin{verbatim} -GENSYM():identifier eval, spread -\end{verbatim} - Creates an identifier which is not interned on the \nameref{oblist} and - consequently not \nameref{eq} to anything else. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{intern} -\begin{verbatim} -INTERN(U:{id,string}):id eval, spread -\end{verbatim} - INTERN searches the \nameref{oblist} for an identifier with the same - print name as U and returns the identifier on the \name{oblist} if a - match is found. Any properties and global values associated - with U may be lost. If U does not match any entry, a - new one is created and returned. If U has more than the - maximum number of characters permitted by the implementation - (the minimum number is 24) an error occurs: -\begin{verbatim} - ***** Too many characters to INTERN -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{remob} -\begin{verbatim} -REMOB(U:id):id eval, spread -\end{verbatim} - If U is present on the \nameref{oblist} it is removed. This does not - affect U having properties, flags, functions and the like. U - is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Property List Functions} -\begin{Introduction}{Property List Functions} -With each id in the system is a \name{property list}, a set of entities -which are associated with the id for fast access. These entities are -called \nameindex{flags} if their use gives the id a single valued -property, and \nameindex{properties} if the id is to have a multivalued -attribute: an indicator with a property. - -Flags and indicators may clash, consequently care should be taken to -avoid this occurrence. Flagging X with an id which already is an -indicator for X may result in that indicator and associated property -being lost. Likewise, adding an indicator which is the same id as a -flag may result in the flag being destroyed. -\end{Introduction} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{flag} -\begin{verbatim} -FLAG(U:id-list, V:id):NIL eval, spread -\end{verbatim} - U is a list of ids which are flagged with V. The effect of - \name{flag} is that \nameref{flagp} will have the value T for those ids of U - which were flagged. Both V and all the elements of U must be - identifiers or the type mismatch error occurs. -\begin{Examples} -flag('(u v),'symmetric)\\ -\end{Examples} -Note: If you want to flag a single \name{id} you must put it into -a list before calling the function \name{flag}. A flag is removed -by \nameref{remflag} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{flagp} -\begin{verbatim} -FLAGP(U:any, V:any):boolean eval, spread -\end{verbatim} - Returns T if U has been previously flagged (see \nameref{flag}} - with V, else NIL. Returns NIL if either U or V is not an \nameref{id}. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{get} -\begin{verbatim} -GET(U:any, IND:any):any eval, spread -\end{verbatim} - Returns the property associated with indicator IND from the - property list of U. If U does not have indicator IND, NIL is - returned. GET cannot be used to access functions (use GETD - instead). For setting a property use the function \nameref{put}. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{put} -\begin{verbatim} -PUT(U:id, IND:id, PROP:any):any eval, spread -\end{verbatim} - The indicator IND with the property PROP is placed on the - property list of the id U. If the action of PUT occurs, the - value of PROP is returned. If either of U and IND are not - ids the type mismatch error will occur and no property will - be placed. PUT cannot be used to define functions - (use \nameref{putd} instead). The values stored on the property - list can be retrieved using \nameref{get}. \nameref{remprop} - removes a property. -\begin{Examples} -put('otto,'hugo,'(a))\\ -get('otto,'hugo) & (a)\\ -put('otto,'hugo,'(b))\\ -get('otto,'hugo) & (b)\\ -remprop('otto,'hugo)\\ -get('otto,'hugo) & nil\\ -\end{Examples} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{remflag} -\begin{verbatim} -REMFLAG(U:any-list, V:id):NIL eval, spread -\end{verbatim} - Removes the flag V from the property list of each member of - the list U. Both V and all the elements of U must be ids or - the type mismatch error will occur (see \nameref{flag}). - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{remprop} -\begin{verbatim} -REMPROP(U:any, IND:any):any eval, spread -\end{verbatim} - Removes the property with indicator IND from the property - list of U. Returns the removed property or NIL if there was - no such indicator (see \nameref{put}}. -\end{Function} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Function Definition} -\begin{Introduction}{Function Definition} -Functions in Standard LISP are global entities. To avoid -function-variable naming clashes no variable may have the same name as -a function. -\end{Introduction} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{de} -\index{expr} -\begin{verbatim} -DE(FNAME:id, PARAMS:id-list, FN:any):id noeval, nospread -\end{verbatim} - The function FN with the formal parameter list PARAMS is - added to the set of defined functions with the name FNAME. - Any previous definitions of the function are lost. The - function created is of type EXPR (see \nameref{Function Types}). If \nameref{*COMP} is - non-NIL, the EXPR is first compiled. The name of the defined - function is returned. -\begin{verbatim} - - FEXPR PROCEDURE DE(U); - PUTD(CAR U, 'EXPR, LIST('LAMBDA, CADR U, CADDR U)); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{df} -\index{fexpr} -\begin{verbatim} -DF(FNAME:id, PARAM:id-list, FN:any):id noeval, nospread -\end{verbatim} - The function FN with formal parameter PARAM is added to the - set of defined functions with the name FNAME. Any previous - definitions of the function are lost. The function created - is of type FEXPR (see \nameref{Function Types}). If \nameref{*COMP} is T the FEXPR - is first compiled. The name of the defined function is - returned. -\begin{verbatim} - - FEXPR PROCEDURE DF(U); - PUTD(CAR U, 'FEXPR, LIST('LAMBDA, CADR U, CADDR U)); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{dm} -\index{macro} -\begin{verbatim} -DM(MNAME:id, PARAM:id-list, FN:any):id noeval, nospread -\end{verbatim} - The macro FN with the formal parameter PARAM is added to the - set of defined functions with the name MNAME. Any previous - definitions of the function are overwritten. The function - created is of type MACRO (see \nameref{Function Types}). - The name of the macro is returned. -\begin{verbatim} - - FEXPR PROCEDURE DM(U); - PUTD(CAR U, 'MACRO, LIST('LAMBDA, CADR U, CADDR U)); -\end{verbatim} - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{getd} -\begin{verbatim} -GETD(FNAME:any):{NIL, dotted-pair} eval, spread -\end{verbatim} - If FNAME is not the name of a defined function, NIL - is returned. If FNAME is a defined function then the - dotted-pair -\begin{verbatim} - (TYPE:ftype . DEF:{function-pointer, lambda}) -\end{verbatim} - is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{putd} -\begin{verbatim} -PUTD(FNAME:id, TYPE:ftype, BODY:function):id eval, spread -\end{verbatim} - Creates a function with name FNAME and definition BODY of - type TYPE. If PUTD succeeds the name of the defined function - is returned. The effect of PUTD is that GETD will return a - dotted-pair with the functions type and definition. Likewise - the \nameref{globalp} predicate will return T when queried with the - function name. - If the function FNAME has already been declared as a GLOBAL - or FLUID variable the error: -\begin{verbatim} - ***** FNAME is a non-local variable -\end{verbatim} - occurs and the function will not be defined. If function - FNAME already exists a warning message will appear: -\begin{verbatim} - *** FNAME redefined -\end{verbatim} - The function defined by PUTD will be compiled before - definition if \nameref{*COMP} variable is non-NIL. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{remd} -\begin{verbatim} -REMD(FNAME:id):{NIL, dotted-pair} eval, spread -\end{verbatim} - Removes the function named FNAME from the set of defined - functions. Returns the (ftype . function) dotted-pair or - NIL as does \nameref)getd}. The global/function attribute of FNAME is - removed and the name may be used subsequently as a variable. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Variables and Bindings} - -\begin{Introduction}{Scope} -\index{variables} -A variable is a place holder for a Standard LISP entity which is said -to be bound to the variable. The scope of a variable is the range over -which the variable has a defined value. There are three different -binding mechanisms in Standard LISP: -\nameref{Local Binding}, \nameref{Global Binding}, and -\nameref{Fluid Binding}. -\end{Introduction} - -\begin{Concept}{Local Binding} -\index{variables} -This type of binding occurs -only in compiled functions. Local variables occur as formal parameters -in \nameref{lambda} expressions (function arguments) - and as \nameref{prog} form variables. The binding occurs -when a lambda expression is evaluated or when a \name{prog} form is executed. -The scope of a local variable is the body of the function in which it -is defined. -\end{Concept} - -\begin{Concept}{Global Binding} -\index{variables} -Only one binding of a -global variable exists at any time allowing direct access to the value -bound to the variable. The scope of a global variable is universal. -Variables declared \nameref{global} may not appear as parameters -in \nameref{lambda} expressions (function arguments) - or as \nameref{prog} form variables. A variable must be declared -\name{global} prior to its use as a global variable since the default type -for undeclared variables is \nameref{fluid}. -\end{Concept} - - - -\begin{Concept}{Fluid Binding} -\index{variables} -Fluid variables are global -in scope but may occur as \name{fluid} formal parameters or -\nameref{prog} form variables. In interpreted functions all formal parameters -and \name{prog} form variables are considered to have fluid binding until -changed to local binding by compilation. When \name{fluid} variables are -used as parameters (\nameref{lambda} expressions} -they are rebound in such a way that the previous -binding may be restored. All references to \name{fluid} variables are to the -currently active binding. -\end{Concept} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{fluid} -\index{variables} -\begin{verbatim} -FLUID(IDLIST:id-list):NIL eval, spread -\end{verbatim} - The ids in IDLIST are declared as FLUID type variables (ids - not previously declared are initialized to NIL). Variables - in IDLIST already declared FLUID are ignored. Changing a - variable's type from GLOBAL to FLUID is not permissible and - results in the error: -\begin{verbatim} - ***** ID cannot be changed to FLUID -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{fluidp} -\index{variables} -\begin{verbatim} -FLUIDP(U:any):boolean eval, spread -\end{verbatim} - If U has been declared by \nameref{fluid} T is - returned, otherwise NIL is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{global} -\index{variables} -\begin{verbatim} -GLOBAL(IDLIST:id-list):NIL eval, spread -\end{verbatim} - The ids of IDLIST are declared global type variables. If - an id has not been declared previously it is initialized to - NIL. Variables already declared GLOBAL are ignored. Changing - a variables type from FLUID to GLOBAL is not permissible and - results in the error: -\begin{verbatim} - ***** ID cannot be changed to GLOBAL -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{globalp} -\index{variables} -\begin{verbatim} -GLOBALP(U:any):boolean eval, spread -\end{verbatim} - If U has been declared GLOBAL or is the name of a defined - function, T is returned, else NIL is returned. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{set} -\index{variables} -\begin{verbatim} -SET(EXP:id, VALUE:any):any eval, spread -\end{verbatim} - EXP must be an identifier or a type mismatch error occurs. - The effect of SET is replacement of the item bound to - the identifier by VALUE. If the identifier is not a local - variable or has not been declared GLOBAL it is automatically - declared FLUID with the resulting warning message: -\begin{verbatim} - *** EXP declared FLUID -\end{verbatim} - EXP must not evaluate to T or NIL or an error occurs: -\begin{verbatim} - ***** Cannot change T or NIL -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{setq} -\index{variables} -\begin{verbatim} -SETQ(VARIABLE:id, VALUE:any):any noeval, nospread -\end{verbatim} - If VARIABLE is not local or GLOBAL it is by default declared - FLUID and the warning message: -\begin{verbatim} - *** VARIABLE declared FLUID -\end{verbatim} - appears. The value of the current binding of VARIABLE is - replaced by the value of VALUE. VARIABLE must not be T or NIL - or an error occurs: -\begin{verbatim} - ***** Cannot change T or NIL -\end{verbatim} - -\begin{verbatim} - MACRO PROCEDURE SETQ(X); - LIST('SET, LIST('QUOTE, CADR X), CADDR X); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{unfluid} -\index{variables} -\begin{verbatim} -UNFLUID(IDLIST:id-list):NIL eval, spread -\end{verbatim} - The variables in IDLIST that have been declared as \nameref{fluid} - variables are no longer considered as fluid variables. - Others are ignored. This affects only compiled functions - as free variables in interpreted functions are automatically - considered fluid. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Program Feature Functions} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{go} -\index{program control} -\index{label} -\begin{verbatim} -GO(LABEL:id) noeval, nospread -\end{verbatim} - GO alters the normal flow of control within a \nameref{prog} function. - The next statement of a PROG function to be evaluated is - immediately preceded by LABEL. A GO may only appear in the - following situations: - - 1. At the top level of a \nameref{prog} referencing a label which - also appears at the top level of the same prog. - - 2. As the consequent of a \nameref{cond} item of a \name{cond} appearing on - the top level of a \nameref{prog}. - - 3. As the consequent of a \nameref{cond} item which appears as the - consequent of a \name{cond} item to any level. - - 4. As the last statement of a \nameref{progn} which appears at - the top level of a \nameref{prog} or in a \name{progn} appearing in - the consequent of a \nameref(cond} to any level subject to the - restrictions of 2 and 3. - - 5. As the last statement of a \nameref{progn} - within a \name{progn} or as - the consequent of a \nameref{prog}in a \name{progn}to any level subject - to the restrictions of 2, 3 and 4. - - If LABEL does not appear at the top level of the \name{prog} in - which the \name{go} appears, an error occurs: -\begin{verbatim} - ***** LABEL is not a known label -\end{verbatim} - - If the \name{go} has been placed in a position not defined by rules - 1-5, another error is detected: -\begin{verbatim} - ***** Illegal use of GO to LABEL -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{prog} -\index{program control} -\begin{verbatim} -PROG(VARS:id-list, [PROGRAM:{id, any}]):any noeval, nospread -\end{verbatim} - VARS is a list of ids which are considered fluid when the - PROG is interpreted and local when compiled (see ``Variables - and Bindings'', section 3.6 on page 22). The PROGs variables - are allocated space when the PROG form is invoked and are - deallocated when the PROG is exited. PROG variables are - initialized to NIL. The PROGRAM is a set of expressions to be - evaluated in order of their appearance in the PROG function. - Identifiers appearing in the top level of the PROGRAM are - labels which can be referenced by GO. The value returned by - the PROG function is determined by a \nameref{return} function or NIL - if the PROG falls through. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{progn} -\index{program control} -\begin{verbatim} -PROGN([U:any]):any noeval, nospread -\end{verbatim} - U is a set of expressions which are executed sequentially. - The value returned is the value of the last expression. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{prog2} -\index{program control} -\begin{verbatim} -PROG2(A:any, B:any)any eval, spread -\end{verbatim} - Returns the value of B. -\begin{verbatim} - - EXPR PROCEDURE PROG2(A, B); - B; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{return} -\index{program control} -\begin{verbatim} -RETURN(U:any) eval, spread -\end{verbatim} - Within a \nameref{prog}, RETURN terminates the evaluation of a PROG - and returns U as the value of the PROG. The restrictions on - the placement of RETURN are exactly those of nameref{go}. Improper - placement of RETURN results in the error: -\begin{verbatim} - ***** Illegal use of RETURN -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Error Handling} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{error} -\index{error handling} -\begin{verbatim} -ERROR(NUMBER:integer, MESSAGE:any) eval, spread -\end{verbatim} - NUMBER and MESSAGE are passed back to a surrounding \nameref{errorset} - (the Standard LISP reader has an ERRORSET). MESSAGE is placed - in the global variable \nameref{emsg*} and the error number becomes - the value of the surrounding ERRORSET. \nameref{fluid} variables and - local bindings are unbound to return to the environment - of the ERRORSET. Global variables are not affected by the - process. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{errorset} -\index{error handling} -\begin{verbatim} -ERRORSET(U:any, MSGP:boolean, TR:boolean):any eval, spread -\end{verbatim} - If an error occurs during the evaluation of U, the value - of NUMBER from the \nameref{error} call is returned as the value of - ERRORSET. In addition, if the value of MSGP is non-NIL, - the MESSAGE from the ERROR call is displayed upon both the - standard output device and the currently selected output - device unless the standard output device is not open. The - message appears prefixed with 5 asterisks. The MESSAGE list - is displayed without top level parentheses. The MESSAGE - from the ERROR call will be available in the global variable - \nameref{emsg*}. The exact format of error messages generated by - Standard LISP functions described in this document are not - fixed and should not be relied upon to be in any particular - form. Likewise, error numbers generated by Standard LISP - functions are implementation dependent. - If no error occurs during the evaluation of U, the value of - (LIST (EVAL U)) is returned. - - If an error has been signaled and the value of TR is non-NIL - a traceback sequence will be initiated on the selected output - device. The traceback will display information such as - unbindings of \nameref{fluid} variables, argument lists and so on in an - implementation dependent format. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Functions for Vectors} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{getv} -\index{vector} -\begin{verbatim} -GETV(V:vector, INDEX:integer):any eval, spread -\end{verbatim} - Returns the value stored at position INDEX of the \nameref{vector} V. - The type mismatch error may occur. An error occurs if the - INDEX does not lie within 0... UPBV(V) inclusive: -\begin{verbatim} - ***** INDEX subscript is out of range -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{mkvect} -\index{vector} -\begin{verbatim} -MKVECT(UPLIM:integer):vector eval, spread -\end{verbatim} - Defines and allocates space for a \nameref{vector} with UPLIM+1 - elements accessed as 0... UPLIM. Each element is initialized - to NIL. An error will occur if UPLIM is < 0 or there is not - enough space for a vector of this size: -\begin{verbatim} - ***** A vector of size UPLIM cannot be allocated -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{putv} -\index{vector} -\begin{verbatim} -PUTV(V:vector, INDEX:integer, VALUE:any):any eval, spread -\end{verbatim} - Stores VALUE into the \nameref{vector} V at position INDEX. VALUE is - returned. The type mismatch error may occur. If INDEX does - not lie in 0... UPBV(V) an error occurs: -\begin{verbatim} - ***** INDEX subscript is out of range -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{upbv} -\index{vector} -\begin{verbatim} -UPBV(U:any):NIL,integer eval, spread -\end{verbatim} - Returns the upper limit of U if U is a \nameref{vector}, or NIL if it - is not. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Boolean Functions, Conditionals} - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{and} -\index{boolean} -\begin{verbatim} -AND([U:any]):extra-boolean noeval, nospread -\end{verbatim} - AND evaluates each U until a value of NIL is found or the end - of the list is encountered. If a non-NIL value is the last - value it is returned, or NIL is returned. -\begin{verbatim} - - FEXPR PROCEDURE AND(U); - BEGIN - IF NULL U THEN RETURN NIL; - LOOP: IF NULL CDR U THEN RETURN EVAL CAR U - ELSE IF NULL EVAL CAR U THEN RETURN NIL; - U := CDR U; - GO LOOP - END; -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{cond} -\index{boolean} -\begin{verbatim} -COND([U:cond-form]):any noeval, nospread -\end{verbatim} - The antecedents of all U's (\nameref{cond-form}s) are evaluated in order of their - appearance until a non-NIL value is encountered. The - consequent of the selected U is evaluated and becomes the - value of the COND. The consequent may also contain the - special functions \nameref{go} and \nameref{return} subject to the restraints - given for these functions. In these cases COND does not have - a defined value, but rather an effect. If no antecedent is - non-NIL the value of COND is NIL. An error is detected if a U - is improperly formed: -\begin{verbatim} - ***** Improper cond-form as argument of COND -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{not} -\index{boolean} -\begin{verbatim} -NOT(U:any):boolean eval, spread -\end{verbatim} - If U is NIL, return T else return NIL (same as function - NULL). -\begin{verbatim} - - EXPR PROCEDURE NOT(U); - U EQ NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{or} -\index{boolean} -\begin{verbatim} -OR([U:any]):extra-boolean noeval, nospread -\end{verbatim} - U is any number of expressions which are evaluated in order - of their appearance. When one is found to be non-NIL it is - returned as the value of OR. If all are NIL, NIL is returned. -\begin{verbatim} - - FEXPR PROCEDURE OR(U); - BEGIN SCALAR X; - LOOP: IF NULL U THEN RETURN NIL - ELSE IF (X := EVAL CAR U) THEN RETURN X; - U := CDR U; - GO LOOP - END; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Arithmetic Functions} -\begin{Introduction}{Conversion} -\index{mixed-mode arithmetic} -Conversions between numeric types are provided explicitly by the -\nameref{fix} and \nameref{float} functions and implicitly by any -multi-parameter arithmetic function which receives mixed types of arguments. A -conversion from fixed to floating point numbers may result in a loss -of precision without a warning message being generated. Since -integers may have a greater magnitude that that permitted for floating -numbers, an error may be signaled when the attempted conversion cannot -be done. - - Because the magnitude of integers is unlimited the conversion -of a floating point number to a fixed number is always possible, the -only loss of precision being the digits to the right of the decimal -point which are truncated. If a function receives mixed types of -arguments the general rule will have the fixed numbers converted to -floating before arithmetic operations are performed. In all cases an -error occurs if the parameter to an arithmetic function is not a -number: -\begin{verbatim} -\errormessage{***** XXX parameter to FUNCTION is not a number} -\end{verbatim} -XXX is the value of the parameter at fault and FUNCTION is the name of -the function that detected the error. Exceptions to the rule are noted -where they occur. -\end{Introduction} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{abs} -\index{arithmetic} -\begin{verbatim} -ABS(U:number):number eval, spread -\end{verbatim} - Returns the absolute value of its argument. -\begin{verbatim} - - EXPR PROCEDURE ABS(U); - IF LESSP(U, 0) THEN MINUS(U) ELSE U; -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{add1} -\index{arithmetic} -\begin{verbatim} -ADD1(U:number):number eval, spread -\end{verbatim} - Returns the value of U plus 1 of the same type as U (fixed or - floating). -\begin{verbatim} - - EXPR PROCEDURE ADD1(U); - PLUS2(U, 1); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{difference} -\index{arithmetic} -\begin{verbatim} -DIFFERENCE(U:number, V:number):number eval, spread -\end{verbatim} - The value U - V is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{divide} -\index{arithmetic} -\begin{verbatim} -DIVIDE(U:number, V:number):dotted-pair eval, spread -\end{verbatim} - The dotted-pair (quotient . remainder) is returned. The - quotient part is computed the same as by QUOTIENT and the - remainder the same as by REMAINDER. An error occurs if - division by zero is attempted: -\begin{verbatim} - ***** Attempt to divide by 0 in DIVIDE -\end{verbatim} -\begin{verbatim} - - EXPR PROCEDURE DIVIDE(U, V); - (QUOTIENT(U, V) . REMAINDER(U, V)); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{expt} -\index{arithmetic} -\begin{verbatim} -EXPT(U:number, V:integer):number eval, spread -\end{verbatim} - Returns U raised to the V power. A floating point U to an - integer power V does not have V changed to a floating number - before exponentiation. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{fix} -\index{arithmetic} -\begin{verbatim} -FIX(U:number):integer eval, spread -\end{verbatim} - Returns an integer which corresponds to the truncated value - of U. The result of conversion must retain all significant - portions of U. If U is an integer it is returned unchanged. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{float} -\index{arithmetic} -\begin{verbatim} -FLOAT(U:number):floating eval, spread -\end{verbatim} - The floating point number corresponding to the value of the - argument U is returned. Some of the least significant - digits of an integer may be lost do to the implementation of - floating point numbers. FLOAT of a floating point number - returns the number unchanged. If U is too large to represent - in floating point an error occurs: -\begin{verbatim} - ***** Argument to FLOAT is too large -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{greaterp} -\index{arithmetic}\index{boolean} -\begin{verbatim} -GREATERP(U:number, V:number):boolean eval, spread -\end{verbatim} - Returns T if U is strictly greater than V, otherwise returns - NIL. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{lessp} -\index{arithmetic}\index{boolean} -\begin{verbatim} -LESSP(U:number, V:number):boolean eval, spread -\end{verbatim} - Returns T if U is strictly less than V, otherwise returns - NIL. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{max} -\index{arithmetic} -\begin{verbatim} -MAX([U:number]):number noeval, nospread, or macro -\end{verbatim} - Returns the largest of the values in U. If two or more values - are the same the first is returned. -\begin{verbatim} - MACRO PROCEDURE MAX(U); - EXPAND(CDR U, 'MAX2); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{max2} -\index{arithmetic} -\begin{verbatim} -MAX2(U:number, V:number):number eval, spread -\end{verbatim} - Returns the larger of U and V. If U and V are the same value - U is returned (U and V might be of different types). -\begin{verbatim} - - EXPR PROCEDURE MAX2(U, V); - IF LESSP(U, V) THEN V ELSE U; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{min} -\index{arithmetic} -\begin{verbatim} -MIN([U:number]):number noeval, nospread, or macro -\end{verbatim} - Returns the smallest of the values in U. If two or more - values are the same the first of these is returned. -\begin{verbatim} - MACRO PROCEDURE MIN(U); - EXPAND(CDR U, 'MIN2); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{min2} -\index{arithmetic} -\begin{verbatim} -MIN2(U:number, V:number):number eval, spread -\end{verbatim} - Returns the smaller of its arguments. If U and V are the - same value, U is returned (U and V might be of different - types). -\begin{verbatim} - - EXPR PROCEDURE MIN2(U, V); - IF GREATERP(U, V) THEN V ELSE U; -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{minus} -\index{arithmetic} -\begin{verbatim} -MINUS(U:number):number eval, spread -\end{verbatim} - Returns -U. -\begin{verbatim} - - EXPR PROCEDURE MINUS(U); - DIFFERENCE(0, U); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{plus} -\index{arithmetic} -\begin{verbatim} -PLUS([U:number]):number noeval, nospread, or macro -\end{verbatim} - Forms the sum of all its arguments. -\begin{verbatim} - MACRO PROCEDURE PLUS(U); - EXPAND(CDR U, 'PLUS2); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{plus2} -\index{arithmetic} -\begin{verbatim} -PLUS2(U:number, V:number):number eval, spread -\end{verbatim} - Returns the sum of U and V. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{quotient} -\index{arithmetic} -\begin{verbatim} -QUOTIENT(U:number, V:number):number eval, spread -\end{verbatim} - The quotient of U divided by V is returned. Division of - two positive or two negative integers is conventional. When - both U and V are integers and exactly one of them is negative - the value returned is the negative truncation of the absolute - value of U divided by the absolute value of V. An error - occurs if division by zero is attempted: -\begin{verbatim} - ***** Attempt to divide by 0 in QUOTIENT -\end{verbatim} - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{remainder} -\index{arithmetic} -\begin{verbatim} -REMAINDER(U:number, V:number):number eval, spread -\end{verbatim} - If both U and V are integers the result is the integer - remainder of U divided by V. If either parameter is floating - point, the result is the difference between U and V*(U/V) - all in floating point. If either number is negative the - remainder is negative. If both are positive or both are - negative the remainder is positive. An error occurs if V is - zero: -\begin{verbatim} - ***** Attempt to divide by 0 in REMAINDER -\end{verbatim} -\begin{verbatim} - - EXPR PROCEDURE REMAINDER(U, V); - DIFFERENCE(U, TIMES2(QUOTIENT(U, V), V)); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{sub1} -\index{arithmetic} -\begin{verbatim} -SUB1(U:number):number eval, spread -\end{verbatim} - Returns the value of U less 1. If U is a FLOAT type number, - the value returned is U less 1.0. -\begin{verbatim} - - EXPR PROCEDURE SUB1(U); - DIFFERENCE(U, 1); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{times} -\index{arithmetic} -\begin{verbatim} -TIMES([U:number]):number noeval, nospread, or macro -\end{verbatim} - Returns the product of all its arguments. -\begin{verbatim} - MACRO PROCEDURE TIMES(U); - EXPAND(CDR U, 'TIMES2); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{times2} -\index{arithmetic} -\begin{verbatim} -TIMES2(U:number, V:number):number eval, spread -\end{verbatim} - Returns the product of U and V. -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{MAP Composite Functions} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{map} -\begin{verbatim} -MAP(X:list, FN:function):any eval, spread -\end{verbatim} - Applies FN to successive CDR segments of X. NIL is returned. -\begin{verbatim} - - EXPR PROCEDURE MAP(X, FN); - WHILE X DO << FN X; X := CDR X >>; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{mapc} -\begin{verbatim} -MAPC(X:list, FN:function):any eval, spread -\end{verbatim} - FN is applied to successive CAR segments of list X. NIL is - returned. -\begin{verbatim} - EXPR PROCEDURE MAPC(X, FN); - WHILE X DO << FN CAR X; X := CDR X >>; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{mapcan} -\begin{verbatim} -MAPCAN(X:list, FN:function):any eval, spread -\end{verbatim} - A concatenated list of FN applied to successive CAR elements - of X is returned. -\begin{verbatim} - EXPR PROCEDURE MAPCAN(X, FN); - IF NULL X THEN NIL - ELSE NCONC(FN CAR X, MAPCAN(CDR X, FN)); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{mapcar} -\begin{verbatim} -MAPCAR(X:list, FN:function):any eval, spread -\end{verbatim} - Returned is a constructed list of FN applied to each CAR of - list X. -\begin{verbatim} - EXPR PROCEDURE MAPCAR(X, FN); - IF NULL X THEN NIL - ELSE FN CAR X . MAPCAR(CDR X, FN); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{mapcon} -\begin{verbatim} -MAPCON(X:list, FN:function):any eval, spread -\end{verbatim} - Returned is a concatenated list of FN applied to successive - CDR segments of X. -\begin{verbatim} - EXPR PROCEDURE MAPCON(X, FN); - IF NULL X THEN NIL - ELSE NCONC(FN X, MAPCON(CDR X, FN)); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{maplist} -\begin{verbatim} -MAPLIST(X:list, FN:function):any eval, spread -\end{verbatim} - Returns a constructed list of FN applied to successive CDR - segments of X. -\begin{verbatim} - EXPR PROCEDURE MAPLIST(X, FN); - IFNULL X THEN NIL - ELSE FN X . MAPLIST(CDR X, FN); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Composite Functions} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{apend} -\begin{verbatim} -APPEND(U:list, V:list):list eval, spread -\end{verbatim} - Returns a constructed list in which the last element of U is - followed by the first element of V. The list U is copied, V - is not. -\begin{verbatim} - EXPR PROCEDURE APPEND(U, V); - IF NULL U THEN V - ELSE CAR U . APPEND(CDR U, V); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{assoc} -\begin{verbatim} -ASSOC(U:any, V:alist):{dotted-pair, NIL} eval, spread -\end{verbatim} - If U occurs as the CAR portion of an element of the \nameref{alist} V, - the dotted-pair in which U occurred is returned, else NIL is - returned. ASSOC might not detect a poorly formed alist so an - invalid construction may be detected by CAR or CDR. -\begin{verbatim} - EXPR PROCEDURE ASSOC(U, V); - IF NULL V THEN NIL - ELSE IF ATOM CAR V THEN - ERROR(000, LIST(V, "is a poorly formed alist")) - ELSE IF U = CAAR V THEN CAR V - ELSE ASSOC(U, CDR V); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{deflist} -\begin{verbatim} -DEFLIST(U:dlist, IND:id):list eval, spread -\end{verbatim} - A "dlist" is a list in which each element is a two element - list: (ID:id PROP:any). Each ID in U has the indicator - IND with property PROP placed on its property list by the - PUT function. The value of DEFLIST is a list of the first - elements of each two element list. Like \nameref{put}, DEFLIST may not - be used to define functions. -\begin{verbatim} - EXPR PROCEDURE DEFLIST(U, IND); - IF NULL U THEN NIL - ELSE << PUT(CAAR U, IND, CADAR U); - CAAR U >> . DEFLIST(CDR U, IND); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{delete} -\begin{verbatim} -DELETE(U:any, V:list):list eval, spread -\end{verbatim} - Returns V with the first top level occurrence of U removed - from it. -\begin{verbatim} - EXPR PROCEDURE DELETE(U, V); - IF NULL V THEN NIL - ELSE IF CAR V = U THEN CDR V - ELSE CAR V . DELETE(U, CDR V); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{digit} -\begin{verbatim} -DIGIT(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a digit, otherwise NIL. -\begin{verbatim} - EXPR PROCEDURE DIGIT(U); - IF MEMQ(U, '(!0 !1 !2 !3 !4 !5 !6 !7 !8 !9)) - THEN T ELSE NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{length} -\begin{verbatim} -LENGTH(X:any):integer eval, spread -\end{verbatim} - The top level length of the list X is returned. -\begin{verbatim} - EXPR PROCEDURE LENGTH(X); - IF ATOM X THEN 0 - ELSE PLUS(1, LENGTH CDR X); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{liter} -\begin{verbatim} -LITER(U:any):boolean eval, spread -\end{verbatim} - Returns T if U is a character of the alphabet, NIL - otherwise. -\begin{verbatim} - EXPR PROCEDURE LITER(U); - IF MEMQ(U, '(!A !B !C !D !E !F !G !H !I !J !K !L !M - !N !O !P !Q !R !S !T !U !V !W !X !Y !Z - !a !b !c !d !e !f !g !h !i !j !k !l !m - !n !o !p !q !r !s !t !u !v !w !x !y !z)) -\end{verbatim} - The published report omits escape characters. These are - required for both upper and lower case as some systems - default to lower. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{member} -\begin{verbatim} -MEMBER(A:any, B:list):extra-boolean eval, spread -\end{verbatim} - Returns NIL if A is not a member of list B, returns the - remainder of B whose first element is A. -\begin{verbatim} - EXPR PROCEDURE MEMBER(A, B); - IF NULL B THEN NIL - ELSE IF A = CAR B THEN B - ELSE MEMBER(A, CDR B); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{memq} -\begin{verbatim} -MEMQ(A:any, B:list):extra-boolean eval, spread -\end{verbatim} - Same as \nameref{member} but an \nameref{eq} check is used for comparison. -\begin{verbatim} - EXPR PROCEDURE MEMQ(A, B); - IF NULL B THEN NIL - ELSE IF A EQ CAR B THEN B - ELSE MEMQ(A, CDR B); -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{nconc} -\begin{verbatim} -NCONC(U:list, V:list):list eval, spread -\end{verbatim} - Concatenates V to U without copying U. The last CDR of U is - modified to point to V. -\begin{verbatim} - EXPR PROCEDURE NCONC(U, V); - BEGIN SCALAR W; - IF NULL U THEN RETURN V; - W := U; - WHILE CDR W DO W := CDR W; - RPLACD(W, V); - RETURN U - END; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{pair} -\begin{verbatim} -PAIR(U:list, V:list):alist eval, spread -\end{verbatim} - U and V are lists which must have an identical number of - elements. If not, an error occurs (the 000 used in the \nameref{error} - call is arbitrary and need not be adhered to). Returned is a - list where each element is a dotted-pair, the CAR of the pair - being from U, and the CDR the corresponding element from V. -\begin{verbatim} - EXPR PROCEDURE PAIR(U, V); - IF AND(U, V) THEN (CAR U . CAR V) . PAIR(CDR U, CDR V) - ELSE IF OR(U, V) THEN ERROR(000, - "Different length lists in PAIR") - ELSE NIL; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{reverse} -\begin{verbatim} -REVERSE(U:list):list eval, spread -\end{verbatim} - Returns a copy of the top level of U in reverse order. -\begin{verbatim} - EXPR PROCEDURE REVERSE(U); - BEGIN SCALAR W; - WHILE U DO << W := CAR U . W; - U := CDR U >>; - RETURN W - END; -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{sassoc} -\begin{verbatim} -SASSOC(U:any, V:alist, FN:function):any eval, spread -\end{verbatim} - Searches the \nameref{alist} V for an occurrence of U. If U is not in - the alist the evaluation of function FN is returned. -\begin{verbatim} - EXPR PROCEDURE SASSOC(U, V, FN); - IF NULL V THEN FN() - ELSE IF U = CAAR V THEN CAR V - ELSE SASSOC(U, CDR V, FN); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{sublis} -\index{substitution} -\begin{verbatim} -SUBLIS(X:alist, Y:any):any eval, spread -\end{verbatim} - The value returned is the result of substituting the CDR of - each element of the alist X for every occurrence of the CAR - part of that element in Y. -\begin{verbatim} - EXPR PROCEDURE SUBLIS(X, Y); - IF NULL X THEN Y - ELSE BEGIN SCALAR U; - U := ASSOC(Y, X); - RETURN IF U THEN CDR U - ELSE IF ATOM Y THEN Y - ELSE SUBLIS(X, CAR Y) . - SUBLIS(X, CDR Y) - END; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{subst} -\index{substitution} -\begin{verbatim} -SUBST(U:any, V:any, W:any):any eval, spread -\end{verbatim} - The value returned is the result of substituting U for all - occurrences of V in W. -\begin{verbatim} - EXPR PROCEDURE SUBST(U, V, W); - IF NULL W THEN NIL - ELSE IF V = W THEN U - ELSE IF ATOM W THEN W - ELSE SUBST(U, V, CAR W) . SUBST(U, V, CDR W); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Interpreter} - - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{apply} -\begin{verbatim} -APPLY(FN:{id,function}, ARGS:any-list):any eval, spread -\end{verbatim} - APPLY returns the value of FN with actual parameters - ARGS. The actual parameters in ARGS are already in the - form required for binding to the formal parameters of FN. - Implementation specific portions described in English are - enclosed in boxes. -\begin{verbatim} - EXPR PROCEDURE APPLY(FN, ARGS); - BEGIN SCALAR DEFN; - IF--------------------------------------------- - -Spread the actual parameters in ARGS- - -following the conventions: for calling- - -functions, transfer to the entry point of; - - - - -the function, and return the value returned- - ---------------------------------------------- - IF IDP FN THEN RETURN - IF NULL(DEFN := GETD FN) THEN - ERROR(000, LIST(FN, "is an undefined function")) - ELSE IF CAR DEFN EQ 'EXPR THEN - APPLY(CDR DEFN, ARGS) - - ELSE ERROR(000, - LIST(FN, "cannot be evaluated by APPLY")); - IF OR(ATOM FN, NOT(CAR FN EQ 'LAMBDA)) THEN - ERROR(000, - LIST(FN, "cannot be evaluated by APPLY")); - RETURN - -Bind-the--actual-parameters--in-ARGS--to-the- - - - - -formal parameters of the lambda expression.- - -If the two lists are not of equal length- - -then ERROR(000, "Number of parameters do not- - -match"); The value returned is EVAL CADDR- - ---------------------------------------------- - END; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{eval} -\begin{verbatim} -EVAL(U:any):any eval, spread -\end{verbatim} - The value of the expression U is computed. Error numbers - are arbitrary. Portions of EVAL involving machine specific - coding are expressed in English enclosed in boxes. -\begin{verbatim} - EXPR PROCEDURE EVAL(U); - BEGIN SCALAR FN; - IF CONSTANTP U THEN RETURN U; - IF IDP U THEN RETURN - -U-is-an-id.--Return-the-value-most-currently- - -bound to U or if there is no such binding:- - - - - ---------------------------------------------- - IF PAIRP CAR U THEN RETURN - IF CAAR U EQ 'LAMBDA THEN APPLY(CAR U, EVLIS CDR U) - ELSE ERROR(000, LIST(CAR U, - "improperly formed LAMBDA expression")) - ELSE IF CODEP CAR U THEN - RETURN APPLY(CAR U, EVLIS CDR U); - - FN := GETD CAR U; - IF NULL FN THEN - ERROR(000, LIST(CAR U, "is an undefined function")) - ELSE IF CAR FN EQ 'EXPR THEN - RETURN APPLY(CDR FN, EVLIS CDR U) - ELSE IF CAR FN EQ 'FEXPR THEN - RETURN APPLY(CDR FN, LIST CDR U) - ELSE IF CAR FN EQ 'MACRO THEN - RETURN EVAL APPLY(CDR FN, LIST U) - END; -\end{verbatim} -see also \nameref{constantp}, \nameref{idp}, \nameref{pairp}, -\nameref{evlis}, nameref{apply}, nameref{getd} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{evlis} -\begin{verbatim} -EVLIS(U:any-list):any-list eval, spread -\end{verbatim} - EVLIS returns a list of the evaluation of each element of U. -\begin{verbatim} - EXPR PROCEDURE EVLIS(U); - IF NULL U THEN NIL - ELSE EVAL CAR U . EVLIS CDR U; -\end{verbatim} -see also \nameref{eval} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{expand} -\index{macro} -\begin{verbatim} -EXPAND(L:list, FN:function):list eval, spread -\end{verbatim} - FN is a defined function of two arguments to be used in the - expansion of a \name{macro} defined by \nameref{dm}. EXPAND returns a list in the form: -\begin{verbatim} - (FN L (FN L ...(FN L L ) ... )) - 0 1 n-1 n -\end{verbatim} - where n is the number of elements in L, Li is the ith element - of L. -\begin{verbatim} - EXPR PROCEDURE EXPAND(L,FN); - IF NULL CDR L THEN CAR L - ELSE LIST(FN, CAR L, EXPAND(CDR L, FN)); -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{function} -\begin{verbatim} -FUNCTION(FN:function):function noeval, nospread -\end{verbatim} - The function FN is to be passed to another function. If - FN is to have side effects its free variables must be \nameref{fluid} - or \nameref{global}. FUNCTION is like \nameref{quote} but its argument may be - affected by compilation. We do not consider \nameindex{FUNARG}s in this - report. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{quote} -\begin{verbatim} -QUOTE(U:any):any noeval, nospread -\end{verbatim} - Stops evaluation and returns U unevaluated. -\begin{verbatim} - FEXPR PROCEDURE QUOTE(U); - CAR U; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{Input and Output} -\begin{Introduction}{IO} -The user normally communicates with Standard LISP through -\nameindex{standard devices}. The default devices are selected in accordance -with the conventions of the implementation site. Other input and -output devices or files may be selected for reading and writing using -the functions described herein. -\end{Introduction} - - -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{close} -\begin{verbatim} -CLOSE(FILEHANDLE:any):any eval, spread -\end{verbatim} - Closes the file with the internal name FILEHANDLE writing - any necessary end of file marks and such. The value of - FILEHANDLE is that returned by the corresponding OPEN. The - value returned is the value of FILEHANDLE. An error occurs if - the file can not be closed. -\begin{verbatim} - ***** FILEHANDLE could not be closed -\end{verbatim} - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{eject} -\begin{verbatim} -EJECT():NIL eval, spread -\end{verbatim} - Skip to the top of the next output page. Automatic EJECTs - are executed by the print functions when the length set by - the \nameref{pagelength} function is exceeded. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{linelength} -\begin{verbatim} -LINELENGTH(LEN:{integer, NIL}):integer eval, spread -\end{verbatim} - If LEN is an integer the maximum line length to be printed - before the print functions initiate an automatic nameref{terpri} is - set to the value LEN. No initial Standard LISP line length is - assumed. The previous line length is returned except when - LEN is NIL. This special case returns the current line length - and does not cause it to be reset. An error occurs if the - requested line length is too large for the currently selected - output file or LEN is negative or zero. -\begin{verbatim} - ***** LEN is an invalid line length -\end{verbatim} - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{lposn} -\begin{verbatim} -LPOSN():integer eval, spread -\end{verbatim} - Returns the number of lines printed on the current page. At - the top of a page, 0 is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{open} -\index{input}\index{output} -\begin{verbatim} -OPEN(FILE:any, HOW:id):any eval, spread -\end{verbatim} - Open the file with the system dependent name FILE for output - if HOW is \nameref{eq} to OUTPUT, or input if HOW is \name{eq} to INPUT. If - the file is opened successfully, a value which is internally - associated with the file is returned. This value must be - saved for use by \nameref{wrs} and \nameref{rds}. An error occurs if HOW is - something other than INPUT or OUTPUT or the file can't be - opened. -\begin{verbatim} - ***** HOW is not option for OPEN - ***** FILE could not be opened -\end{verbatim} -Use the \nameref{close} function to close a file. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{pagelength} -\begin{verbatim} -PAGELENGTH(LEN:{integer, NIL}):integer eval, spread -\end{verbatim} - Sets the vertical length (in lines) of an output page. - Automatic page \nameref{eject}s are executed by the print functions - when this length is reached. The initial vertical length - is implementation specific. The previous page length is - returned. If LEN is 0, no automatic page ejects will - occur. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{posn} -\begin{verbatim} -POSN():integer eval, spread -\end{verbatim} - Returns the number of characters in the output buffer. When - the buffer is empty, 0 is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{princ} -\begin{verbatim} -PRINC(U:id):id eval, spread -\end{verbatim} - U must be a single character id such as produced by \nameref{explode} - or read by \nameref{readch} or the value of \nameref{$eol$}. The effect is - the character U displayed upon the currently selected output - device. The value of \name{!$EOL!$} causes termination of the - current line like a call to \nameref{terpri}. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{print} -\begin{verbatim} -PRINT(U:any):any eval, spread -\end{verbatim} - Displays U in \nameref{read} readable format and terminates the print - line. The value of U is returned. -\begin{verbatim} - EXPR PROCEDURE PRINT(U); - << PRIN1 U; TERPRI(); U >>; -\end{verbatim} -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{prin1} -\begin{verbatim} -PRIN1(U:any):any eval, spread -\end{verbatim} - U is displayed in a \nameref{read} readable form. The format - of display is the result of \nameref{explode} expansion; special - characters are prefixed with the escape character !, and - strings are enclosed in "... ". Lists are displayed in - list-notation and vectors in vector-notation. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{prin2} -\begin{verbatim} -PRIN2(U:any):any eval, spread -\end{verbatim} - U is displayed upon the currently selected print device - but output is not \nameref{read} readable. The value of U is - returned. Items are displayed as described in the \nameref{explode} - function with the exceptions that the escape character does - not prefix special characters and strings are not enclosed in - "... ". Lists are displayed in list-notation and vectors in - vector-notation. The value of U is returned. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{rds} -\begin{verbatim} -RDS(FILEHANDLE:any):any eval, spread -\end{verbatim} - Input from the currently selected input file is suspended - and further input comes from the file named. FILEHANDLE is - a system dependent internal name which is a value returned - by \nameref{open}. If FILEHANDLE is NIL the standard input device is - selected. When end of file is reached on a non-standard - input device, the standard input device is reselected. When - end of file occurs on the standard input device the Standard - LISP reader terminates. RDS returns the internal name of the - previously selected input file. -\begin{verbatim} - ***** FILEHANDLE could not be selected for input -\end{verbatim} -The function name RDS goes back to "read select"; -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{read} -\begin{verbatim} -READ():any -\end{verbatim} - The next expression from the file currently selected for - input. Valid input forms are: vector-notation, dot- - notation, list-notation, numbers, function-pointers, strings, - and identifiers with escape characters. Identifiers are - interned on the \name{oblist} (see \nameref{intern}) - READ returns the - value of \nameref{\$eof\$} when the end of the currently selected input - file is reached. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{readch} -\begin{verbatim} -READCH():id -\end{verbatim} - Returns the next interned character from the file currently - selected for input. Two special cases occur. If all the - characters in an input record have been read, the value of - \nameref{\$eol\$} is returned. If the file selected for input has - all been read the value of \nameref{\$eof\$} is returned. Comments - delimited by % and end-of-line are not transparent to \nameref{readch}. - - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{terpri} -\begin{verbatim} -TERPRI():NIL -\end{verbatim} - The current print line is terminated. The following output - begins on a new line. - -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\begin{Function}{wrs} -\begin{verbatim} -WRS(FILEHANDLE:any):any eval, spread -\end{verbatim} - Output to the currently active output file is suspended and - further output is directed to the file named. FILEHANDLE is - an internal name which is returned by \nameref{open}. The file named - must have been opened for output. If FILEHANDLE is NIL the - standard output device is selected. WRS returns the internal - name of the previously selected output file. -\begin{verbatim} - ***** FILEHANDLE could not be selected for output -\end{verbatim} -The function name WRS goes back to "write select". -\end{Function} -%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -\section{LISP Reader} -\begin{Introduction}{LISP Reader} -An EVAL read loop has been chosen to drive a Standard LISP system to -provide a continuity in functional syntax. Choices of messages and the -amount of extra information displayed are decisions left to the -implementor. -\end{Introduction} - -\begin{Function}{quit} -\begin{verbatim} -QUIT() -\end{verbatim} -Causes termination of the LISP reader and control to be transferred -to the operating system. -\end{Function} - -\section{System GLOBAL Variables} - - -\begin{Variable}{*comp} -\index{expr} -The value of the global variable !*comp controls whether or not -\nameref{putd} compiles the -function defined in its arguments before defining it. If !*comp is NIL -the function is defined as an \name{expr}. If !*comp is something else the -function is first compiled. Compilation will produce certain changes -in the semantics of functions particularly \nameref{fluid} type access. -\end{Variable} - - -\begin{Variable}{emsg*} -Will contain the MESSAGE generated by the last \nameref{error} call. -\end{Variable} - - -\begin{Variable}{$eof$} -The value of !\$eof!\$ is returned by all input functions when the -end \index{end of file} -of the currently selected input file is reached. -\end{Variable} - - -\begin{Variable}{$eol$} -The value of !\$eol!\$ is returned by \nameref{readch} when it reaches the end -of \name{readch} \index{end of line} -a logical input record. Likewise \nameref{princ} will terminate its current line -(like a call to \nameref{terpri}) when !\$eol!\$ is its argument. -\end{Variable} - -\begin{Variable}{*gc} -\index{garbage collector} -!*gc controls the printing of garbage collector messages. If NIL no -indication of garbage collection may occur. If non-NIL various system -dependent messages may be displayed. -\end{Variable} - - -\begin{Variable}{nil} -\name{nil} is a special global variable. It is protected from being modified -by \nameref{set} or \nameref{setq}. Its value is \name{nil}. -\end{Variable} - -\begin{Variable}{*raise} -If \name{!*raise} is non-NIL all characters input through Standard LISP -input/output functions will be raised to upper case. If \name{!*RAISE} is NIL -characters will be input as is. -\end{Variable} - - -\begin{Variable}{t} -\name{t} is a special global variable. It is protected from being modified -by \nameref{set} or \nameref{setq}. Its value is \name{t}. -\end{Variable} - -\end{document} +\begin{document} + + + +\section{Preliminaries} + +\subsection{Primitive Data Types} +\begin{Type}{integer} +Integer numbers: +Integers are also called "fixed" numbers. The magnitude of +an integer is unrestricted. Integers in the LISP input stream are +an arbitrary number of integer digits, eventually preceded by +a plus or minus sign. +\begin{Examples} +22\\ +-31415926585\\ +\end{Examples} +\end{Type} + +\begin{Type}{floating} +Floating point numbers: The precision of floating point +numbers is determined solely by the implementation. In BNF floating +point numbers are recognized by the grammar: +\begin{verbatim} + ::= .|.| + . + ::= | + E| + E-| + E+ + ::= | + +|- +\end{verbatim} +\begin{Examples} +3.1415\\ +17.0\\ +-22e100\\ +1.1e-5 +\end{Examples} +\end{Type} + +\begin{Type}{id} +An identifier is a string of characters which may have the +following items associated with it. + + + print name: The characters of the identifier. + + flags: An identifier may be tagged with a flag. Access is + by the \nameref{flag}, \nameref{remflag}and + \nameref{flagp} functions. + + properties: An identifier may have an indicator-value pair + associated with it. Access is by the + \nameref{put}, \nameref{get}, and \nameref{remprop} + functions. + + values: An identifier may have a value associated with + it. Access to values is by \nameref{set} \nameref{setq} + The method by which the value + is attached to the identifier is known as the binding + type, being one of + \nameref{Local Binding}, \nameref{Global Binding}, + or \nameref{Fluid Binding}. + + functions: + An identifier may have a function or macro associated with + it. Access is by the + \nameref{putd}, \nameref{getd}, and \nameref{remd} functions. + An identifier may not have both a function and a value + associated with it. + + + \name{oblist} entry: An identifier may be entered and removed from a + structure called the \nameref{oblist}. Its presence on the \name{oblist} + does not directly affect the other properties. Access to + the \name{oblist} is by the + \nameref{intern}, \nameref{remob}, and \nameref{read} + functions. + + The maximum length of a Standard LISP identifier is 24 + characters (excluding occurrences of the escape character !) + but an implementation may allow more. Special characters + (digits in the first position and punctuation) must be prefixed + with an escape character, an ! in Standard LISP. In BNF + identifiers are recognized by the grammar: +\begin{verbatim} + ::= ! + ::= + + A|B|C|D|E|F|G|H|I|J|K|L|M|N|O|P|Q|R|S|T|U|V|W|X|Y|Z| + a|b|c|d|e|f|g|h|i|j|k|l|m|n|o|p|q|r|s|t|u|v|w|x|y|z + ::= | + ::= | + ::= | + + ::= | + + Note: Using lower case letters in identifiers may cause + portability problems. Lower case letters are automatically + converted to upper case when the \nameref{!*RAISE} flag is T. +\end{verbatim} + +\begin{Examples} +a\\ +Hugo\\ +!1!-otto\\ +!*raise\\ +this!-is!-a!-long!-id\\ +!U!P!P!E!R!-and!-!l!o!w!e!r\\ +\end{Examples} +\end{Type} + + +\begin{Type}{string} +A set of characters enclosed in double quotes as +in "THIS IS A STRING". A quote is included by doubling it as in "HE +SAID, ""LISP""". The maximum size of strings is 80 characters but an +implementation may allow more. Strings are not part of the \nameref{oblist} and +are considered constants like \nameref{number}s, \nameref{vector}s, +and \nameref{function-pointer}s. +\end{Type} + +\begin{Type}{dotted-pair} +\index{car}\index{cdr} +A dotted pair is a primitive structure which has a left and right part. +A notation called {\em dot-notation} is used for dotted pairs and +takes the form: +\begin{verbatim} + ( . ) +\end{verbatim} + +The is known as the \nameref{car} portion and the + as the \nameref{cdr} portion. The left and right parts may be of any type. +Spaces are used to resolve ambiguity with floating point numbers. + +When or are dotted-pairs themselves, +the \nameref{list-notation} is often more convenient. +\end{Type} + +\begin{Type}{vector} +A vector is a primitive uniform structure in which +an integer index is used to access random values in the structure. The +individual elements of a vector may be of any type. Access to vectors +is restricted to functions \nameref{putv}, \nameref{getv}, and +\nameref{upbv}. +A notation for vectors, vector-notation, has the +elements of a vector surrounded by square brackets +\begin{verbatim} + ::= | + ::= [] +\end{verbatim} +\begin{Examples} +[1 2 3 5 7 11 13 17 19 23]\\ +[nil (a) (a . a)]\\ +[[1 2 3 4 5][2 4 6 8 10][3 6 9 12 15]]\\ +\end{Examples} +\end{Type} + +\begin{Type}{function-pointer} + + An implementation may have functions which deal + with specific data types other than those listed. The use + of these entities is to be avoided with the exception of a + restricted use of the \name{function-pointer}, an access method to + compiled EXPRs and FEXPRs (see \nameref{Function Types}). + + A particular + \name{function-pointer} must + remain valid throughout execution. Systems which change the + location of a function must use either an indirect reference or + change all occurrences of the associated value. There are two + classes of use of function-pointers, those which are supported + by Standard LISP but are not well defined, and those which are + well defined. +\end{Type} + +\subsection{Classes of Primitive Data Types} +\begin{Introduction}{Type Classes} +The classes of primitive types are a notational convenience for +describing the properties of functions. +\end{Introduction} + +\begin{Type}{boolean} +The set of global variables \{\nameref{T}, \nameref{NIL}\}, or their respective + values, \{T, NIL\}. +\end{Type} + +\begin{Type}{extra-boolean} +Any value in the system. Anything that is not \nameref{NIL} has + the boolean interpretation T. +\end{Type} + +\begin{Type}{ftype} + The class of definable function types. The set of ids \{EXPR, + FEXPR, MACRO\}. See \nameref{Function Types}. +\end{Type} + +\begin{Type}{number} +The set of \{\nameref{integer}, \nameref{floating}\}. +\end{Type} + + +\begin{Type}{constant} +The set of \{\nameref{integer}, \nameref{floating}, \nameref{string}, + \nameref{vector}, \nameref{function-pointer} \}. + Constants evaluate to themselves (see \nameref{eval}) +\end{Type} + +\begin{Type}{any} +The set of \{\nameref{integer}, \nameref{floating}, \nameref{string}, + \nameref{id}, \nameref{dotted-pair}, \nameref{vector}, + \nameref{function-pointer}\}. An S-expression is another term for any. + All Standard LISP entities have some value unless an \nameref{error} + occurs during evaluation or the function causes transfer of + control (such as \nameref{go} and \nameref{return}). +\end{Type} + +\begin{Type}{atom} +The set \nameref{any} - \{\nameref{dotted-pair}\}. Any item wich is not a \name{dotted-pair} +is considered as \name{atom}. +\end{Type} + + +\subsection{Structures} +\begin{Introduction}{Structures} +Structures are entities created out of the primitive types by the +use of dotted-pairs. Lists are structures very commonly required +as actual parameters to functions. Where a list of homogeneous +entities is required by a function this class will be denoted +by where xxx is the name of a class of primitives or +structures. Thus a list of ids is an id-list, a list of integers an +integer-list and so on. +\end{Introduction} + +\begin{Concept}{List-Notation} +A \name{list} is recursively defined as \nameref{nil} or the dotted-pair + (\nameref{any} . list). A special notation called list-notation is used + to represent lists. List-notation eliminates extra parentheses + and dots. The structure (a . (b . (c . nil))) in list notation + + is (a b c). List-notation and dot-notation may be mixed as in + (a b . c) or (a (b . c) d) which are (a . (b . c)) and (a . + ((b . c) . (d . nil))). In BNF lists are recognized by the + grammar: +\begin{verbatim} + ::= ( | + ::= ) | . ) +\end{verbatim} + Note: () is an alternate input representation of nil. +\end{Concept} + +\begin{Concept}{alist} +An association list; each element of the list is a + dotted-pair, the CAR part being a key associated with the value + in the CDR part. +\begin{Examples} +((a . 17)(b . (expt x 2))(q . nil))\\ +\end{Examples} +Here a is associated wity 17 while b is linked to the square of x +and q points to nil. +\end{Concept} + +\begin{Concept}{cond-form} + A cond-form is a list of 2 element lists of the form: + + (ANTECEDENT:any CONSEQUENT:any) + + The first element will henceforth be known as the antecedent + and the second as the consequent. The antecedent must have a + value. The consequent may have a value or an occurrence of + \nameref{go} or \nameref{return}. +\begin{Examples} +((greaterp x 0) 1)\\ +(t 0)\\ +\end{Examples} +\end{Concept} + +\begin{Concept}{lambda} +A LAMBDA expression which must have the form (in list + notation): + + (LAMBDA ). + + is a + list of formal parameters for an S-expression to be + evaluated. The semantics of the evaluation are defined with + the \nameref{eval}. +\begin{Examples} + (lambda(x y)(cons (car x)(cddr y))) +\end{Examples} +\end{Concept} + +\begin{Concept}{function} + + A LAMBDA expression or a function-pointer to a function. A + function is always evaluated as an EVAL, SPREAD form. +(see \nameref{Function Types}). +\end{Concept} + + + +\section{Notation} + +\begin{Introduction}{Function Descriptions} + +Each function is provided with a prototypical header line. Each formal +parameter is given a name and suffixed with its allowed type. Lower +case, italic tokens are names of classes and upper case, bold face, +tokens are parameter names referred to in the definition. The type of +the value returned by the function (if any) is suffixed to the +parameter list. +If it is not commonly used the parameter type +may be a specific set enclosed in brackets {...}. For example: + +\begin{verbatim} +PUTD(FNAME:id, TYPE:ftype, BODY:{lambda, function-pointer}):id +\end{verbatim} + +PUTD is a function with three parameters. The parameter FNAME is +an id to be the name of the function being defined. TYPE is the +type of the function being defined and BODY is a lambda expression +or a function-pointer. PUTD returns the name of the function being +defined. + +Functions which accept formal parameter lists of arbitrary length +have the type class and parameter enclosed in square brackets +indicating that zero or more occurrences of that argument are +permitted. For example: + +\begin{verbatim} +AND([U:any]):extra-boolean +\end{verbatim} + +AND is a function which accepts zero or more arguments which may be +of any type. +\end{Introduction} + +\begin{Introduction}{Function Types} +\index{eval type}\index{noeval type} +\index{spread type}\index{nospread type} +\index{expr type}\index{macro type} + +EVAL type functions are those which are invoked with evaluated +arguments. NOEVAL functions are invoked with unevaluated arguments. +SPREAD type functions have their arguments passed in one-to-one +correspondence with their formal parameters. NOSPREAD functions +receive their arguments as a single list. EVAL, SPREAD functions +are associated with EXPRs and NOEVAL, NOSPREAD functions with +FEXPRs. EVAL, NOSPREAD and NOEVAL, SPREAD functions can be +simulated using NOEVAL, NOSPREAD functions or MACROs. + +EVAL, SPREAD type functions may have a maximum of 15 parameters. +There is no limit on the number of parameters a NOEVAL, NOSPREAD +function or MACRO may have. + +In the context of the description of an EVAL, SPREAD function, then +we speak of the formal parameters we mean their actual values. +However, in a NOEVAL, NOSPREAD function it is the unevaluated actual +parameters. + +A third function type, the MACRO, implements functions which create +S-expressions based on actual parameters. When a macro invocation + +is encountered, the body of the macro, a lambda expression, is +invoked as a NOEVAL, NOSPREAD function with the macro's invocation +bound as a list to the macros single formal parameter. When the +macro has been evaluated the resulting S-expression is reevaluated. +The description of \nameref{eval} and \nameref{expand} provide precise +details. +\end{Introduction} + +\begin{Introduction}{Messages} +\index{error}\index{warning} +Many functions detect errors. The description of such functions +will include these error conditions and suggested formats for +display of the generated error messages. A call on the +\nameref{error} +function is implied but the error number is not specified by +Standard LISP. In some cases a warning message is sufficient. To +distinguish between errors and warnings, errors are prefixed with +five asterisks and warnings with only three. + +Primitive functions check arguments that must be of a certain +primitive type for being of that type and display an error message +if the argument is not correct. The type mismatch error always +takes the form: +\begin{verbatim} +***** PARAMETER not TYPE for FN +\end{verbatim} + +Here PARAMETER is the unacceptable actual parameter, TYPE is the +type that PARAMETER was supposed to be. FN is the name of the +function that detected the error. +\end{Introduction} + +\begin{Introduction}{Comments} + +The character \% signals the start of a comment, text to be ignored during +parsing. A comment is terminated by the end of the line it is on. The +function \nameref{readch}must be able to read a comment one character at a +time. Comments are transparent to the function READ. The percent sign +may occur as a character in identifiers by preceding it with the escape +character. + + (setq a 17) \% this is a comment + +\end{Introduction} + +%----------------------------------------------------------------- +\section{Elementary Predicates} +%----------------------------------------------------------------- + +\begin{Introduction}{Elementary Predicates} +Functions in this section return \nameref{T} when the condition defined is met +and \nameref{NIL} when it is not. Defined are type checking functions and +elementary comparisons. +\end{Introduction} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{atom} +\begin{verbatim} +ATOM(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is not a \nameref{dotted-pair}. +\begin{verbatim} + + EXPR PROCEDURE ATOM(U); + NULL PAIRP U; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{codep} +\begin{verbatim} +CODEP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a \nameref{function-pointer}. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{constantp} +\begin{verbatim} +CONSTANTP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a constant (a \nameref{number}, + \nameref{string}, \nameref{function-pointer}, or \nameref{vector}). +\begin{verbatim} + + EXPR PROCEDURE CONSTANTP(U); + NULL OR(PAIRP U, IDP U); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{eq} +\begin{verbatim} +EQ(U:any, V:any):boolean eval, spread +\end{verbatim} + Returns T if U points to the same object as V. EQ is not a + reliable comparison between numeric arguments. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{eqn} +\begin{verbatim} +EQN(U:any, V:any):boolean eval, spread +\end{verbatim} + Returns T if U and V are EQ or if U and V are + \nameref{number}s and have the same value and type. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{equal} +\begin{verbatim} +EQUAL(U:any, V:any):boolean eval, spread +\end{verbatim} + Returns T if U and V are the same. Dotted-pairs are + compared recursively to the bottom levels of their trees. + Vectors must have identical dimensions and EQUAL values in + all positions. Strings must have identical characters. + Function pointers must have \nameref{eq} values. Other atoms must be + \nameref{eqn} equal. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{fixp} +\begin{verbatim} +FIXP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is an \nameref{integer}. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{floatp} +\begin{verbatim} +FLOATP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a \nameref{floating} point number. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{idp} +\begin{verbatim} +IDP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is an \nameref{id}. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{minusp} +\begin{verbatim} +MINUSP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a number and less than 0. If U is not a + \nameref{number} or is a positive number, NIL is returned. +\begin{verbatim} + + EXPR PROCEDURE MINUSP(U); + IF NUMBERP U THEN LESSP(U, 0) ELSE NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{null} +\begin{verbatim} +NULL(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is NIL. +\begin{verbatim} + + EXPR PROCEDURE NULL(U); + U EQ NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{numberp} +\begin{verbatim} +NUMBERP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a \nameref{number}. +\begin{verbatim} + + EXPR PROCEDURE NUMBERP(U); + IF OR(FIXP U, FLOATP U) THEN T ELSE NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{onep} +\begin{verbatim} +ONEP(U:any):boolean eval, spread. +\end{verbatim} + Returns T if U is a \nameref{number} and has the value 1 or 1.0. + Returns NIL otherwise. +\begin{verbatim} + + + EXPR PROCEDURE ONEP(U); + IF EQN(U,1) OR EQN(U,1.0) THEN T ELSE NIL; +\end{verbatim} + The definition in the published report is incorrect as it + does not return T for U of 1.0. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{pairp} +\begin{verbatim} +PAIRP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a \nameref{dotted-pair}. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{stringp} +\begin{verbatim} +STRINGP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a string. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{vectorp} +\begin{verbatim} +VECTORP(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a vector. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{zerop} +\begin{verbatim} +ZEROP(U:any):boolean eval, spread. +\end{verbatim} + Returns T if U is a number and has the value 0 or 0.0. + Returns NIL otherwise. + + The definition in the published report is incorrect as it + does not return T for U of 0.0. +\end{Function} + +\section{Functions on Dotted-Pairs} +\begin{Introduction}{Function on Dotted-Pairs} +\index{dotted-pair} +The following are elementary functions on dotted-pairs. All functions +in this section which require dotted-pairs as parameters detect a type +mismatch error if the actual parameter is not a dotted-pair. +\end{Introduction} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{car} +\begin{verbatim} +CAR(U:dotted-pair):any eval, spread +\end{verbatim} + CAR(CONS(a, b)) -> a. The left part of U is returned. The + type mismatch error occurs if U is not a dotted-pair. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{cdr} +\begin{verbatim} +CDR(U:dotted-pair):any eval, spread +\end{verbatim} + CDR(CONS(a, b)) -> b. The right part of U is returned. The + type mismatch error occurs if U is not a dotted-pair. + +\end{Function} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{caar} +\index{CAAAAR}\index{CAAAR}\index{CAAADR}\index{CAADR} +\index{CADR}\index{CAADAR}\index{CADAR}\index{CDAR}\index{CAADDR} +\index{CADDR}\index{CDDR}\index{CADAAR}\index{CDAAR}\index{CADADR} +\index{CDADR}\index{CADDAR}\index{CDDAR}\index{CADDDR}\index{CDDDR} +\index{CDAAAR}\index{CDAADR}\index{CDADAR}\index{CDADDR}\index{CDDAAR} +\index{CDDADR}\index{CDDDAR}\index{CDDDDR} +The composites of CAR and CDR are supported up to 4 levels, namely: + +CAAAAR CAAAR CAAR CAAADR CAADR CADR + +CAADAR CADAR CDAR CAADDR CADDR CDDR + +CADAAR CDAAR CADADR CDADR CADDAR CDDAR + +CADDDR CDDDR CDAAAR CDAADR CDADAR CDADDR + +CDDAAR CDDADR CDDDAR CDDDDR + +Here e.g. (cdar x) is equivlaent to (cdr (car x)). + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{cons} +\begin{verbatim} +CONS(U:any, V:any):dotted-pair eval, spread +\end{verbatim} + Returns a dotted-pair which is not \nameref{eq} to anything and has U + as its \nameref{car} part and V as its nameref(cdr) part. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{list} +\begin{verbatim} +LIST([U:any]):list noeval, nospread, or macro +\end{verbatim} + A list of the evaluation of each element of U is returned. + The order of evaluation nead not be first to last as the + following definition implies. +\begin{verbatim} + + FEXPR PROCEDURE LIST(U); + EVLIS U; +\end{verbatim} + The published report's definition implies a specific + ordering. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{rplaca} +\begin{verbatim} +RPLACA(U:dotted-pair, V:any):dotted-pair eval, spread +\end{verbatim} + The \nameref{car} portion of the dotted-pair U is replaced by V. If + dotted-pair U is (a . b) then (V . b) is returned. The type + mismatch error occurs if U is not a dotted-pair. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{rplacd} +\begin{verbatim} +RPLACD(U:dotted-pair, V:any):dotted-pair eval, spread +\end{verbatim} + The \nameref{cdr} portion of the dotted-pair U is replaced by V. If + dotted-pair U is (a . b) then (a . V) is returned. The + type mismatch error occurs if U is not a dotted-pair. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Functions for Identifiers} + +\begin{Concept}{oblist} +The following functions deal with identifiers and the \nameref{oblist}, +the structure of which is not defined. +The \name{oblist} is an internal stucture where \nameref{id}s +are kept. The function of the \name{oblist} is +to provide a symbol table for identifiers created during input. +Identifiers created by \nameref{read} which have the same characters will +therefore refer to the same object (see the \nameref{eq} function). + +Identifiers created by \nameref{gensym} or \nameref{compress} are +not member of the \name{oblist} and therefore they are not +unique even if they are represented by the same character +sequence on output. The function \nameref{intern} is used +to create an equivalent unique \name{id} which then is +member of the \name{oblist}. +\end{Concept} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{compress} +\begin{verbatim} +COMPRESS(U:id-list):{atom-vector} eval, spread +\end{verbatim} + U is a list of single character identifiers which is built + into a Standard LISP entity and returned. Recognized are + \nameref{number}s, \nameref{string}s, + and identifiers (see \nameref{id}) with the \name{escape} character + prefixing special characters. Function pointers + may be compressed but this is an undefined use. If an entity + cannot be parsed out of U or characters are left over after + parsing an error occurs: +\begin{verbatim} + ***** Poorly formed atom in COMPRESS +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\begin{Function}{explode} +\begin{verbatim} +EXPLODE(U:{atom}-{vector}):id-list eval, spread +\end{verbatim} + Returned is a list of interned characters representing the + characters to print of the value of U. The primitive data + types have these formats: + + \nameref{integer}: Leading zeroes are suppressed and a minus sign + prefixes the digits if the integer is negative. + + \nameref{floating}: The value appears in the format [-]0.nn...nnE[-]mm + if the magnitude of the number is too large or small to + display in [-]nnnn.nnnn format. The crossover point is + determined by the implementation. + + \nameref{id}: The characters of the print name of the identifier + are produced with special characters prefixed with the + escape character. + + \nameref{string}: The characters of the string are produced surrounded + by double quotes "...". + + \nameref{function-pointer}: The value of the function-pointer is created + as a list of characters conforming to the conventions of + the system site. + + The type mismatch error occurs if U is not a number, + identifier, string, or function-pointer. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{gensym} +\begin{verbatim} +GENSYM():identifier eval, spread +\end{verbatim} + Creates an identifier which is not interned on the \nameref{oblist} and + consequently not \nameref{eq} to anything else. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{intern} +\begin{verbatim} +INTERN(U:{id,string}):id eval, spread +\end{verbatim} + INTERN searches the \nameref{oblist} for an identifier with the same + print name as U and returns the identifier on the \name{oblist} if a + match is found. Any properties and global values associated + with U may be lost. If U does not match any entry, a + new one is created and returned. If U has more than the + maximum number of characters permitted by the implementation + (the minimum number is 24) an error occurs: +\begin{verbatim} + ***** Too many characters to INTERN +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{remob} +\begin{verbatim} +REMOB(U:id):id eval, spread +\end{verbatim} + If U is present on the \nameref{oblist} it is removed. This does not + affect U having properties, flags, functions and the like. U + is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Property List Functions} +\begin{Introduction}{Property List Functions} +With each id in the system is a \name{property list}, a set of entities +which are associated with the id for fast access. These entities are +called \nameindex{flags} if their use gives the id a single valued +property, and \nameindex{properties} if the id is to have a multivalued +attribute: an indicator with a property. + +Flags and indicators may clash, consequently care should be taken to +avoid this occurrence. Flagging X with an id which already is an +indicator for X may result in that indicator and associated property +being lost. Likewise, adding an indicator which is the same id as a +flag may result in the flag being destroyed. +\end{Introduction} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{flag} +\begin{verbatim} +FLAG(U:id-list, V:id):NIL eval, spread +\end{verbatim} + U is a list of ids which are flagged with V. The effect of + \name{flag} is that \nameref{flagp} will have the value T for those ids of U + which were flagged. Both V and all the elements of U must be + identifiers or the type mismatch error occurs. +\begin{Examples} +flag('(u v),'symmetric)\\ +\end{Examples} +Note: If you want to flag a single \name{id} you must put it into +a list before calling the function \name{flag}. A flag is removed +by \nameref{remflag} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{flagp} +\begin{verbatim} +FLAGP(U:any, V:any):boolean eval, spread +\end{verbatim} + Returns T if U has been previously flagged (see \nameref{flag}} + with V, else NIL. Returns NIL if either U or V is not an \nameref{id}. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{get} +\begin{verbatim} +GET(U:any, IND:any):any eval, spread +\end{verbatim} + Returns the property associated with indicator IND from the + property list of U. If U does not have indicator IND, NIL is + returned. GET cannot be used to access functions (use GETD + instead). For setting a property use the function \nameref{put}. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{put} +\begin{verbatim} +PUT(U:id, IND:id, PROP:any):any eval, spread +\end{verbatim} + The indicator IND with the property PROP is placed on the + property list of the id U. If the action of PUT occurs, the + value of PROP is returned. If either of U and IND are not + ids the type mismatch error will occur and no property will + be placed. PUT cannot be used to define functions + (use \nameref{putd} instead). The values stored on the property + list can be retrieved using \nameref{get}. \nameref{remprop} + removes a property. +\begin{Examples} +put('otto,'hugo,'(a))\\ +get('otto,'hugo) & (a)\\ +put('otto,'hugo,'(b))\\ +get('otto,'hugo) & (b)\\ +remprop('otto,'hugo)\\ +get('otto,'hugo) & nil\\ +\end{Examples} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{remflag} +\begin{verbatim} +REMFLAG(U:any-list, V:id):NIL eval, spread +\end{verbatim} + Removes the flag V from the property list of each member of + the list U. Both V and all the elements of U must be ids or + the type mismatch error will occur (see \nameref{flag}). + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{remprop} +\begin{verbatim} +REMPROP(U:any, IND:any):any eval, spread +\end{verbatim} + Removes the property with indicator IND from the property + list of U. Returns the removed property or NIL if there was + no such indicator (see \nameref{put}}. +\end{Function} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Function Definition} +\begin{Introduction}{Function Definition} +Functions in Standard LISP are global entities. To avoid +function-variable naming clashes no variable may have the same name as +a function. +\end{Introduction} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{de} +\index{expr} +\begin{verbatim} +DE(FNAME:id, PARAMS:id-list, FN:any):id noeval, nospread +\end{verbatim} + The function FN with the formal parameter list PARAMS is + added to the set of defined functions with the name FNAME. + Any previous definitions of the function are lost. The + function created is of type EXPR (see \nameref{Function Types}). If \nameref{*COMP} is + non-NIL, the EXPR is first compiled. The name of the defined + function is returned. +\begin{verbatim} + + FEXPR PROCEDURE DE(U); + PUTD(CAR U, 'EXPR, LIST('LAMBDA, CADR U, CADDR U)); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{df} +\index{fexpr} +\begin{verbatim} +DF(FNAME:id, PARAM:id-list, FN:any):id noeval, nospread +\end{verbatim} + The function FN with formal parameter PARAM is added to the + set of defined functions with the name FNAME. Any previous + definitions of the function are lost. The function created + is of type FEXPR (see \nameref{Function Types}). If \nameref{*COMP} is T the FEXPR + is first compiled. The name of the defined function is + returned. +\begin{verbatim} + + FEXPR PROCEDURE DF(U); + PUTD(CAR U, 'FEXPR, LIST('LAMBDA, CADR U, CADDR U)); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{dm} +\index{macro} +\begin{verbatim} +DM(MNAME:id, PARAM:id-list, FN:any):id noeval, nospread +\end{verbatim} + The macro FN with the formal parameter PARAM is added to the + set of defined functions with the name MNAME. Any previous + definitions of the function are overwritten. The function + created is of type MACRO (see \nameref{Function Types}). + The name of the macro is returned. +\begin{verbatim} + + FEXPR PROCEDURE DM(U); + PUTD(CAR U, 'MACRO, LIST('LAMBDA, CADR U, CADDR U)); +\end{verbatim} + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{getd} +\begin{verbatim} +GETD(FNAME:any):{NIL, dotted-pair} eval, spread +\end{verbatim} + If FNAME is not the name of a defined function, NIL + is returned. If FNAME is a defined function then the + dotted-pair +\begin{verbatim} + (TYPE:ftype . DEF:{function-pointer, lambda}) +\end{verbatim} + is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{putd} +\begin{verbatim} +PUTD(FNAME:id, TYPE:ftype, BODY:function):id eval, spread +\end{verbatim} + Creates a function with name FNAME and definition BODY of + type TYPE. If PUTD succeeds the name of the defined function + is returned. The effect of PUTD is that GETD will return a + dotted-pair with the functions type and definition. Likewise + the \nameref{globalp} predicate will return T when queried with the + function name. + If the function FNAME has already been declared as a GLOBAL + or FLUID variable the error: +\begin{verbatim} + ***** FNAME is a non-local variable +\end{verbatim} + occurs and the function will not be defined. If function + FNAME already exists a warning message will appear: +\begin{verbatim} + *** FNAME redefined +\end{verbatim} + The function defined by PUTD will be compiled before + definition if \nameref{*COMP} variable is non-NIL. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{remd} +\begin{verbatim} +REMD(FNAME:id):{NIL, dotted-pair} eval, spread +\end{verbatim} + Removes the function named FNAME from the set of defined + functions. Returns the (ftype . function) dotted-pair or + NIL as does \nameref)getd}. The global/function attribute of FNAME is + removed and the name may be used subsequently as a variable. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{Variables and Bindings} + +\begin{Introduction}{Scope} +\index{variables} +A variable is a place holder for a Standard LISP entity which is said +to be bound to the variable. The scope of a variable is the range over +which the variable has a defined value. There are three different +binding mechanisms in Standard LISP: +\nameref{Local Binding}, \nameref{Global Binding}, and +\nameref{Fluid Binding}. +\end{Introduction} + +\begin{Concept}{Local Binding} +\index{variables} +This type of binding occurs +only in compiled functions. Local variables occur as formal parameters +in \nameref{lambda} expressions (function arguments) + and as \nameref{prog} form variables. The binding occurs +when a lambda expression is evaluated or when a \name{prog} form is executed. +The scope of a local variable is the body of the function in which it +is defined. +\end{Concept} + +\begin{Concept}{Global Binding} +\index{variables} +Only one binding of a +global variable exists at any time allowing direct access to the value +bound to the variable. The scope of a global variable is universal. +Variables declared \nameref{global} may not appear as parameters +in \nameref{lambda} expressions (function arguments) + or as \nameref{prog} form variables. A variable must be declared +\name{global} prior to its use as a global variable since the default type +for undeclared variables is \nameref{fluid}. +\end{Concept} + + + +\begin{Concept}{Fluid Binding} +\index{variables} +Fluid variables are global +in scope but may occur as \name{fluid} formal parameters or +\nameref{prog} form variables. In interpreted functions all formal parameters +and \name{prog} form variables are considered to have fluid binding until +changed to local binding by compilation. When \name{fluid} variables are +used as parameters (\nameref{lambda} expressions} +they are rebound in such a way that the previous +binding may be restored. All references to \name{fluid} variables are to the +currently active binding. +\end{Concept} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{fluid} +\index{variables} +\begin{verbatim} +FLUID(IDLIST:id-list):NIL eval, spread +\end{verbatim} + The ids in IDLIST are declared as FLUID type variables (ids + not previously declared are initialized to NIL). Variables + in IDLIST already declared FLUID are ignored. Changing a + variable's type from GLOBAL to FLUID is not permissible and + results in the error: +\begin{verbatim} + ***** ID cannot be changed to FLUID +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{fluidp} +\index{variables} +\begin{verbatim} +FLUIDP(U:any):boolean eval, spread +\end{verbatim} + If U has been declared by \nameref{fluid} T is + returned, otherwise NIL is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{global} +\index{variables} +\begin{verbatim} +GLOBAL(IDLIST:id-list):NIL eval, spread +\end{verbatim} + The ids of IDLIST are declared global type variables. If + an id has not been declared previously it is initialized to + NIL. Variables already declared GLOBAL are ignored. Changing + a variables type from FLUID to GLOBAL is not permissible and + results in the error: +\begin{verbatim} + ***** ID cannot be changed to GLOBAL +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{globalp} +\index{variables} +\begin{verbatim} +GLOBALP(U:any):boolean eval, spread +\end{verbatim} + If U has been declared GLOBAL or is the name of a defined + function, T is returned, else NIL is returned. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{set} +\index{variables} +\begin{verbatim} +SET(EXP:id, VALUE:any):any eval, spread +\end{verbatim} + EXP must be an identifier or a type mismatch error occurs. + The effect of SET is replacement of the item bound to + the identifier by VALUE. If the identifier is not a local + variable or has not been declared GLOBAL it is automatically + declared FLUID with the resulting warning message: +\begin{verbatim} + *** EXP declared FLUID +\end{verbatim} + EXP must not evaluate to T or NIL or an error occurs: +\begin{verbatim} + ***** Cannot change T or NIL +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{setq} +\index{variables} +\begin{verbatim} +SETQ(VARIABLE:id, VALUE:any):any noeval, nospread +\end{verbatim} + If VARIABLE is not local or GLOBAL it is by default declared + FLUID and the warning message: +\begin{verbatim} + *** VARIABLE declared FLUID +\end{verbatim} + appears. The value of the current binding of VARIABLE is + replaced by the value of VALUE. VARIABLE must not be T or NIL + or an error occurs: +\begin{verbatim} + ***** Cannot change T or NIL +\end{verbatim} + +\begin{verbatim} + MACRO PROCEDURE SETQ(X); + LIST('SET, LIST('QUOTE, CADR X), CADDR X); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{unfluid} +\index{variables} +\begin{verbatim} +UNFLUID(IDLIST:id-list):NIL eval, spread +\end{verbatim} + The variables in IDLIST that have been declared as \nameref{fluid} + variables are no longer considered as fluid variables. + Others are ignored. This affects only compiled functions + as free variables in interpreted functions are automatically + considered fluid. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + +\section{Program Feature Functions} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{go} +\index{program control} +\index{label} +\begin{verbatim} +GO(LABEL:id) noeval, nospread +\end{verbatim} + GO alters the normal flow of control within a \nameref{prog} function. + The next statement of a PROG function to be evaluated is + immediately preceded by LABEL. A GO may only appear in the + following situations: + + 1. At the top level of a \nameref{prog} referencing a label which + also appears at the top level of the same prog. + + 2. As the consequent of a \nameref{cond} item of a \name{cond} appearing on + the top level of a \nameref{prog}. + + 3. As the consequent of a \nameref{cond} item which appears as the + consequent of a \name{cond} item to any level. + + 4. As the last statement of a \nameref{progn} which appears at + the top level of a \nameref{prog} or in a \name{progn} appearing in + the consequent of a \nameref(cond} to any level subject to the + restrictions of 2 and 3. + + 5. As the last statement of a \nameref{progn} + within a \name{progn} or as + the consequent of a \nameref{prog}in a \name{progn}to any level subject + to the restrictions of 2, 3 and 4. + + If LABEL does not appear at the top level of the \name{prog} in + which the \name{go} appears, an error occurs: +\begin{verbatim} + ***** LABEL is not a known label +\end{verbatim} + + If the \name{go} has been placed in a position not defined by rules + 1-5, another error is detected: +\begin{verbatim} + ***** Illegal use of GO to LABEL +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{prog} +\index{program control} +\begin{verbatim} +PROG(VARS:id-list, [PROGRAM:{id, any}]):any noeval, nospread +\end{verbatim} + VARS is a list of ids which are considered fluid when the + PROG is interpreted and local when compiled (see ``Variables + and Bindings'', section 3.6 on page 22). The PROGs variables + are allocated space when the PROG form is invoked and are + deallocated when the PROG is exited. PROG variables are + initialized to NIL. The PROGRAM is a set of expressions to be + evaluated in order of their appearance in the PROG function. + Identifiers appearing in the top level of the PROGRAM are + labels which can be referenced by GO. The value returned by + the PROG function is determined by a \nameref{return} function or NIL + if the PROG falls through. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{progn} +\index{program control} +\begin{verbatim} +PROGN([U:any]):any noeval, nospread +\end{verbatim} + U is a set of expressions which are executed sequentially. + The value returned is the value of the last expression. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{prog2} +\index{program control} +\begin{verbatim} +PROG2(A:any, B:any)any eval, spread +\end{verbatim} + Returns the value of B. +\begin{verbatim} + + EXPR PROCEDURE PROG2(A, B); + B; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{return} +\index{program control} +\begin{verbatim} +RETURN(U:any) eval, spread +\end{verbatim} + Within a \nameref{prog}, RETURN terminates the evaluation of a PROG + and returns U as the value of the PROG. The restrictions on + the placement of RETURN are exactly those of nameref{go}. Improper + placement of RETURN results in the error: +\begin{verbatim} + ***** Illegal use of RETURN +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{Error Handling} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{error} +\index{error handling} +\begin{verbatim} +ERROR(NUMBER:integer, MESSAGE:any) eval, spread +\end{verbatim} + NUMBER and MESSAGE are passed back to a surrounding \nameref{errorset} + (the Standard LISP reader has an ERRORSET). MESSAGE is placed + in the global variable \nameref{emsg*} and the error number becomes + the value of the surrounding ERRORSET. \nameref{fluid} variables and + local bindings are unbound to return to the environment + of the ERRORSET. Global variables are not affected by the + process. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{errorset} +\index{error handling} +\begin{verbatim} +ERRORSET(U:any, MSGP:boolean, TR:boolean):any eval, spread +\end{verbatim} + If an error occurs during the evaluation of U, the value + of NUMBER from the \nameref{error} call is returned as the value of + ERRORSET. In addition, if the value of MSGP is non-NIL, + the MESSAGE from the ERROR call is displayed upon both the + standard output device and the currently selected output + device unless the standard output device is not open. The + message appears prefixed with 5 asterisks. The MESSAGE list + is displayed without top level parentheses. The MESSAGE + from the ERROR call will be available in the global variable + \nameref{emsg*}. The exact format of error messages generated by + Standard LISP functions described in this document are not + fixed and should not be relied upon to be in any particular + form. Likewise, error numbers generated by Standard LISP + functions are implementation dependent. + If no error occurs during the evaluation of U, the value of + (LIST (EVAL U)) is returned. + + If an error has been signaled and the value of TR is non-NIL + a traceback sequence will be initiated on the selected output + device. The traceback will display information such as + unbindings of \nameref{fluid} variables, argument lists and so on in an + implementation dependent format. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Functions for Vectors} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{getv} +\index{vector} +\begin{verbatim} +GETV(V:vector, INDEX:integer):any eval, spread +\end{verbatim} + Returns the value stored at position INDEX of the \nameref{vector} V. + The type mismatch error may occur. An error occurs if the + INDEX does not lie within 0... UPBV(V) inclusive: +\begin{verbatim} + ***** INDEX subscript is out of range +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{mkvect} +\index{vector} +\begin{verbatim} +MKVECT(UPLIM:integer):vector eval, spread +\end{verbatim} + Defines and allocates space for a \nameref{vector} with UPLIM+1 + elements accessed as 0... UPLIM. Each element is initialized + to NIL. An error will occur if UPLIM is < 0 or there is not + enough space for a vector of this size: +\begin{verbatim} + ***** A vector of size UPLIM cannot be allocated +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{putv} +\index{vector} +\begin{verbatim} +PUTV(V:vector, INDEX:integer, VALUE:any):any eval, spread +\end{verbatim} + Stores VALUE into the \nameref{vector} V at position INDEX. VALUE is + returned. The type mismatch error may occur. If INDEX does + not lie in 0... UPBV(V) an error occurs: +\begin{verbatim} + ***** INDEX subscript is out of range +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{upbv} +\index{vector} +\begin{verbatim} +UPBV(U:any):NIL,integer eval, spread +\end{verbatim} + Returns the upper limit of U if U is a \nameref{vector}, or NIL if it + is not. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{Boolean Functions, Conditionals} + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{and} +\index{boolean} +\begin{verbatim} +AND([U:any]):extra-boolean noeval, nospread +\end{verbatim} + AND evaluates each U until a value of NIL is found or the end + of the list is encountered. If a non-NIL value is the last + value it is returned, or NIL is returned. +\begin{verbatim} + + FEXPR PROCEDURE AND(U); + BEGIN + IF NULL U THEN RETURN NIL; + LOOP: IF NULL CDR U THEN RETURN EVAL CAR U + ELSE IF NULL EVAL CAR U THEN RETURN NIL; + U := CDR U; + GO LOOP + END; +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{cond} +\index{boolean} +\begin{verbatim} +COND([U:cond-form]):any noeval, nospread +\end{verbatim} + The antecedents of all U's (\nameref{cond-form}s) are evaluated in order of their + appearance until a non-NIL value is encountered. The + consequent of the selected U is evaluated and becomes the + value of the COND. The consequent may also contain the + special functions \nameref{go} and \nameref{return} subject to the restraints + given for these functions. In these cases COND does not have + a defined value, but rather an effect. If no antecedent is + non-NIL the value of COND is NIL. An error is detected if a U + is improperly formed: +\begin{verbatim} + ***** Improper cond-form as argument of COND +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{not} +\index{boolean} +\begin{verbatim} +NOT(U:any):boolean eval, spread +\end{verbatim} + If U is NIL, return T else return NIL (same as function + NULL). +\begin{verbatim} + + EXPR PROCEDURE NOT(U); + U EQ NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{or} +\index{boolean} +\begin{verbatim} +OR([U:any]):extra-boolean noeval, nospread +\end{verbatim} + U is any number of expressions which are evaluated in order + of their appearance. When one is found to be non-NIL it is + returned as the value of OR. If all are NIL, NIL is returned. +\begin{verbatim} + + FEXPR PROCEDURE OR(U); + BEGIN SCALAR X; + LOOP: IF NULL U THEN RETURN NIL + ELSE IF (X := EVAL CAR U) THEN RETURN X; + U := CDR U; + GO LOOP + END; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{Arithmetic Functions} +\begin{Introduction}{Conversion} +\index{mixed-mode arithmetic} +Conversions between numeric types are provided explicitly by the +\nameref{fix} and \nameref{float} functions and implicitly by any +multi-parameter arithmetic function which receives mixed types of arguments. A +conversion from fixed to floating point numbers may result in a loss +of precision without a warning message being generated. Since +integers may have a greater magnitude that that permitted for floating +numbers, an error may be signaled when the attempted conversion cannot +be done. + + Because the magnitude of integers is unlimited the conversion +of a floating point number to a fixed number is always possible, the +only loss of precision being the digits to the right of the decimal +point which are truncated. If a function receives mixed types of +arguments the general rule will have the fixed numbers converted to +floating before arithmetic operations are performed. In all cases an +error occurs if the parameter to an arithmetic function is not a +number: +\begin{verbatim} +\errormessage{***** XXX parameter to FUNCTION is not a number} +\end{verbatim} +XXX is the value of the parameter at fault and FUNCTION is the name of +the function that detected the error. Exceptions to the rule are noted +where they occur. +\end{Introduction} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{abs} +\index{arithmetic} +\begin{verbatim} +ABS(U:number):number eval, spread +\end{verbatim} + Returns the absolute value of its argument. +\begin{verbatim} + + EXPR PROCEDURE ABS(U); + IF LESSP(U, 0) THEN MINUS(U) ELSE U; +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{add1} +\index{arithmetic} +\begin{verbatim} +ADD1(U:number):number eval, spread +\end{verbatim} + Returns the value of U plus 1 of the same type as U (fixed or + floating). +\begin{verbatim} + + EXPR PROCEDURE ADD1(U); + PLUS2(U, 1); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{difference} +\index{arithmetic} +\begin{verbatim} +DIFFERENCE(U:number, V:number):number eval, spread +\end{verbatim} + The value U - V is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{divide} +\index{arithmetic} +\begin{verbatim} +DIVIDE(U:number, V:number):dotted-pair eval, spread +\end{verbatim} + The dotted-pair (quotient . remainder) is returned. The + quotient part is computed the same as by QUOTIENT and the + remainder the same as by REMAINDER. An error occurs if + division by zero is attempted: +\begin{verbatim} + ***** Attempt to divide by 0 in DIVIDE +\end{verbatim} +\begin{verbatim} + + EXPR PROCEDURE DIVIDE(U, V); + (QUOTIENT(U, V) . REMAINDER(U, V)); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{expt} +\index{arithmetic} +\begin{verbatim} +EXPT(U:number, V:integer):number eval, spread +\end{verbatim} + Returns U raised to the V power. A floating point U to an + integer power V does not have V changed to a floating number + before exponentiation. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{fix} +\index{arithmetic} +\begin{verbatim} +FIX(U:number):integer eval, spread +\end{verbatim} + Returns an integer which corresponds to the truncated value + of U. The result of conversion must retain all significant + portions of U. If U is an integer it is returned unchanged. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{float} +\index{arithmetic} +\begin{verbatim} +FLOAT(U:number):floating eval, spread +\end{verbatim} + The floating point number corresponding to the value of the + argument U is returned. Some of the least significant + digits of an integer may be lost do to the implementation of + floating point numbers. FLOAT of a floating point number + returns the number unchanged. If U is too large to represent + in floating point an error occurs: +\begin{verbatim} + ***** Argument to FLOAT is too large +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{greaterp} +\index{arithmetic}\index{boolean} +\begin{verbatim} +GREATERP(U:number, V:number):boolean eval, spread +\end{verbatim} + Returns T if U is strictly greater than V, otherwise returns + NIL. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{lessp} +\index{arithmetic}\index{boolean} +\begin{verbatim} +LESSP(U:number, V:number):boolean eval, spread +\end{verbatim} + Returns T if U is strictly less than V, otherwise returns + NIL. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{max} +\index{arithmetic} +\begin{verbatim} +MAX([U:number]):number noeval, nospread, or macro +\end{verbatim} + Returns the largest of the values in U. If two or more values + are the same the first is returned. +\begin{verbatim} + MACRO PROCEDURE MAX(U); + EXPAND(CDR U, 'MAX2); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{max2} +\index{arithmetic} +\begin{verbatim} +MAX2(U:number, V:number):number eval, spread +\end{verbatim} + Returns the larger of U and V. If U and V are the same value + U is returned (U and V might be of different types). +\begin{verbatim} + + EXPR PROCEDURE MAX2(U, V); + IF LESSP(U, V) THEN V ELSE U; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{min} +\index{arithmetic} +\begin{verbatim} +MIN([U:number]):number noeval, nospread, or macro +\end{verbatim} + Returns the smallest of the values in U. If two or more + values are the same the first of these is returned. +\begin{verbatim} + MACRO PROCEDURE MIN(U); + EXPAND(CDR U, 'MIN2); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{min2} +\index{arithmetic} +\begin{verbatim} +MIN2(U:number, V:number):number eval, spread +\end{verbatim} + Returns the smaller of its arguments. If U and V are the + same value, U is returned (U and V might be of different + types). +\begin{verbatim} + + EXPR PROCEDURE MIN2(U, V); + IF GREATERP(U, V) THEN V ELSE U; +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{minus} +\index{arithmetic} +\begin{verbatim} +MINUS(U:number):number eval, spread +\end{verbatim} + Returns -U. +\begin{verbatim} + + EXPR PROCEDURE MINUS(U); + DIFFERENCE(0, U); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{plus} +\index{arithmetic} +\begin{verbatim} +PLUS([U:number]):number noeval, nospread, or macro +\end{verbatim} + Forms the sum of all its arguments. +\begin{verbatim} + MACRO PROCEDURE PLUS(U); + EXPAND(CDR U, 'PLUS2); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{plus2} +\index{arithmetic} +\begin{verbatim} +PLUS2(U:number, V:number):number eval, spread +\end{verbatim} + Returns the sum of U and V. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{quotient} +\index{arithmetic} +\begin{verbatim} +QUOTIENT(U:number, V:number):number eval, spread +\end{verbatim} + The quotient of U divided by V is returned. Division of + two positive or two negative integers is conventional. When + both U and V are integers and exactly one of them is negative + the value returned is the negative truncation of the absolute + value of U divided by the absolute value of V. An error + occurs if division by zero is attempted: +\begin{verbatim} + ***** Attempt to divide by 0 in QUOTIENT +\end{verbatim} + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{remainder} +\index{arithmetic} +\begin{verbatim} +REMAINDER(U:number, V:number):number eval, spread +\end{verbatim} + If both U and V are integers the result is the integer + remainder of U divided by V. If either parameter is floating + point, the result is the difference between U and V*(U/V) + all in floating point. If either number is negative the + remainder is negative. If both are positive or both are + negative the remainder is positive. An error occurs if V is + zero: +\begin{verbatim} + ***** Attempt to divide by 0 in REMAINDER +\end{verbatim} +\begin{verbatim} + + EXPR PROCEDURE REMAINDER(U, V); + DIFFERENCE(U, TIMES2(QUOTIENT(U, V), V)); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{sub1} +\index{arithmetic} +\begin{verbatim} +SUB1(U:number):number eval, spread +\end{verbatim} + Returns the value of U less 1. If U is a FLOAT type number, + the value returned is U less 1.0. +\begin{verbatim} + + EXPR PROCEDURE SUB1(U); + DIFFERENCE(U, 1); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{times} +\index{arithmetic} +\begin{verbatim} +TIMES([U:number]):number noeval, nospread, or macro +\end{verbatim} + Returns the product of all its arguments. +\begin{verbatim} + MACRO PROCEDURE TIMES(U); + EXPAND(CDR U, 'TIMES2); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{times2} +\index{arithmetic} +\begin{verbatim} +TIMES2(U:number, V:number):number eval, spread +\end{verbatim} + Returns the product of U and V. +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + +\section{MAP Composite Functions} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{map} +\begin{verbatim} +MAP(X:list, FN:function):any eval, spread +\end{verbatim} + Applies FN to successive CDR segments of X. NIL is returned. +\begin{verbatim} + + EXPR PROCEDURE MAP(X, FN); + WHILE X DO << FN X; X := CDR X >>; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{mapc} +\begin{verbatim} +MAPC(X:list, FN:function):any eval, spread +\end{verbatim} + FN is applied to successive CAR segments of list X. NIL is + returned. +\begin{verbatim} + EXPR PROCEDURE MAPC(X, FN); + WHILE X DO << FN CAR X; X := CDR X >>; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{mapcan} +\begin{verbatim} +MAPCAN(X:list, FN:function):any eval, spread +\end{verbatim} + A concatenated list of FN applied to successive CAR elements + of X is returned. +\begin{verbatim} + EXPR PROCEDURE MAPCAN(X, FN); + IF NULL X THEN NIL + ELSE NCONC(FN CAR X, MAPCAN(CDR X, FN)); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{mapcar} +\begin{verbatim} +MAPCAR(X:list, FN:function):any eval, spread +\end{verbatim} + Returned is a constructed list of FN applied to each CAR of + list X. +\begin{verbatim} + EXPR PROCEDURE MAPCAR(X, FN); + IF NULL X THEN NIL + ELSE FN CAR X . MAPCAR(CDR X, FN); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{mapcon} +\begin{verbatim} +MAPCON(X:list, FN:function):any eval, spread +\end{verbatim} + Returned is a concatenated list of FN applied to successive + CDR segments of X. +\begin{verbatim} + EXPR PROCEDURE MAPCON(X, FN); + IF NULL X THEN NIL + ELSE NCONC(FN X, MAPCON(CDR X, FN)); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{maplist} +\begin{verbatim} +MAPLIST(X:list, FN:function):any eval, spread +\end{verbatim} + Returns a constructed list of FN applied to successive CDR + segments of X. +\begin{verbatim} + EXPR PROCEDURE MAPLIST(X, FN); + IFNULL X THEN NIL + ELSE FN X . MAPLIST(CDR X, FN); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Composite Functions} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{apend} +\begin{verbatim} +APPEND(U:list, V:list):list eval, spread +\end{verbatim} + Returns a constructed list in which the last element of U is + followed by the first element of V. The list U is copied, V + is not. +\begin{verbatim} + EXPR PROCEDURE APPEND(U, V); + IF NULL U THEN V + ELSE CAR U . APPEND(CDR U, V); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{assoc} +\begin{verbatim} +ASSOC(U:any, V:alist):{dotted-pair, NIL} eval, spread +\end{verbatim} + If U occurs as the CAR portion of an element of the \nameref{alist} V, + the dotted-pair in which U occurred is returned, else NIL is + returned. ASSOC might not detect a poorly formed alist so an + invalid construction may be detected by CAR or CDR. +\begin{verbatim} + EXPR PROCEDURE ASSOC(U, V); + IF NULL V THEN NIL + ELSE IF ATOM CAR V THEN + ERROR(000, LIST(V, "is a poorly formed alist")) + ELSE IF U = CAAR V THEN CAR V + ELSE ASSOC(U, CDR V); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{deflist} +\begin{verbatim} +DEFLIST(U:dlist, IND:id):list eval, spread +\end{verbatim} + A "dlist" is a list in which each element is a two element + list: (ID:id PROP:any). Each ID in U has the indicator + IND with property PROP placed on its property list by the + PUT function. The value of DEFLIST is a list of the first + elements of each two element list. Like \nameref{put}, DEFLIST may not + be used to define functions. +\begin{verbatim} + EXPR PROCEDURE DEFLIST(U, IND); + IF NULL U THEN NIL + ELSE << PUT(CAAR U, IND, CADAR U); + CAAR U >> . DEFLIST(CDR U, IND); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{delete} +\begin{verbatim} +DELETE(U:any, V:list):list eval, spread +\end{verbatim} + Returns V with the first top level occurrence of U removed + from it. +\begin{verbatim} + EXPR PROCEDURE DELETE(U, V); + IF NULL V THEN NIL + ELSE IF CAR V = U THEN CDR V + ELSE CAR V . DELETE(U, CDR V); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{digit} +\begin{verbatim} +DIGIT(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a digit, otherwise NIL. +\begin{verbatim} + EXPR PROCEDURE DIGIT(U); + IF MEMQ(U, '(!0 !1 !2 !3 !4 !5 !6 !7 !8 !9)) + THEN T ELSE NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{length} +\begin{verbatim} +LENGTH(X:any):integer eval, spread +\end{verbatim} + The top level length of the list X is returned. +\begin{verbatim} + EXPR PROCEDURE LENGTH(X); + IF ATOM X THEN 0 + ELSE PLUS(1, LENGTH CDR X); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{liter} +\begin{verbatim} +LITER(U:any):boolean eval, spread +\end{verbatim} + Returns T if U is a character of the alphabet, NIL + otherwise. +\begin{verbatim} + EXPR PROCEDURE LITER(U); + IF MEMQ(U, '(!A !B !C !D !E !F !G !H !I !J !K !L !M + !N !O !P !Q !R !S !T !U !V !W !X !Y !Z + !a !b !c !d !e !f !g !h !i !j !k !l !m + !n !o !p !q !r !s !t !u !v !w !x !y !z)) +\end{verbatim} + The published report omits escape characters. These are + required for both upper and lower case as some systems + default to lower. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{member} +\begin{verbatim} +MEMBER(A:any, B:list):extra-boolean eval, spread +\end{verbatim} + Returns NIL if A is not a member of list B, returns the + remainder of B whose first element is A. +\begin{verbatim} + EXPR PROCEDURE MEMBER(A, B); + IF NULL B THEN NIL + ELSE IF A = CAR B THEN B + ELSE MEMBER(A, CDR B); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{memq} +\begin{verbatim} +MEMQ(A:any, B:list):extra-boolean eval, spread +\end{verbatim} + Same as \nameref{member} but an \nameref{eq} check is used for comparison. +\begin{verbatim} + EXPR PROCEDURE MEMQ(A, B); + IF NULL B THEN NIL + ELSE IF A EQ CAR B THEN B + ELSE MEMQ(A, CDR B); +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{nconc} +\begin{verbatim} +NCONC(U:list, V:list):list eval, spread +\end{verbatim} + Concatenates V to U without copying U. The last CDR of U is + modified to point to V. +\begin{verbatim} + EXPR PROCEDURE NCONC(U, V); + BEGIN SCALAR W; + IF NULL U THEN RETURN V; + W := U; + WHILE CDR W DO W := CDR W; + RPLACD(W, V); + RETURN U + END; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{pair} +\begin{verbatim} +PAIR(U:list, V:list):alist eval, spread +\end{verbatim} + U and V are lists which must have an identical number of + elements. If not, an error occurs (the 000 used in the \nameref{error} + call is arbitrary and need not be adhered to). Returned is a + list where each element is a dotted-pair, the CAR of the pair + being from U, and the CDR the corresponding element from V. +\begin{verbatim} + EXPR PROCEDURE PAIR(U, V); + IF AND(U, V) THEN (CAR U . CAR V) . PAIR(CDR U, CDR V) + ELSE IF OR(U, V) THEN ERROR(000, + "Different length lists in PAIR") + ELSE NIL; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{reverse} +\begin{verbatim} +REVERSE(U:list):list eval, spread +\end{verbatim} + Returns a copy of the top level of U in reverse order. +\begin{verbatim} + EXPR PROCEDURE REVERSE(U); + BEGIN SCALAR W; + WHILE U DO << W := CAR U . W; + U := CDR U >>; + RETURN W + END; +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{sassoc} +\begin{verbatim} +SASSOC(U:any, V:alist, FN:function):any eval, spread +\end{verbatim} + Searches the \nameref{alist} V for an occurrence of U. If U is not in + the alist the evaluation of function FN is returned. +\begin{verbatim} + EXPR PROCEDURE SASSOC(U, V, FN); + IF NULL V THEN FN() + ELSE IF U = CAAR V THEN CAR V + ELSE SASSOC(U, CDR V, FN); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{sublis} +\index{substitution} +\begin{verbatim} +SUBLIS(X:alist, Y:any):any eval, spread +\end{verbatim} + The value returned is the result of substituting the CDR of + each element of the alist X for every occurrence of the CAR + part of that element in Y. +\begin{verbatim} + EXPR PROCEDURE SUBLIS(X, Y); + IF NULL X THEN Y + ELSE BEGIN SCALAR U; + U := ASSOC(Y, X); + RETURN IF U THEN CDR U + ELSE IF ATOM Y THEN Y + ELSE SUBLIS(X, CAR Y) . + SUBLIS(X, CDR Y) + END; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{subst} +\index{substitution} +\begin{verbatim} +SUBST(U:any, V:any, W:any):any eval, spread +\end{verbatim} + The value returned is the result of substituting U for all + occurrences of V in W. +\begin{verbatim} + EXPR PROCEDURE SUBST(U, V, W); + IF NULL W THEN NIL + ELSE IF V = W THEN U + ELSE IF ATOM W THEN W + ELSE SUBST(U, V, CAR W) . SUBST(U, V, CDR W); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + +\section{Interpreter} + + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{apply} +\begin{verbatim} +APPLY(FN:{id,function}, ARGS:any-list):any eval, spread +\end{verbatim} + APPLY returns the value of FN with actual parameters + ARGS. The actual parameters in ARGS are already in the + form required for binding to the formal parameters of FN. + Implementation specific portions described in English are + enclosed in boxes. +\begin{verbatim} + EXPR PROCEDURE APPLY(FN, ARGS); + BEGIN SCALAR DEFN; + IF--------------------------------------------- + -Spread the actual parameters in ARGS- + -following the conventions: for calling- + -functions, transfer to the entry point of; + - - + -the function, and return the value returned- + ---------------------------------------------- + IF IDP FN THEN RETURN + IF NULL(DEFN := GETD FN) THEN + ERROR(000, LIST(FN, "is an undefined function")) + ELSE IF CAR DEFN EQ 'EXPR THEN + APPLY(CDR DEFN, ARGS) + + ELSE ERROR(000, + LIST(FN, "cannot be evaluated by APPLY")); + IF OR(ATOM FN, NOT(CAR FN EQ 'LAMBDA)) THEN + ERROR(000, + LIST(FN, "cannot be evaluated by APPLY")); + RETURN + -Bind-the--actual-parameters--in-ARGS--to-the- + - - + -formal parameters of the lambda expression.- + -If the two lists are not of equal length- + -then ERROR(000, "Number of parameters do not- + -match"); The value returned is EVAL CADDR- + ---------------------------------------------- + END; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{eval} +\begin{verbatim} +EVAL(U:any):any eval, spread +\end{verbatim} + The value of the expression U is computed. Error numbers + are arbitrary. Portions of EVAL involving machine specific + coding are expressed in English enclosed in boxes. +\begin{verbatim} + EXPR PROCEDURE EVAL(U); + BEGIN SCALAR FN; + IF CONSTANTP U THEN RETURN U; + IF IDP U THEN RETURN + -U-is-an-id.--Return-the-value-most-currently- + -bound to U or if there is no such binding:- + - - + ---------------------------------------------- + IF PAIRP CAR U THEN RETURN + IF CAAR U EQ 'LAMBDA THEN APPLY(CAR U, EVLIS CDR U) + ELSE ERROR(000, LIST(CAR U, + "improperly formed LAMBDA expression")) + ELSE IF CODEP CAR U THEN + RETURN APPLY(CAR U, EVLIS CDR U); + + FN := GETD CAR U; + IF NULL FN THEN + ERROR(000, LIST(CAR U, "is an undefined function")) + ELSE IF CAR FN EQ 'EXPR THEN + RETURN APPLY(CDR FN, EVLIS CDR U) + ELSE IF CAR FN EQ 'FEXPR THEN + RETURN APPLY(CDR FN, LIST CDR U) + ELSE IF CAR FN EQ 'MACRO THEN + RETURN EVAL APPLY(CDR FN, LIST U) + END; +\end{verbatim} +see also \nameref{constantp}, \nameref{idp}, \nameref{pairp}, +\nameref{evlis}, nameref{apply}, nameref{getd} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{evlis} +\begin{verbatim} +EVLIS(U:any-list):any-list eval, spread +\end{verbatim} + EVLIS returns a list of the evaluation of each element of U. +\begin{verbatim} + EXPR PROCEDURE EVLIS(U); + IF NULL U THEN NIL + ELSE EVAL CAR U . EVLIS CDR U; +\end{verbatim} +see also \nameref{eval} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{expand} +\index{macro} +\begin{verbatim} +EXPAND(L:list, FN:function):list eval, spread +\end{verbatim} + FN is a defined function of two arguments to be used in the + expansion of a \name{macro} defined by \nameref{dm}. EXPAND returns a list in the form: +\begin{verbatim} + (FN L (FN L ...(FN L L ) ... )) + 0 1 n-1 n +\end{verbatim} + where n is the number of elements in L, Li is the ith element + of L. +\begin{verbatim} + EXPR PROCEDURE EXPAND(L,FN); + IF NULL CDR L THEN CAR L + ELSE LIST(FN, CAR L, EXPAND(CDR L, FN)); +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{function} +\begin{verbatim} +FUNCTION(FN:function):function noeval, nospread +\end{verbatim} + The function FN is to be passed to another function. If + FN is to have side effects its free variables must be \nameref{fluid} + or \nameref{global}. FUNCTION is like \nameref{quote} but its argument may be + affected by compilation. We do not consider \nameindex{FUNARG}s in this + report. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{quote} +\begin{verbatim} +QUOTE(U:any):any noeval, nospread +\end{verbatim} + Stops evaluation and returns U unevaluated. +\begin{verbatim} + FEXPR PROCEDURE QUOTE(U); + CAR U; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{Input and Output} +\begin{Introduction}{IO} +The user normally communicates with Standard LISP through +\nameindex{standard devices}. The default devices are selected in accordance +with the conventions of the implementation site. Other input and +output devices or files may be selected for reading and writing using +the functions described herein. +\end{Introduction} + + +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{close} +\begin{verbatim} +CLOSE(FILEHANDLE:any):any eval, spread +\end{verbatim} + Closes the file with the internal name FILEHANDLE writing + any necessary end of file marks and such. The value of + FILEHANDLE is that returned by the corresponding OPEN. The + value returned is the value of FILEHANDLE. An error occurs if + the file can not be closed. +\begin{verbatim} + ***** FILEHANDLE could not be closed +\end{verbatim} + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{eject} +\begin{verbatim} +EJECT():NIL eval, spread +\end{verbatim} + Skip to the top of the next output page. Automatic EJECTs + are executed by the print functions when the length set by + the \nameref{pagelength} function is exceeded. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{linelength} +\begin{verbatim} +LINELENGTH(LEN:{integer, NIL}):integer eval, spread +\end{verbatim} + If LEN is an integer the maximum line length to be printed + before the print functions initiate an automatic nameref{terpri} is + set to the value LEN. No initial Standard LISP line length is + assumed. The previous line length is returned except when + LEN is NIL. This special case returns the current line length + and does not cause it to be reset. An error occurs if the + requested line length is too large for the currently selected + output file or LEN is negative or zero. +\begin{verbatim} + ***** LEN is an invalid line length +\end{verbatim} + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{lposn} +\begin{verbatim} +LPOSN():integer eval, spread +\end{verbatim} + Returns the number of lines printed on the current page. At + the top of a page, 0 is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{open} +\index{input}\index{output} +\begin{verbatim} +OPEN(FILE:any, HOW:id):any eval, spread +\end{verbatim} + Open the file with the system dependent name FILE for output + if HOW is \nameref{eq} to OUTPUT, or input if HOW is \name{eq} to INPUT. If + the file is opened successfully, a value which is internally + associated with the file is returned. This value must be + saved for use by \nameref{wrs} and \nameref{rds}. An error occurs if HOW is + something other than INPUT or OUTPUT or the file can't be + opened. +\begin{verbatim} + ***** HOW is not option for OPEN + ***** FILE could not be opened +\end{verbatim} +Use the \nameref{close} function to close a file. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{pagelength} +\begin{verbatim} +PAGELENGTH(LEN:{integer, NIL}):integer eval, spread +\end{verbatim} + Sets the vertical length (in lines) of an output page. + Automatic page \nameref{eject}s are executed by the print functions + when this length is reached. The initial vertical length + is implementation specific. The previous page length is + returned. If LEN is 0, no automatic page ejects will + occur. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{posn} +\begin{verbatim} +POSN():integer eval, spread +\end{verbatim} + Returns the number of characters in the output buffer. When + the buffer is empty, 0 is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{princ} +\begin{verbatim} +PRINC(U:id):id eval, spread +\end{verbatim} + U must be a single character id such as produced by \nameref{explode} + or read by \nameref{readch} or the value of \nameref{$eol$}. The effect is + the character U displayed upon the currently selected output + device. The value of \name{!$EOL!$} causes termination of the + current line like a call to \nameref{terpri}. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{print} +\begin{verbatim} +PRINT(U:any):any eval, spread +\end{verbatim} + Displays U in \nameref{read} readable format and terminates the print + line. The value of U is returned. +\begin{verbatim} + EXPR PROCEDURE PRINT(U); + << PRIN1 U; TERPRI(); U >>; +\end{verbatim} +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{prin1} +\begin{verbatim} +PRIN1(U:any):any eval, spread +\end{verbatim} + U is displayed in a \nameref{read} readable form. The format + of display is the result of \nameref{explode} expansion; special + characters are prefixed with the escape character !, and + strings are enclosed in "... ". Lists are displayed in + list-notation and vectors in vector-notation. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{prin2} +\begin{verbatim} +PRIN2(U:any):any eval, spread +\end{verbatim} + U is displayed upon the currently selected print device + but output is not \nameref{read} readable. The value of U is + returned. Items are displayed as described in the \nameref{explode} + function with the exceptions that the escape character does + not prefix special characters and strings are not enclosed in + "... ". Lists are displayed in list-notation and vectors in + vector-notation. The value of U is returned. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{rds} +\begin{verbatim} +RDS(FILEHANDLE:any):any eval, spread +\end{verbatim} + Input from the currently selected input file is suspended + and further input comes from the file named. FILEHANDLE is + a system dependent internal name which is a value returned + by \nameref{open}. If FILEHANDLE is NIL the standard input device is + selected. When end of file is reached on a non-standard + input device, the standard input device is reselected. When + end of file occurs on the standard input device the Standard + LISP reader terminates. RDS returns the internal name of the + previously selected input file. +\begin{verbatim} + ***** FILEHANDLE could not be selected for input +\end{verbatim} +The function name RDS goes back to "read select"; +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{read} +\begin{verbatim} +READ():any +\end{verbatim} + The next expression from the file currently selected for + input. Valid input forms are: vector-notation, dot- + notation, list-notation, numbers, function-pointers, strings, + and identifiers with escape characters. Identifiers are + interned on the \name{oblist} (see \nameref{intern}) + READ returns the + value of \nameref{\$eof\$} when the end of the currently selected input + file is reached. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{readch} +\begin{verbatim} +READCH():id +\end{verbatim} + Returns the next interned character from the file currently + selected for input. Two special cases occur. If all the + characters in an input record have been read, the value of + \nameref{\$eol\$} is returned. If the file selected for input has + all been read the value of \nameref{\$eof\$} is returned. Comments + delimited by % and end-of-line are not transparent to \nameref{readch}. + + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{terpri} +\begin{verbatim} +TERPRI():NIL +\end{verbatim} + The current print line is terminated. The following output + begins on a new line. + +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +\begin{Function}{wrs} +\begin{verbatim} +WRS(FILEHANDLE:any):any eval, spread +\end{verbatim} + Output to the currently active output file is suspended and + further output is directed to the file named. FILEHANDLE is + an internal name which is returned by \nameref{open}. The file named + must have been opened for output. If FILEHANDLE is NIL the + standard output device is selected. WRS returns the internal + name of the previously selected output file. +\begin{verbatim} + ***** FILEHANDLE could not be selected for output +\end{verbatim} +The function name WRS goes back to "write select". +\end{Function} +%- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + +\section{LISP Reader} +\begin{Introduction}{LISP Reader} +An EVAL read loop has been chosen to drive a Standard LISP system to +provide a continuity in functional syntax. Choices of messages and the +amount of extra information displayed are decisions left to the +implementor. +\end{Introduction} + +\begin{Function}{quit} +\begin{verbatim} +QUIT() +\end{verbatim} +Causes termination of the LISP reader and control to be transferred +to the operating system. +\end{Function} + +\section{System GLOBAL Variables} + + +\begin{Variable}{*comp} +\index{expr} +The value of the global variable !*comp controls whether or not +\nameref{putd} compiles the +function defined in its arguments before defining it. If !*comp is NIL +the function is defined as an \name{expr}. If !*comp is something else the +function is first compiled. Compilation will produce certain changes +in the semantics of functions particularly \nameref{fluid} type access. +\end{Variable} + + +\begin{Variable}{emsg*} +Will contain the MESSAGE generated by the last \nameref{error} call. +\end{Variable} + + +\begin{Variable}{$eof$} +The value of !\$eof!\$ is returned by all input functions when the +end \index{end of file} +of the currently selected input file is reached. +\end{Variable} + + +\begin{Variable}{$eol$} +The value of !\$eol!\$ is returned by \nameref{readch} when it reaches the end +of \name{readch} \index{end of line} +a logical input record. Likewise \nameref{princ} will terminate its current line +(like a call to \nameref{terpri}) when !\$eol!\$ is its argument. +\end{Variable} + +\begin{Variable}{*gc} +\index{garbage collector} +!*gc controls the printing of garbage collector messages. If NIL no +indication of garbage collection may occur. If non-NIL various system +dependent messages may be displayed. +\end{Variable} + + +\begin{Variable}{nil} +\name{nil} is a special global variable. It is protected from being modified +by \nameref{set} or \nameref{setq}. Its value is \name{nil}. +\end{Variable} + +\begin{Variable}{*raise} +If \name{!*raise} is non-NIL all characters input through Standard LISP +input/output functions will be raised to upper case. If \name{!*RAISE} is NIL +characters will be input as is. +\end{Variable} + + +\begin{Variable}{t} +\name{t} is a special global variable. It is protected from being modified +by \nameref{set} or \nameref{setq}. Its value is \name{t}. +\end{Variable} + +\end{document} Index: r36/help/switch.tex ================================================================== --- r36/help/switch.tex +++ r36/help/switch.tex @@ -1,1750 +1,1750 @@ -\section{General Switches} - -\begin{Introduction}{SWITCHES} -Switches are set on or off using the commands \nameref{on} or -\nameref{off}, respectively. -The default setting of the switches described in this section is -\nameref{off} unless stated otherwise. -\end{Introduction} - -\begin{Switch}{ALGINT} -\index{integration} -When the \name{algint} switch is on, the algebraic integration module (which -must be loaded from the REDUCE library) is used for integration. - -\begin{Comments} -Loading \name{algint} from the library automatically turns on the -\name{algint} switch. An error message will be given if \name{algint} is -turned on when the \name{algint} has not been loaded from the library. -\end{Comments} -\end{Switch} - - -\begin{Switch}{ALLBRANCH} -When \name{allbranch} is on, the operator \nameref{solve} selects all -branches of solutions. -When \name{allbranch} is off, it selects only the principal -branches. Default is \name{on}. - -\begin{Examples} - -solve(log(sin(x+3)),x); & -\begin{multilineoutput}{6cm} -\{X=2*ARBINT(1)*PI - ASIN(1) - 3, - X=2*ARBINT(1)*PI + ASIN(1) + PI - 3\} -\end{multilineoutput}\\ -off allbranch; \\ -solve(log(sin(x+3)),x); & - {X=ASIN(1) - 3} -\end{Examples} - -\begin{Comments} -\nameref{arbint}(1) indicates an arbitrary integer, which is given a -unique identifier by REDUCE, showing that there are infinitely many -solutions of this type. When \name{allbranch} is off, the single -canonical solution is given. -\end{Comments} -\end{Switch} - - -\begin{Switch}{ALLFAC} -\index{output} -The \name{allfac} switch, when on, causes REDUCE to factor out automatically -common products in the output of expressions. Default is \name{on}. - -\begin{Examples} -x + x*y**3 + x**2*cos(z); & X*(COS(Z)*X + Y^{3} + 1) \\ -off allfac; \\ -x + x*y**3 + x**2*cos(z); & COS(Z)*X^{2} + X*Y^{3} + X -\end{Examples} - -\begin{Comments} -The \name{allfac} switch has no effect when \name{pri} is off. Although the -switch setting stays as it was, printing behavior is as if it were off. -\end{Comments} -\end{Switch} - - -% \begin{Switch}{ALLPREC} -% -% \end{Switch} -% -% -\begin{Switch}{ARBVARS} -\index{solve} -When \name{arbvars} is on, the solutions of singular or underdetermined -systems of equations are presented in terms of arbitrary complex variables -(see \nameref{arbcomplex}). Otherwise, the solution is parametrized in -terms of some of the input variables. Default is \name{on}. - -\begin{Examples} -solve({2x + y,4x + 2y},{x,y}); & - \{\{x= - \rfrac{arbcomplex(1)}{2},y=arbcomplex(1)\}\} \\ -solve({sqrt(x)+ y**3-1},{x,y}); & - \{\{y=arbcomplex(2),x=y^6 - 2*y^3 + 1\}\} \\ -off arbvars; \\ -solve({2x + y,4x + 2y},{x,y}); & - \{\{x= - \rfrac{y}{2}\}\} \\ -solve({sqrt(x)+ y**3-1},{x,y}); & - \{\{x=y^6 - 2*y^3 + 1\}\} \\ -\end{Examples} -\begin{Comments} - -With \name{arbvars} off, the return value \name{\{\{\}\}} means that the -equations given to \nameref{solve} imply no relation among the input -variables. -\end{Comments} -\end{Switch} - - -\begin{Switch}{BALANCED\_MOD} -\index{modular} -\nameref{modular} numbers are normally produced in the range [0,...\meta{n}), -where -\meta{n} is the current modulus. With \name{balanced\_mod} on, the range -[-\meta{n}/2,\meta{n}/2] is used instead. - -\begin{Examples} -setmod 7; & 1 \\ -on modular; \\ -4; & 4 \\ -on balanced_mod; \\ -4; & -3 -\end{Examples} -\end{Switch} - - -\begin{Switch}{BFSPACE} -\index{output}\index{floating point} -Floating point numbers are normally printed in a compact notation (either -fixed point or in scientific notation if \nameref{SCIENTIFIC\_NOTATION} -has been used). In some (but not all) cases, it helps comprehensibility -if spaces are inserted in the number at regular intervals. The switch -\name{bfspace}, if on, will cause a blank to be inserted in the number after -every five characters. -\begin{Examples} -on rounded; \\ -1.2345678; & 1.2345678 \\ -on bfspace; \\ -1.2345678; & 1.234 5678 -\end{Examples} -\begin{Comments} -\name{bfspace} is normally off. -\end{Comments} -\end{Switch} - - -\begin{Switch}{COMBINEEXPT} -\index{exponent simplification} -REDUCE is in general poor at surd simplification. However, when the -switch \name{combineexpt} is on, the system attempts to combine -exponentials whenever possible. -\begin{TEX} -\begin{Examples} -3^(1/2)*3^(1/3)*3^(1/6); & SQRT(3)*3^{\rfrac{1}{3}}*3^{\rfrac{1}{6}} \\ -on combineexpt; \\ -ws; & 1 -\end{Examples} -\end{TEX} -\begin{INFO} -{\begin{Examples} -3^(1/2)*3^(1/3)*3^(1/6); & SQRT(3)*3^{1/3}*3^{1/6} \\ -on combineexpt; \\ -ws; & 1 -\end{Examples}} -\end{INFO} - -\end{Switch} - - -\begin{Switch}{COMBINELOGS} -\index{logarithm} -In many cases it is desirable to expand product arguments of logarithms, -or collect a sum of logarithms into a single logarithm. Since these are -inverse operations, it is not possible to provide rules for doing both at -the same time and preserve the REDUCE concept of idempotent evaluation. -As an alternative, REDUCE provides two switches \nameref{expandlogs} and -\name{combinelogs} to carry out these operations. -\begin{Examples} -on expandlogs; \\ -log(x*y); & LOG(X) + LOG(Y) \\ -on combinelogs; \\ -ws; & LOG(X*Y) -\end{Examples} - -\begin{Comments} -At the present time, it is possible to have both switches on at once, -which could lead to infinite recursion. However, an expression is -switched from one form to the other in this case. Users should not rely -on this behavior, since it may change in the next release. -\end{Comments} - -\end{Switch} - - -\begin{Switch}{COMP} -\index{compiler} -When \name{comp} is on, any succeeding function definitions are compiled -into a faster-running form. Default is \name{off}. - -\begin{Examples} -\explanation{The following procedure finds Fibonacci numbers recursively. -Create a new file ``refib" in your current directory with the following -lines in it:} \\[6mm] -\begin{multilineinput} -procedure refib(n); - if fixp n and n >= 0 then - if n <= 1 then 1 - else refib(n-1) + refib(n-2) - else rederr "nonnegative integer only"; - -end; -\end{multilineinput}\\ -\explanation{Now load REDUCE and run the following:}\\ -on time; & Time: 100 ms \\ - -in "refib"$ & Time: 0 ms \\ - - & REFIB \\ - - & Time: 260 ms \\ - - & Time: 20 ms \\ - -refib(80); & 37889062373143906 \\ - - & Time: 14840 ms \\ - -on comp; & Time: 80 ms \\ - -in "refib"$ & Time: 20 ms \\ - - & REFIB \\ - - & Time: 640 ms \\ - -refib(80); & 37889062373143906 \\ - - & Time: 10940 ms -\end{Examples} -\begin{Comments} -Note that the compiled procedure runs faster. Your time messages will -differ depending upon which system you have. Compiled functions remain so -for the duration of the REDUCE session, and are then lost. They must be -recompiled if wanted in another session. With the switch \nameref{time} on -as shown above, the CPU time used in executing the command is returned in -milliseconds. Be careful not to leave \name{comp} on unless you want it, -as it makes the processing of procedures much slower. - -\end{Comments} -\end{Switch} - - -\begin{Switch}{COMPLEX} -\index{complex} -When the \name{complex} switch is on, full complex arithmetic is used in -simplification, function evaluation, and factorization. Default is \name{off}. - -\begin{Examples} - -factorize(a**2 + b**2); & \{A^{2} + B^{2} \} \\ -on complex; \\ - -factorize(a**2 + b**2); & \{A - I*B,A + I*B\} \\ - -(x**2 + y**2)/(x + i*y); & X - I*Y \\ - -on rounded; & - - *** Domain mode COMPLEX changed to COMPLEX\_FLOAT \\ - -sqrt(-17); & 4.12310562562*I \\ - -log(7*i); & 1.94591014906 + 1.57079632679*I -\end{Examples} - -\begin{Comments} -Complex floating-point can be done by turning on \nameref{rounded} in -addition to \name{complex}. With \name{complex} off however, REDUCE knows -that \IFTEX{$i$}{i} is the square root of \IFTEX{$-1$}{-1} but will not -carry out more complicated complex operations. If you want complex -denominators cleared by multiplication by their conjugates, turn on the -switch \nameref{rationalize}. -\end{Comments} -\end{Switch} - - -\begin{Switch}{CREF} -\index{cross reference} -The switch \name{cref} invokes the CREF cross-reference program that -processes a set of procedure definitions to produce a summary of their -entry points, undefined procedures, non-local variables and so on. The -program will also check that procedures are called with a consistent -number of arguments, and print a diagnostic message otherwise. - -The output is alphabetized on the first seven characters of each function -name. - -To invoke the cross-reference program, \name{cref} is first turned on. -This causes the program to load and the cross-referencing process to -begin. After all the required definitions are loaded, turning \name{cref} -off will cause a cross-reference listing to be produced. - -\begin{Comments} - -Algebraic procedures in REDUCE are treated as if they were symbolic, so -that algebraic constructs will actually appear as calls to symbolic -functions, such as \name{aeval}. -\end{Comments} - -\end{Switch} - - -\begin{Switch}{CRAMER} -\index{matrix}\index{linear system}\index{solve} -When the \name{cramer} switch is on, \nameref{matrix} inversion -and linear equation -solving (operator \nameref{solve}) is done by Cramer's rule, through exterior -multiplication. Default is \name{off}. - -\begin{Examples} -on time; & Time: 80 ms \\ -off output; & Time: 100 ms \\[4mm] -\begin{multilineinput} -mm := mat((a,b,c,d,f),(a,a,c,f,b),(b,c,a,c,d), (c,c,a,b,f), - (d,a,d,e,f)); -\end{multilineinput} & Time: 300 ms \\ -inverse := 1/mm; & Time: 18460 ms \\ -on cramer; & Time: 80 ms \\ -cramersinv := 1/mm; & Time: 9260 ms -\end{Examples} - -\begin{Comments} -Your time readings will vary depending on the REDUCE version you use. -After you invert the matrix, turn on \nameref{output} and ask for one of -the elements of the inverse matrix, such as \name{cramersinv(3,2)}, so that -you can see the size of the expressions produced. - -Inversion of matrices and the solution of linear equations with dense -symbolic entries in many variables is generally considerably faster with -\name{cramer} on. However, inversion of numeric-valued matrices is -slower. Consider the matrices you're inverting before deciding whether to -turn \name{cramer} on or off. A substantial portion of the time in matrix -inversion is given to formatting the results for printing. To save this -time, turn \name{output} off, as shown in this example or terminate the -expression with a dollar sign instead of a semicolon. The results are -still available to you in the workspace associated with your prompt -number, or you can assign them to an identifier for further use. -\end{Comments} -\end{Switch} - - -\begin{Switch}{DEFN} -\index{lisp} -When the switch \name{defn} is on, the Standard Lisp equivalent of the -input statement or procedure is printed, but not evaluated. Default is -\name{off}. - -\begin{Examples} - -on defn; \\ - -17/3; & (AEVAL (LIST 'QUOTIENT 17 3)) \\ - -df(sin(x),x,2); - & (AEVAL (LIST 'DF (LIST 'SIN 'X) 'X 2)) \\ -\begin{multilineinput} -procedure coshval(a); - begin scalar g; - g := (exp(a) + exp(-a))/2; - return g - end; -\end{multilineinput} & -\begin{multilineoutput}{7cm} -(AEVAL - (PROGN - (FLAG '(COSHVAL) 'OPFN) - (DE COSHVAL (A) - (PROG (G) - (SETQ G - (AEVAL - (LIST - 'QUOTIENT - (LIST - 'PLUS - (LIST 'EXP A) - (LIST 'EXP (LIST 'MINUS A))) - 2))) - (RETURN G)))) ) -\end{multilineoutput} \\ - -coshval(1); & (AEVAL (LIST 'COSHVAL 1)) \\ - -off defn; \\ - -coshval(1); & Declare COSHVAL operator? (Y or N) \\ - -n \\ -\begin{multilineinput} -procedure coshval(a); - begin scalar g; - g := (exp(a) + exp(-a))/2; - return g - end; -\end{multilineinput} & COSHVAL \\ - -on rounded; \\ - -coshval(1); & 1.54308063482 -\end{Examples} - -\begin{Comments} -The above function \name{coshval} finds the hyperbolic cosine (cosh) of its -argument. When \name{defn} is on, you can see the Standard Lisp equivalent -of the function, but it is not entered into the system as shown by the -message \name{Declare COSHVAL operator?}. It must be reentered with -\name{defn} off to be recognized. This procedure is used as an example; a -more efficient procedure would eliminate the unnecessary local variable -with -\begin{verbatim} - procedure coshval(a); - (exp(a) + exp(-a))/2; -\end{verbatim} - -\end{Comments} -\end{Switch} - - -\begin{Switch}{DEMO} -\index{interactive}\index{output} -The \name{demo} switch is used for interactive files, causing the system -to pause after each command in the file until you type a \key{Return}. -Default is \name{off}. - -\begin{Comments} -The switch \name{demo} has no effect on top level interactive -statements. Use it when you want to slow down operations in a file so -you can see what is happening. - -You can either include the \name{on demo} command in the file, or enter -it from the top level before bringing in any file. Unlike the -\nameref{pause} command, \name{on demo} does not permit you to interrupt -the file for questions of your own. - -\end{Comments} -\end{Switch} - - -\begin{Switch}{DFPRINT} -\index{output}\index{derivative} -When \name{dfprint} is on, expressions in the differentiation operator -\nameref{df} are printed in a more ``natural'' notation, with the -differentiation variables appearing as subscripts. In addition, if the -switch \nameref{noarg} is on (the default), the arguments of the -differentiated operator are suppressed. - -\begin{Examples} -operator f; \\ -df(f x,x); & DF(F(X),X); \\ -on dfprint; \\ -ws; & F_{X} \\ -df(f(x,y),x,y); & F_{X}_{,}_{Y} \\ -off noarg; \\ -ws; & F(X,Y)_{X} -\end{Examples} - -\end{Switch} - - -\begin{Switch}{DIV} -\index{output} -When \name{div} is on, the system divides any simple factors found in -the denominator of an expression into the numerator. Default is \name{off}. - -\begin{Examples} - -on div; \\ - -a := x**2/y**2; & A := X^{2} *Y^{-2} \\ - -b := a/(3*z); & B := \rfrac{1}{3}*X^{2} *Y^{-2} *Z^{-1} \\ - -off div; \\ - -a; & \rfrac{X^{2}}{Y^{2}}\\ - -b; & \rfrac{X^{2}}{3*Y^{2} *Z} - -\end{Examples} - -\begin{Comments} -The \name{div} switch only has effect when the \nameref{pri} switch is on. -When \name{pri} is off, regardless of the setting of \name{div}, the -printing behavior is as if \name{div} were off. -\end{Comments} -\end{Switch} - - -\begin{Switch}{ECHO} -\index{output} -The \name{echo} switch is normally off for top-level entry, and on when files -are brought in. If \name{echo} is turned on at the top level, your input -statements are echoed to the screen (thus appearing twice). Default -\name{off} (but note default \name{on} for files). - -\begin{Comments} -If you want to display certain portions of a file and not others, use the -commands \name{off echo} and \name{on echo} inside the file. If you want -no display of the file, use the input command - - \name{in} {\em filename}\name{\$} - -rather than using the semicolon delimiter. - -Be careful when you use commands within a file to generate another file. -Since \name{echo} is on for files, the output file echoes input statements -(unlike its behavior from the top level). You should explicitly turn off -\name{echo} when writing output, and turn it back on when you're done. -\end{Comments} -\end{Switch} - - -\begin{Switch}{ERRCONT} -\index{error handling} -When the \name{errcont} switch is on, error conditions do not stop file -execution. Error messages will be printed whether \name{errcont} is on or -off. - -Default is \name{off}. - -\begin{Comments} -\begin{TEX} -The table below shows REDUCE behavior under the settings of \name{errcont} and -\name{int} : - - \begin{center} - \begin{tabular}{|l|l|p{9.5cm}|} -\hline -\multicolumn{3}{|c|}{Behavior in Case of Error in Files}\\ -\hline -\multicolumn{1}{|c|}{errcont} & - \multicolumn{1}{c|}{int} & - \multicolumn{1}{c|}{Behavior when errors in files are encountered}\\ -\hline -off & off & -Message is printed and parsing continues, but no further statements are -executed; no commands from keyboard accepted except \verb|bye| or -\verb|end| \\ -off & on & -Message is printed, and you are asked if you wish to continue. (This is the -default behavior) \\ -on & off & -Message is printed, and file continues to execute without pause \\ -on & on & -Message is printed, and file continues to execute without pause\\ -\hline - \end{tabular} - \end{center} -\end{TEX} -\begin{INFO} -The following describes what happens when an error occurs in a file under -each setting of \name{errcont} and \name{int}: - -Both off: Message is printed and parsing continues, but no further -statements are executed; no commands from keyboard accepted except bye or -end; - -\name{errcont} off, \name{int} on: Message is printed, and you are asked -if you wish to continue. (This is the default behavior); - -\name{errcont} on, \name{int} off: Message is printed, and file continues -to execute without pause; - -Both on: Message is printed, and file continues to execute without pause. -\end{INFO} -\end{Comments} -\end{Switch} - - -\begin{Switch}{EVALLHSEQP} -\index{equation} -Under normal circumstances, the right-hand-side of an \nameref{equation} -is evaluated but not the left-hand-side. This also applies to any -substitutions made by the \nameref{sub} operator. If both sides are to be -evaluated, the switch \name{evallhseqp} should be turned on. - -\end{Switch} - - -\begin{Switch}{EXP} -\index{simplification} -When the \name{exp} switch is on, powers and products of expressions are -expanded. Default is \name{on}. - -\begin{Examples} -(x+1)**3; & X^{3} + 3*X^{2} + 3*X + 1 \\ -(a + b*i)*(c + d*i); & A*C + A*D*I + B*C*I - B*D \\ -off exp; \\ -(x+1)**3; & (X + 1)^{3} \\ -(a + b*i)*(c + d*i); & (A + B*I)*(C + D*I) \\ -length((x+1)**2/(y+1)); & 2 -\end{Examples} - -\begin{Comments} -Note that REDUCE knows that \IFTEX{$i^2 = -1$}{i^2 = -1}. -When \name{exp} is off, equivalent expressions may not simplify to the same -form, although zero expressions still simplify to zero. Several operators -that expect a polynomial argument behave differently when \name{exp} is -off, such as \nameref{length}. Be cautious about leaving \name{exp} off. -\end{Comments} -\end{Switch} - - -\begin{Switch}{EXPANDLOGS} -\index{logarithm} -In many cases it is desirable to expand product arguments of logarithms, -or collect a sum of logarithms into a single logarithm. Since these are -inverse operations, it is not possible to provide rules for doing both at -the same time and preserve the REDUCE concept of idempotent evaluation. -As an alternative, REDUCE provides two switches \name{expandlogs} and -\nameref{combinelogs} to carry out these operations. Both are off by default. -\begin{Examples} -on expandlogs; \\ -log(x*y); & LOG(X) + LOG(Y) \\ -on combinelogs; \\ -ws; & LOG(X*Y) -\end{Examples} - -\begin{Comments} -At the present time, it is possible to have both switches on at once, -which could lead to infinite recursion. However, an expression is -switched from one form to the other in this case. Users should not rely -on this behavior, since it may change in the next release. -\end{Comments} - -\end{Switch} - - -\begin{Switch}{EZGCD} -\index{greatest common divisor}\index{polynomial} -When \name{ezgcd} and \nameref{gcd} are on, greatest common divisors are -computed using the EZ GCD algorithm that uses modular arithmetic (and is -usually faster). Default is \name{off}. - -\begin{Comments} -As a side effect of the gcd calculation, the expressions involved are -factored, though not the heavy-duty factoring of \nameref{factorize}. The -EZ GCD algorithm was introduced in a paper by J. Moses and D.Y.Y. Yun in -\meta{Proceedings of the ACM}, 1973, pp. 159-166. - -Note that the \nameref{gcd} switch must also be on for \name{ezgcd} to have -effect. -\end{Comments} -\end{Switch} - - -\begin{Switch}{FACTOR} -\index{output} -When the \name{factor} switch is on, input expressions and results are -automatically factored. - -\begin{Examples} - -on factor; \\ - -aa := 3*x**3*a + 6*x**2*y*a + 3*x**3*b + 6*x**2*y*b\\ -+ x*y*a + 2*y**2*a + x*y*b + 2*y**2*b; - & AA := (A + B)*(3*X^{2} + Y)*(X + 2*Y) \\ -off factor; \\ -aa; & - 3*A*X^{3} + 6*A*X^{2}*Y + A*X*Y + 2*A*Y^{2} + 3*B*X^{3} + 6*B*X^{2}*Y\\ -+ B*X*Y + 2*B*Y^{2} \\ -on factor; \\ -ab := x**2 - 2; & AB := X^{2} - 2 -\end{Examples} - -\begin{Comments} -REDUCE factors univariate and multivariate polynomials with -integer coefficients, finding any factors that also have integer coefficients. -The factoring is done by reducing multivariate problems to univariate -ones with symbolic coefficients, and then solving the univariate ones modulo -small primes. The results of these calculations are merged to -determine the factors of the original polynomial. The factorizer normally -selects evaluation points and primes using a random number generator. -Thus, the detailed factoring behavior may be different each time any -particular problem is tackled. - -When the \name{factor} switch is turned on, the \nameref{exp} switch is -turned off, and when the \name{factor} switch is turned off, the -\nameref{exp} switch is turned on, whether it was on previously or not. - -When the switch \nameref{trfac} is on, informative messages are generated at -each call to the factorizer. The \nameref{trallfac} switch causes the -production of a more verbose trace message. It takes precedence over -\name{trfac} if they are both on. - -To factor a polynomial explicitly and store the results, use the operator -\nameref{factorize}. -\end{Comments} -\end{Switch} - - -\begin{Switch}{FAILHARD} -\index{integration} -When the \name{failhard} switch is on, the integration operator \nameref{int} -terminates with an error message if the integral cannot be done in closed -terms. -Default is off. - -\begin{Comments} -Use the \name{failhard} switch when you are dealing with complicated integrals -and want to know immediately if REDUCE was unable to handle them. The -integration operator sometimes returns a formal integration form that is -more complicated than the original expression, when it is unable to -complete the integration. -\end{Comments} -\end{Switch} - - -\begin{Switch}{FORT} -\index{FORTRAN} -When \name{fort} is on, output is given Fortran-compatible syntax. Default -is \name{off}. - -\begin{Examples} -on fort; \\ -df(sin(7*x + y),x); & ANS=7.*COS(7*X+Y) \\ -on rounded; \\ -b := log(sin(pi/5 + n*pi)); & - B=LOG(SIN(3.14159265359*N+0.628318530718)) -\end{Examples} - -\begin{Comments} -REDUCE results can be written to a file (using \nameref{out}) and used as data -by Fortran programs when \name{fort} is in effect. \name{fort} knows about -correct statement length, continuation characters, defining a symbol when -it is first used, and other Fortran details. - -The \nameref{GENTRAN} package offers many more possibilities than the -\name{fort} switch. It produces Fortran (or C or Ratfor) code from REDUCE -procedures or structured specifications, including facilities for producing -double precision output. -\end{Comments} -\end{Switch} - -\begin{Switch}{FORTUPPER} -\index{FORTRAN} -When \name{fortupper} is on, any Fortran-style output appears in upper case. -Default is \name{off}. - -\begin{Examples} -on fort; \\ -df(sin(7*x + y),x); & ans=7.*cos(7*x+y) \\ -on fortupper; \\ -df(sin(7*x + y),x); & ANS=7.*COS(7*X+Y) \\ -\end{Examples} -\end{Switch} - - -\begin{Switch}{FULLPREC} -\index{precision}\index{rounded} -Trailing zeroes of rounded numbers to the full system precision are -normally not printed. If this information is needed, for example to get a -more understandable indication of the accuracy of certain data, the switch -\name{fullprec} can be turned on. - -\begin{Examples} -on rounded; \\ -1/2; & 0.5 \\ -on fullprec; \\ -ws; & 0.500000000000 -\end{Examples} - -\begin{Comments} -This is just an output options which neither influences -the accuracy of the computation nor does it give additional -information about the precision of the results. -See also \nameref{scientific_notation}. -\end{Comments} -\end{Switch} - -\begin{Switch}{FULLROOTS} -\index{solve}\index{polynomial} -Since roots of cubic and quartic polynomials can often be very -messy, a switch \name{fullroots} controls the production -of results in closed form. \nameref{solve} will apply the -formulas for explicit forms for degrees 3 and 4 only if -\name{fullroots} is \name{on}. Otherwise the result forms -are built using \nameref{root\_of}. Default is \name{off}. -\end{Switch} - -\begin{Switch}{GC} -\index{memory} -With the \name{gc} switch, you can turn the garbage collection messages on -or off. The form of the message depends on the particular Lisp used for -the REDUCE implementation. - -\begin{Comments} -See \nameref{reclaim} for an explanation of garbage collection. REDUCE does -garbage collection when needed even if you have turned the notices off. -\end{Comments} -\end{Switch} - - -\begin{Switch}{GCD} -\index{greatest common divisor}\index{rational expression} -When \name{gcd} is on, common factors in numerators and denominators of -expressions are canceled. Default is \name{off}. - -\begin{Examples} -\begin{multilineinput} - -(2*(f*h)**2 - f**2*g*h - (f*g)**2 - f*h**3 + f*h*g**2 - - h**4 + g*h**3)/(f**2*h - f**2*g - f*h**2 + 2*f*g*h - - f*g**2 - g*h**2 + g**2*h); -\end{multilineinput} & -\rfrac{F^{2}*G^{2} + F^{2}*G*H - 2*F^{2}*H^{2} - F*G^{2}*H + F*H^{3} - G*H^{3} + - H^{4}} - {F^{2}*G - F^{2}*H + F*G^{2} - 2*F*G*H + F*H^{2} - G^{2}*H + G*H^{2}} \\ -on gcd; \\ -ws; & \rfrac{F*G + 2*F*H + H^{2}}{F + G} \\ -e2 := a*c + a*d + b*c + b*d; & E2 := A*C + A*D + B*C + B*D \\ -off exp; \\ -e2; & (A + B)*(C + D) -\end{Examples} - -\begin{Comments} -Even with \name{gcd} off, a check is automatically made for common variable -and numerical products in the numerators and denominators of expression, -and the appropriate cancellations made. Thus the example demonstrating the -use of \name{gcd} is somewhat complicated. Note when \nameref{exp} is off, -\name{gcd} has the side effect of factoring the expression. -\end{Comments} -\end{Switch} - - -\begin{Switch}{HORNER} -\index{output}\index{polynomial} -When the \name{horner} switch is on, polynomial expressions are printed -in Horner's form for faster and safer numerical evaluation. Default -is \name{off}. The leading variable of the expression is selected as -Horner variable. To select the Horner variable explicitly use the -\nameref{korder} declaration. - -\begin{Examples} -on horner;\\ -(13p-4q)^3;& -( - 64)*q^3 + p*(624*q^2 + p*(( - 2028)*q + p*2197))\\ -korder q;\\ -ws;& -2197*p^3 + q*(( - 2028)*p^2 + q*(624*p + q*(-64))) -\end{Examples} -\end{Switch} - - -\begin{Switch}{IFACTOR} -\index{integer}\index{factorize} -When the \name{ifactor} switch is on, any integer terms appearing as a result -of the \nameref{factorize} command are factored themselves into primes. Default -is \name{off}. If the argument of \name{factorize} is an integer, -\name{ifactor} has no effect, since the integer is always factored. - -\begin{Examples} -factorize(4*x**2 + 28*x + 48); & \{4,X + 3,X + 4\} \\ -factorize(22587); & \{3,7529\} \\ -on ifactor; \\ -factorize(4*x**2 + 28*x + 48); & \{2,2,X + 4,X + 3\} \\ -factorize(22587); & \{3,7529\} -\end{Examples} - -\begin{Comments} -Constant terms that appear within nonconstant -polynomial factors are not factored. - -The \name{ifactor} switch affects only factoring done specifically -with \nameref{factorize}, not on factoring done automatically when the -\nameref{factor} switch is on. -\end{Comments} -\end{Switch} - - -\begin{Switch}{INT} -\index{interactive} -The \name{int} switch specifies an interactive mode of operation. Default -\name{on}. - -\begin{Comments} -There is no reason to turn \name{int} off during interactive calculations, -since there are no benefits to be gained. If you do have \name{int} off -while inputting a file, and REDUCE finds an error, it prints the message -``Continuing with parsing only." In this state, REDUCE accepts only -\nameref{end}\name{;} or \nameref{bye}\name{;} from the keyboard; -everything else is ignored, even the command \name{on int}. -\end{Comments} -\end{Switch} - - -\begin{Switch}{INTSTR} -\index{output} -If \name{intstr} (for ``internal structure'') is on, arguments of an -operator are printed in a more structured form. - -\begin{Examples} -operator f; \\ -f(2x+2y); & F(2*X + 2*Y) \\ -on intstr; \\ -ws; & F(2*(X + Y)) -\end{Examples} - -\end{Switch} - - -\begin{Switch}{LCM} -\index{rational expression} -The \name{lcm} switch instructs REDUCE to compute the least common multiple -of denominators whenever rational expressions occur. Default is \name{on}. - -\begin{Examples} -off lcm; \\ -z := 1/(x**2 - y**2) + 1/(x-y)**2; - & Z := \rfrac{2*X*(X - Y)}{X^{4} - 2*X^{3}*Y + -2*X*Y^{3} - Y^{4}} \\ -on lcm; \\ -z; & \rfrac{2*X*(X - Y)}{X^{4} - 2*X^{3}*Y + 2*X*Y -^{3} - Y^{4}} \\ -zz := 1/(x**2 - y**2) + 1/(x-y)**2; - & ZZ := \rfrac{2*X}{X^{3} - X^{2}*Y - X*Y^{2} + - Y^{3}} \\ -on gcd; \\ -z; & \rfrac{2*X}{X^{3} - X^{2}*Y - X*Y^{2} + Y^{3} -} -\end{Examples} - -\begin{Comments} -Note that \name{lcm} has effect only when rational expressions are first -combined. It does not examine existing structures for simplifications on -display. That is shown above when \IFTEX{$z$}{z} is entered with -\name{lcm} off. It remains unsimplified even after \name{lcm} is turned -back on. However, a new variable containing the same expression is -simplified on entry. The switch \nameref{gcd} does examine existing -structures, as shown in the last example line above. - -Full greatest common divisor calculations become expensive if work with -large rational expressions is required. A considerable savings of time -can be had if a full gcd check is made only when denominators are combined, -and only a partial check for numerators. This is the effect of the \name{lcm} -switch. -\end{Comments} -\end{Switch} - - -\begin{Switch}{LESSSPACE} -\index{output} -You can turn on the switch \name{lessspace} if you want fewer -blank lines in your output. -\end{Switch} - - -\begin{Switch}{LIMITEDFACTORS} -\index{factorize}\index{polynomial} -To get limited factorization in cases where it is too expensive to use -full multivariate polynomial factorization, the switch -\name{limitedfactors} can be turned on. In that case, only ``inexpensive'' -factoring operations, such as square-free factorization, will be used -when \nameref{factorize} is called. - -\begin{Examples} -a := (y-x)^2*(y^3+2x*y+5)*(y^2-3x*y+7)$ \\ -factorize a; & -\begin{multilineoutput}{7cm} -\{ - X + Y, - X - Y, - 2*X*Y + Y^{3} + 5, - 3*X*Y - Y^{2} - 7\} -\end{multilineoutput} \\ -on limitedfactors; \\ -factorize a; & -\begin{multilineoutput}{7cm} -\{ - X + Y, - X - Y, - 6*X^{2}*Y^{2} + 3*X*Y^{4} - 2*X*Y^{3} + X*Y - Y^{5} - 7*Y^{3} - 5*Y^{2} - 35\} -\end{multilineoutput} -\end{Examples} - -\end{Switch} - - -\begin{Switch}{LIST} -The \name{list} switch causes REDUCE to print each term in any sum on -separate lines. - -\begin{Examples} -x**2*(y**2 + 2*y) + x*(y**2 + z)/(2*a); - & \rfrac{X*(2*A*X*Y^{2} + 4*A*X*Y + Y^{2} + -Z)}{2*A} \\ -on list; \\ -ws; & -\begin{multilineoutput}{6cm} -(X*(2*A*X*Y^{2} - + 4*A*X*Y - + Y^{2} - + Z))/(2*A) -\end{multilineoutput} -\end{Examples} -\end{Switch} - - -\begin{Switch}{LISTARGS} -\index{list}\index{argument}\index{operator} -If an operator other than those specifically defined for lists is given a -single argument that is a list, then the result of this operation will be -a list in which that operator is applied to each element of the list. -This process can be inhibited globally by turning on the switch -\name{listargs}. - -\begin{Examples} -log {a,b,c}; & {LOG(A),LOG(B),LOG(C)} \\ -on listargs; \\ -log {a,b,c}; & LOG({A,B,C}) -\end{Examples} - -\begin{Comments} -It is possible to inhibit such distribution for a specific operator by -using the declaration \nameref{listargp}. In addition, if an operator has -more than one argument, no such distribution occurs, so \name{listargs} -has no effect. -\end{Comments} - -\end{Switch} - - -\begin{Switch}{MCD} -\index{rational expression} -When \name{mcd} is on, sums and differences of rational expressions are put -on a common denominator. Default is \name{on}. - -\begin{Examples} -a/(x+1) + b/5; & \rfrac{5*A + B*X + B}{5*(X + 1)} \\ -off mcd; \\ -a/(x+1) + b/5; & (X + 1)^{-1}*A + 1/5*B \\ -1/6 + 1/7; & 13/42 -\end{Examples} - -\begin{Comments} -Even with \name{mcd} off, rational expressions involving only numbers are still -put over a common denominator. - -Turning \name{mcd} off is useful when explicit negative powers are needed, -or if no greatest common divisor calculations are desired, or when -differentiating complicated rational expressions. Results when \name{mcd} -is off are no longer in canonical form, and expressions equivalent to zero -may not simplify to 0. Some operations, such as factoring cannot be done -while \name{mcd} is off. This option should therefore be used with some -caution. Turning \name{mcd} off is most valuable in intermediate parts of -a complicated calculation, and should be turned back on for the last stage. -\end{Comments} -\end{Switch} - - -\begin{Switch}{MODULAR} -\index{modular} -When \name{modular} is on, polynomial coefficients are reduced by the -modulus set by \nameref{setmod}. If no modulus has been set, \name{modular} -has no effect. - -\begin{Examples} -setmod 2; & 1 \\ -on modular; \\ -(x+y)**2; & X^{2} + Y^{2} \\ -145*x**2 + 20*x**3 + 17 + 15*x*y; - & X^{2} + X*Y + 1 -\end{Examples} - -\begin{Comments} -Modular operations are only conducted on the coefficients, not the -exponents. The modulus is not restricted to being prime. When the modulus -is prime, division by a number not relatively prime to the modulus results -in a \meta{Zero divisor} error message. When the modulus is a composite -number, division by a power of the modulus results in an error message, but -division by an integer which is a factor of the modulus does not. -The representation of modular number can be influenced by -\nameref{balanced\_mod}. -\end{Comments} -\end{Switch} - - -\begin{Switch}{MSG} -\index{output} -When \name{msg} is off, the printing of warning messages is suppressed. Error -messages are still printed. - -\begin{Comments} -Warning messages include those about redimensioning an \nameref{array} -or declaring an \nameref{operator} where one is expected. -\end{Comments} -\end{Switch} - - -\begin{Switch}{MULTIPLICITIES} -\index{solve} -When \nameref{solve} is applied to a set of equations with multiple roots, -solution multiplicities are normally stored in the global variable -\nameref{root\_multiplicities} rather than the solution list. If you want -the multiplicities explicitly displayed, the switch \name{multiplicities} -should be turned on. In this case, \name{root_multiplicities} has no value. - -\begin{Examples} -solve(x^2=2x-1,x); & {X=1} \\ -root_multiplicities; & {2} \\ -on multiplicities; \\ -solve(x^2=2x-1,x); & {X=1,X=1} \\ -root_multiplicities; & -\end{Examples} - -\end{Switch} - - -\begin{Switch}{NAT} -\index{output} -When \name{nat} is on, output is printed to the screen in natural form, with -raised exponents. \name{nat} should be turned off when outputting expressions -to a file for future input. Default is \name{on}. - -\begin{Examples} -(x + y)**3; & X^{3} + 3*X^{2}*Y + 3*X*Y^{2} + Y^{3} \\ -off nat; \\ -(x + y)**3; & X**3 + 3*X**2*Y + 3*X*Y**2 + Y**3\$ \\ -on fort; \\ -(x + y)**3; & ANS=X**3+3.*X**2*Y+3.*X*Y**2+Y**3 -\end{Examples} -\begin{Comments} -With \name{nat} off, a dollar sign is printed at the end of each expression. -An output file written with \name{nat} off is ready to be read into REDUCE -using the command \nameref{in}. -\end{Comments} -\end{Switch} - - -\begin{Switch}{NERO} -\index{output} -When \name{nero} is on, zero assignments (such as matrix elements) are not -printed. - -\begin{Examples} -matrix a; -a := mat((1,0),(0,1)); & \begin{multilineoutput}{6cm} -A(1,1) := 1 -A(1,2) := 0 -A(2,1) := 0 -A(2,2) := 1 -\end{multilineoutput}\\ -on nero; \\ -a; & \begin{multilineoutput}{6cm} -MAT(1,1) := 1 -MAT(2,2) := 1 -\end{multilineoutput}\\ -a(1,2); & \explanationo{nothing is printed.} \\ -b := 0; & \explanationo{nothing is printed.} \\ -off nero; \\ -b := 0; & B := 0 -\end{Examples} -\begin{Comments} -\name{nero} is often used when dealing with large sparse matrices, to avoid -being overloaded with zero assignments. -\end{Comments} -\end{Switch} - - -\begin{Switch}{NOARG} -\index{output}\index{derivative} -When \nameref{dfprint} is on, expressions in the differentiation operator -\nameref{df} are printed in a more ``natural'' notation, with the -differentiation variables appearing as subscripts. When \name{noarg} -is on (the default), the arguments of the differentiated operator are also -suppressed. - -\begin{Examples} -operator f; \\ -df(f x,x); & DF(F(X),X); \\ -on dfprint; \\ -ws; & F_{X} \\ -off noarg; \\ -ws; & F(X)_{X} -\end{Examples} - -\end{Switch} - - -\begin{Switch}{NOLNR} -\index{integration} -When \name{nolnr} is on, the linear properties of the integration operator -\nameref{int} are suppressed if the integral cannot be found in closed terms. - -\begin{Comments} -REDUCE uses the linear properties of integration to attempt to break down -an integral into manageable pieces. If an integral cannot be found in -closed terms, these pieces are returned. When the \name{nolnr} switch is off, -as many of the pieces as possible are integrated. When it is on, if any piece -fails, the rest of them remain unevaluated. -\end{Comments} -\end{Switch} - - -%\begin{Switch}{NORNDBF} -% -%***** To be added ***** -% -%\end{Switch} - - -\begin{Switch}{NOSPLIT} -\index{output} -Under normal circumstances, the printing routines try to break an expression -across lines at a natural point. This is a fairly expensive process. If -you are not overly concerned about where the end-of-line breaks come, you -can speed up the printing of expressions by turning off the switch -\name{nosplit}. This switch is normally on. - -\end{Switch} - - -\begin{Switch}{NUMVAL} -\index{rounded} -With \nameref{rounded} on, elementary functions with numerical arguments -will return a numerical answer where appropriate. If you wish to inhibit -this evaluation, \name{numval} should be turned off. It is normally on. - -\begin{Examples} -on rounded; \\ -cos 3.4; & - 0.966798192579 \\ -off numval; \\ -cos 3.4; & COS(3.4) -\end{Examples} - -\end{Switch} - - -\begin{Switch}{OUTPUT} -\index{output} -When \name{output} is off, no output is printed from any REDUCE calculation. -The calculations have their usual effects other than printing. Default is -\name{on}. - -\begin{Comments} -Turn output \name{off} if you do not wish to see output when executing -large files, or to save the time REDUCE spends formatting large expressions -for display. Results are still available with \nameref{ws}, or in their -assigned variables. -\end{Comments} -\end{Switch} - - -\begin{Switch}{OVERVIEW} -\index{factorize} -When \name{overview} is on, the amount of detail reported by the factorizer -switches \nameref{trfac} and \nameref{trallfac} is reduced. - -\end{Switch} - - -\begin{Switch}{PERIOD} -\index{output}\index{integer} -When \name{period} is on, periods are added after integers in -Fortran-compatible output (when \nameref{fort} is on). There is no effect -when \name{fort} is off. Default is \name{on}. -\end{Switch} - - -\begin{Switch}{PRECISE} -\index{simplification}\index{square root} -When the \name{precise} switch is on, simplification of roots of even -powers returns absolute values, a more precise answer mathematically. -Default is \name{on}. - -\begin{Examples} -sqrt(x**2); & X \\ -(x**2)**(1/4); & SQRT(X) \\ -on precise; \\ -sqrt(x**2); & ABS(X) \\ -(x**2)**(1/4); & SQRT(ABS(X)) -\end{Examples} - -\begin{Comments} -In many types of mathematical work, simplification of powers and surds can -proceed by the fastest means of simplifying the exponents arithmetically. -When it is important to you that the positive root be returned, turn -\name{precise} on. One situation where this is important is when graphing -square-root expressions such as \IFTEX{$\sqrt{x^2+y^2}$}{sqrt(x^2+y^2)} to -avoid a spike caused by REDUCE simplifying -\IFTEX{$\sqrt{y^2}$}{sqrt(y^2)} to \IFTEX{$y$}{y} when \IFTEX{$x$}{x} is -zero. -\end{Comments} -\end{Switch} - - -\begin{Switch}{PRET} -\index{output} -When \name{pret} is on, input is printed in standard REDUCE format and then -evaluated. - -\begin{Examples} -on pret; \\ - (x+1)^3; & -\begin{multilineoutput}{6cm} - (x + 1)**3; -X^{3} + 3*X^{2} + 3*X + 1 -\end{multilineoutput} \\ -\begin{multilineinput} - -procedure fac(n); - if not (fixp(n) and n>=0) - then rederr "Choose nonneg. integer only" - else for i := 0:n-1 product i+1; -\end{multilineinput} & -\begin{multilineoutput}{8cm} -procedure fac n; - if not (fixp n and n>=0) - then rederr "Choose nonneg. integer only" - else for i := 0:n - 1 product i + 1; - -FAC -\end{multilineoutput}\\ - -fac 5; & \begin{multilineoutput}{6cm} -fac 5; -120 -\end{multilineoutput} - -\end{Examples} - -\begin{Comments} -Note that all input is converted to lower case except strings (which keep -the same case) all operators with a single argument have had the -parentheses removed, and all infix operators have had a space added on each -side. In addition, syntactical constructs like -\name{if}\ldots\name{then}\ldots\name{else} are printed in a standard format. -\end{Comments} -\end{Switch} - - -\begin{Switch}{PRI} -\index{output} -When \name{pri} is on, the declarations \nameref{order} and \nameref{factor} can -be used, and the switches \nameref{allfac}, \nameref{div}, \nameref{rat}, -and \nameref{revpri} take effect when they are on. Default is \name{on}. - -\begin{Comments} -Printing of expressions is faster with \name{pri} off. The expressions are -then returned in one standard form, without any of the display options that -can be used to feature or display various parts of the expression. You can -also gain insight into REDUCE's representation of expressions with -\name{pri} off. -\end{Comments} -\end{Switch} - - -\begin{Switch}{RAISE} -\index{input}\index{character} -When \name{raise} is on, lower case letters are automatically converted to -upper case on input. \name{raise} is normally on. - -\begin{Comments} -This conversion affects the internal representation of the letter, and is -independent of the case with which a letter is printed, which is normally -lower case. -\end{Comments} - -\end{Switch} - - -\begin{Switch}{RAT} -\index{output} -When the \name{rat} switch is on, and kernels have been selected to display -with the \nameref{factor} declaration, the denominator is printed with each -term rather than one common denominator at the end of an expression. - -\begin{Examples} -(x+1)/x + x**2/sin y; - & \rfrac{SIN(Y)*X + SIN(Y) + X^{3}}{SIN(Y)*X} \ -\ -factor x; \\ -(x+1)/x + x**2/sin y; - & \rfrac{X^{3} + X*SIN(Y) + SIN(Y)}{X*SIN(Y)} \ -\ -on rat; \\ -(x+1)/x + x**2/sin y; - & \rfrac{X^{2}}{SIN(Y)} + 1 + X^{-1} -\end{Examples} - -\begin{Comments} -The \name{rat} switch only has effect when the \nameref{pri} switch is on. -When \name{pri} is off, regardless of the setting of \name{rat}, the -printing behavior is as if \name{rat} were off. \name{rat} only has -effect upon the display of expressions, not their internal form. -\end{Comments} -\end{Switch} - - -\begin{Switch}{RATARG} -\index{rational expression}\index{polynomial} -When \name{ratarg} is on, rational expressions can be given to operators -such as \nameref{coeff} and \nameref{lterm} that normally require -polynomials in one of their arguments. When \name{ratarg} is off, rational -expressions cause an error message. - -\begin{Examples} -aa := x/y**2 + 1/x + y/x**2; - & AA := \rfrac{X^{3} + X*Y^{2} + Y^{3}}{X^{2}*Y^{2}} \\ -coeff(aa,x); & - ***** \rfrac{X^{3} + X*Y^{2} + Y^{3}}{X^{2}*Y^{2}} invalid as POLYNOMIAL\\ -on ratarg; \\ -coeff(aa,x); - & \{\rfrac{Y}{X^{2}},\rfrac{1}{X^{2}},0,\rfrac{1}{X^{2}*Y^{2}}\} -\end{Examples} -\end{Switch} - - -\begin{Switch}{RATIONAL} -\index{rational expression}\index{polynomial} -When \name{rational} is on, polynomial expressions with rational coefficients -are produced. - -\begin{Examples} -x/2 + 3*y/4; & \rfrac{2*X + 3*Y}{4} \\ -(x**2 + 5*x + 17)/2; & \rfrac{X^{2} + 5*X + 17}{2} \\ -on rational; \\ -x/2 + 3y/4; & \rfrac{1}{2}*(X + \rfrac{3}{2}*Y) \\ -(x**2 + 5*x + 17)/2; & \rfrac{1}{2}*(X^{2} + 5*X + 17) -\end{Examples} - -\begin{Comments} -By using \name{rational}, polynomial expressions with rational -coefficients can be used in some commands that expect polynomials. With -\name{rational} off, such a polynomial becomes a rational expression, with -denominator the least common multiple of the denominators of the rational -number coefficients. % The \nameref{factorize} command does not accept -% polynomials with rational coefficients. -\end{Comments} -\end{Switch} - - -\begin{Switch}{RATIONALIZE} -\index{rational expression}\index{simplification}\index{complex} -When the \name{rationalize} switch is on, denominators of rational expressions -that contain complex numbers or root expressions are simplified by -multiplication by their conjugates. - -\begin{Examples} -qq := (1+sqrt(3))/(sqrt(3)-7); & QQ := \rfrac{SQRT(3) + 1}{SQRT(3) - 7} \\ -on rationalize; \\ -qq; & \rfrac{- 4*SQRT(3) - 5}{23} \\ -2/(4 + 6**(1/3)); & \rfrac{6^{2/3} - 4*6^{1/3} + 16}{35} \\ -(i-1)/(i+3); & \rfrac{2*I - 1}{5} \\ -off rationalize; \\ -(i-1)/(i+3); & \rfrac{I - 1}{I + 3} -\end{Examples} - -\end{Switch} - - -\begin{Switch}{RATPRI} -\index{output}\index{rational expression} -When the \name{ratpri} switch is on, rational expressions and fractions are -printed as two lines separated by a fraction bar, rather than in a linear -style. Default is \name{on}. - -\begin{Examples} -3/17; & \rfrac{3}{17} \\ -2/b + 3/y; & \rfrac{3*B + 2*Y}{B*Y} \\ -off ratpri; \\ -3/17; & 3/17 \\ -2/b + 3/y; & (3*B + 2*Y)/(B*Y) -\end{Examples} -\end{Switch} - - -\begin{Switch}{REVPRI} -\index{output} -When the \name{revpri} switch is on, terms are printed in reverse order from -the normal printing order. - -\begin{Examples} -x**5 + x**2 + 18 + sqrt(y); & SQRT(Y) + X^{5} + X^{2} + 18 \\ -a + b + c + w; & A + B + C + W \\ -on revpri; \\ -x**5 + x**2 + 18 + sqrt(y); & 17 + X^{2} + X^{5} + SQRT(Y) \\ -a + b + c + w; & W + C + B + A -\end{Examples} - -\begin{Comments} -Turn \name{revpri} on when you want to display a polynomial in ascending -rather than descending order. -\end{Comments} -\end{Switch} - - -\begin{Switch}{RLISP88} -\index{lisp} -Rlisp '88 is a superset of the Rlisp that has been traditionally used for -the support of REDUCE. It is fully documented in the book Marti, J.B., -``{RLISP} '88: An Evolutionary Approach to Program Design and Reuse'', -World Scientific, Singapore (1993). It supports different looping -constructs from the traditional Rlisp, and treats ``-'' as a letter unless -separated by spaces. Turning on the switch \name{rlisp88} converts to -Rlisp '88 parsing conventions in symbolic mode, and enables the use of -Rlisp '88 extensions. Turning off the switch reverts to the traditional -Rlisp and the previous mode ( (\nameref{symbolic} or \nameref{algebraic}) -in force before \name{rlisp88} was turned on. - -\end{Switch} - - -\begin{Switch}{ROUNDALL} -\index{rounded}\index{rational expression}\index{floating point} -In \nameref{rounded} mode, rational numbers are normally converted to a -floating point representation. If \name{roundall} is off, this conversion -does not occur. \name{roundall} is normally \name{on}. - -\begin{Examples} -on rounded; \\ -1/2; & 0.5 \\ -off roundall; \\ -1/2; \rfrac{1}{2} -\end{Examples} - -\end{Switch} - - -\begin{Switch}{ROUNDBF} -When \nameref{rounded} is on, the normal defaults cause underflows to be -converted to zero. If you really want the small number that results in -such cases, \name{roundbf} can be turned on. - -\begin{Examples} -on rounded; \\ -exp(-100000.1^2); & 0 \\ -on roundbf; \\ -exp(-100000.1^2); & 1.18441281937E-4342953505 -\end{Examples} - -\begin{Comments} -If a polynomial is input in \nameref{rounded} mode at the default -precision into any \nameref{roots} function, and it is not possible to -represent any of the coefficients of the polynomial precisely in the -system floating point representation, the switch \name{roundbf} will be -automatically turned on. All rounded computation will use the internal -bigfloat representation until the user subsequently turns \name{roundbf} -off. (A message is output to indicate that this condition is in effect.) -\end{Comments} -\end{Switch} - - -\begin{Switch}{ROUNDED} -\index{floating point} -When \name{rounded} is on, floating-point arithmetic is enabled, with -precision initially at a system default value, which is usually 12 digits. -The precise number can be found by the command \nameref{precision}(0). -\begin{Examples} -pi; & PI \\ -35/217; & \rfrac{5}{31} \\ -on rounded; \\ -pi; & 3.14159265359 \\ -35/217; & 0.161 \\ -sqrt(3); & 1.73205080756 -\end{Examples} -\begin{Comments} -If more than the default number of decimal places are required, use the -\nameref{precision} command to set the required number. -\end{Comments} -\end{Switch} - - -\begin{Switch}{SAVESTRUCTR} -\index{STRUCTR OPERATOR} -When \name{savestructr} is on, results of the \nameref{structr} command are -returned as a list whose first element is the representation for the -expression and the remaining elements are equations showing the -relationships of the generated variables. - -\begin{Examples} -off exp; \\ -structr((x+y)^3 + sin(x)^2); & -\begin{multilineoutput}{6cm} -ANS3 - where - ANS3 := ANS1^{3} + ANS2^{2} - ANS2 := SIN(X) - ANS1 := X + Y -\end{multilineoutput}\\ -ans3; & ANS3 \\ -on savestructr; \\ -structr((x+y)^{3} + sin(x)^{2}); & -{ANS3,ANS3=ANS1^{3} + ANS2^{2},ANS2=SIN(X),ANS1=X + Y} \\ -ans3 where rest ws; & -(X + Y)^{3} + SIN(X)^{2} -\end{Examples} -\begin{Comments} -In normal operation, \nameref{structr} is only a display command. With -\name{savestructr} on, you can access the various parts of the expression -produced by \name{structr}. - -The generic system names use the stem \name{ANS}. You can change this to your -own stem by the command \nameref{varname}. REDUCE adds integers to this stem -to make unique identifiers. -\end{Comments} -\end{Switch} - - -\begin{Switch}{SOLVESINGULAR} -\index{solve} -When \name{solvesingular} is on, singular or underdetermined systems of -linear equations are solved, using arbitrary real, complex or integer -variables in the answer. Default is \name{on}. - -\begin{Examples} -solve({2x + y,4x + 2y},{x,y}); & - \{\{X= - \rfrac{ARBCOMPLEX(1)}{2},Y=ARBCOMPLEX(1)\}\} \\ -solve({7x + 15y - z,x - y - z},{x,y,z}); & -\begin{multilineoutput}{6cm} -\{\{X=\rfrac{8*ARBCOMPLEX(3)}{11} - Y= - \rfrac{3*ARBCOMPLEX(3)}{11} - Z=ARBCOMPLEX(3)\}\} -\end{multilineoutput}\\ -off solvesingular; \\ -solve({2x + y,4x + 2y},{x,y}); & - ***** SOLVE given singular equations \\ -solve({7x + 15y - z,x - y - z},{x,y,z}); & - ***** SOLVE given singular equations -\end{Examples} -\begin{Comments} - -The integer following the identifier \nameref{arbcomplex} above is assigned by -the system, and serves to identify the variable uniquely. It has no other -significance. -\end{Comments} -\end{Switch} - - -\begin{Switch}{TIME} -\index{time} -When \name{time} is on, the system time used in executing each REDUCE -statement is printed after the answer is printed. - -\begin{Examples} -on time; & Time: 4940 ms \\ -df(sin(x**2 + y),y); & -\begin{multilineoutput}{6cm} -COS(X + Y^{2}) -Time: 180 ms -\end{multilineoutput}\\ -solve(x**2 - 6*y,x); & -\begin{multilineoutput}{6cm} -\{X= - SQRT(Y)*SQRT(6), - X=SQRT(Y)*SQRT(6)\} -Time: 320 ms -\end{multilineoutput} -\end{Examples} -\begin{Comments} -When \name{time} is first turned on, the time since the beginning of the -REDUCE session is printed. After that, the time used in computation, -(usually in milliseconds, though this is system dependent) is printed after -the results of each command. Idle time or time spent typing in commands is -not counted. If \name{time} is turned off, the first reading after it is -turned on again gives the time elapsed since it was turned off. The time -printed is CPU or wall clock time, depending on the system. -\end{Comments} -\end{Switch} - - -\begin{Switch}{TRALLFAC} -\index{factorize} -When \name{trallfac} is on, a more detailed trace of factorizer calls is -generated. - -\begin{Comments} -The \name{trallfac} switch takes precedence over \nameref{trfac} if they are -both on. \name{trfac} gives a factorization trace with less detail in it. -When the \nameref{factor} switch is on also, all input polynomials are sent to -the factorizer automatically and trace information is generated. The -\nameref{out} command saves the results of the factoring, but not the trace. -% You need to use the \name{dribble} command to save the trace text to a file. -\end{Comments} -\end{Switch} - - -\begin{Switch}{TRFAC} -\index{factorize} -When \name{trfac} is on, a narrative trace of any calls to the factorizer is -generated. Default is \name{off}. - -\begin{Comments} -When the switch \nameref{factor} is on, and \name{trfac} is on, every input -polynomial is sent to the factorizer, and a trace generated. With -\name{factor} off, only polynomials that are explicitly factored with the -command \nameref{factorize} generate trace information. - -% Use the \name{dribble} or \name{logfile} command to save the trace text to -% a file. -The \nameref{out} command saves the results of the factoring, but not -the trace. The \nameref{trallfac} switch gives trace information to a -greater level of detail. -\end{Comments} -\end{Switch} - -\begin{Switch}{TRIGFORM} -\index{solve}\index{polynomial} -When \nameref{fullroots} is on, \nameref{solve} will compute the -roots of a cubic or quartic polynomial is closed form. When -\name{trigform} is on, the roots will be expressed by trigonometric -forms. Otherwise nested surds are used. Default is \name{on}. -\end{Switch} - - -\begin{Switch}{TRINT} -\index{integration} -When \name{trint} is on, a narrative tracing various steps in the -integration process is produced. - -\begin{Comments} -%Use the \name{dribble} or \name{logfile} command to save this text to a file. -The \nameref{out} command saves the results of the integration, but not the -trace. -\end{Comments} -\end{Switch} - -\begin{Switch}{TRNONLNR} -\index{solve} -When \name{trnonlnr} is on, a narrative tracing various steps in -the process for solving non-linear equations is produced. - -\begin{Comments} -\name{trnonlnr} can only be used after the solve package has been loaded -(e.g., by an explicit call of \nameref{load\_package}). The \nameref{out} -command saves the results of the equation solving, but not the trace. -\end{Comments} -\end{Switch} - - -\begin{Switch}{VAROPT} -\index{solve} -When \name{varopt} is on, the sequence of variables is optimized by -\nameref{solve} with respect to execution speed. Otherwise, the sequence -given in the call to \nameref{solve} is preserved. Default is \name{on}. - -In combination with the switch \nameref{arbvars}, \name{varopt} can be used -to control variable elimination. - -\begin{Examples} -off arbvars; \\ -solve({x+2z,x-3y},{x,y,z}); & - \{\{y=\rfrac{x}{3},z= - \rfrac{x}{2}\}\} \\ -solve({x*y=1,z=x},{x,y,z}); & - \{\{z=x,y=\rfrac{1}{x}\}\} \\ -off varopt; \\ -solve({x+2z,x-3y},{x,y,z}); & - \{\{x= - 2*z,y= - \rfrac{2*z}{3}\}\} \\ -solve({x*y=1,z=x},{x,y,z}); & - \{\{y=\rfrac{1}{z},x=z\}\} \\ -\end{Examples} -\end{Switch} - +\section{General Switches} + +\begin{Introduction}{SWITCHES} +Switches are set on or off using the commands \nameref{on} or +\nameref{off}, respectively. +The default setting of the switches described in this section is +\nameref{off} unless stated otherwise. +\end{Introduction} + +\begin{Switch}{ALGINT} +\index{integration} +When the \name{algint} switch is on, the algebraic integration module (which +must be loaded from the REDUCE library) is used for integration. + +\begin{Comments} +Loading \name{algint} from the library automatically turns on the +\name{algint} switch. An error message will be given if \name{algint} is +turned on when the \name{algint} has not been loaded from the library. +\end{Comments} +\end{Switch} + + +\begin{Switch}{ALLBRANCH} +When \name{allbranch} is on, the operator \nameref{solve} selects all +branches of solutions. +When \name{allbranch} is off, it selects only the principal +branches. Default is \name{on}. + +\begin{Examples} + +solve(log(sin(x+3)),x); & +\begin{multilineoutput}{6cm} +\{X=2*ARBINT(1)*PI - ASIN(1) - 3, + X=2*ARBINT(1)*PI + ASIN(1) + PI - 3\} +\end{multilineoutput}\\ +off allbranch; \\ +solve(log(sin(x+3)),x); & + {X=ASIN(1) - 3} +\end{Examples} + +\begin{Comments} +\nameref{arbint}(1) indicates an arbitrary integer, which is given a +unique identifier by REDUCE, showing that there are infinitely many +solutions of this type. When \name{allbranch} is off, the single +canonical solution is given. +\end{Comments} +\end{Switch} + + +\begin{Switch}{ALLFAC} +\index{output} +The \name{allfac} switch, when on, causes REDUCE to factor out automatically +common products in the output of expressions. Default is \name{on}. + +\begin{Examples} +x + x*y**3 + x**2*cos(z); & X*(COS(Z)*X + Y^{3} + 1) \\ +off allfac; \\ +x + x*y**3 + x**2*cos(z); & COS(Z)*X^{2} + X*Y^{3} + X +\end{Examples} + +\begin{Comments} +The \name{allfac} switch has no effect when \name{pri} is off. Although the +switch setting stays as it was, printing behavior is as if it were off. +\end{Comments} +\end{Switch} + + +% \begin{Switch}{ALLPREC} +% +% \end{Switch} +% +% +\begin{Switch}{ARBVARS} +\index{solve} +When \name{arbvars} is on, the solutions of singular or underdetermined +systems of equations are presented in terms of arbitrary complex variables +(see \nameref{arbcomplex}). Otherwise, the solution is parametrized in +terms of some of the input variables. Default is \name{on}. + +\begin{Examples} +solve({2x + y,4x + 2y},{x,y}); & + \{\{x= - \rfrac{arbcomplex(1)}{2},y=arbcomplex(1)\}\} \\ +solve({sqrt(x)+ y**3-1},{x,y}); & + \{\{y=arbcomplex(2),x=y^6 - 2*y^3 + 1\}\} \\ +off arbvars; \\ +solve({2x + y,4x + 2y},{x,y}); & + \{\{x= - \rfrac{y}{2}\}\} \\ +solve({sqrt(x)+ y**3-1},{x,y}); & + \{\{x=y^6 - 2*y^3 + 1\}\} \\ +\end{Examples} +\begin{Comments} + +With \name{arbvars} off, the return value \name{\{\{\}\}} means that the +equations given to \nameref{solve} imply no relation among the input +variables. +\end{Comments} +\end{Switch} + + +\begin{Switch}{BALANCED\_MOD} +\index{modular} +\nameref{modular} numbers are normally produced in the range [0,...\meta{n}), +where +\meta{n} is the current modulus. With \name{balanced\_mod} on, the range +[-\meta{n}/2,\meta{n}/2] is used instead. + +\begin{Examples} +setmod 7; & 1 \\ +on modular; \\ +4; & 4 \\ +on balanced_mod; \\ +4; & -3 +\end{Examples} +\end{Switch} + + +\begin{Switch}{BFSPACE} +\index{output}\index{floating point} +Floating point numbers are normally printed in a compact notation (either +fixed point or in scientific notation if \nameref{SCIENTIFIC\_NOTATION} +has been used). In some (but not all) cases, it helps comprehensibility +if spaces are inserted in the number at regular intervals. The switch +\name{bfspace}, if on, will cause a blank to be inserted in the number after +every five characters. +\begin{Examples} +on rounded; \\ +1.2345678; & 1.2345678 \\ +on bfspace; \\ +1.2345678; & 1.234 5678 +\end{Examples} +\begin{Comments} +\name{bfspace} is normally off. +\end{Comments} +\end{Switch} + + +\begin{Switch}{COMBINEEXPT} +\index{exponent simplification} +REDUCE is in general poor at surd simplification. However, when the +switch \name{combineexpt} is on, the system attempts to combine +exponentials whenever possible. +\begin{TEX} +\begin{Examples} +3^(1/2)*3^(1/3)*3^(1/6); & SQRT(3)*3^{\rfrac{1}{3}}*3^{\rfrac{1}{6}} \\ +on combineexpt; \\ +ws; & 1 +\end{Examples} +\end{TEX} +\begin{INFO} +{\begin{Examples} +3^(1/2)*3^(1/3)*3^(1/6); & SQRT(3)*3^{1/3}*3^{1/6} \\ +on combineexpt; \\ +ws; & 1 +\end{Examples}} +\end{INFO} + +\end{Switch} + + +\begin{Switch}{COMBINELOGS} +\index{logarithm} +In many cases it is desirable to expand product arguments of logarithms, +or collect a sum of logarithms into a single logarithm. Since these are +inverse operations, it is not possible to provide rules for doing both at +the same time and preserve the REDUCE concept of idempotent evaluation. +As an alternative, REDUCE provides two switches \nameref{expandlogs} and +\name{combinelogs} to carry out these operations. +\begin{Examples} +on expandlogs; \\ +log(x*y); & LOG(X) + LOG(Y) \\ +on combinelogs; \\ +ws; & LOG(X*Y) +\end{Examples} + +\begin{Comments} +At the present time, it is possible to have both switches on at once, +which could lead to infinite recursion. However, an expression is +switched from one form to the other in this case. Users should not rely +on this behavior, since it may change in the next release. +\end{Comments} + +\end{Switch} + + +\begin{Switch}{COMP} +\index{compiler} +When \name{comp} is on, any succeeding function definitions are compiled +into a faster-running form. Default is \name{off}. + +\begin{Examples} +\explanation{The following procedure finds Fibonacci numbers recursively. +Create a new file ``refib" in your current directory with the following +lines in it:} \\[6mm] +\begin{multilineinput} +procedure refib(n); + if fixp n and n >= 0 then + if n <= 1 then 1 + else refib(n-1) + refib(n-2) + else rederr "nonnegative integer only"; + +end; +\end{multilineinput}\\ +\explanation{Now load REDUCE and run the following:}\\ +on time; & Time: 100 ms \\ + +in "refib"$ & Time: 0 ms \\ + + & REFIB \\ + + & Time: 260 ms \\ + + & Time: 20 ms \\ + +refib(80); & 37889062373143906 \\ + + & Time: 14840 ms \\ + +on comp; & Time: 80 ms \\ + +in "refib"$ & Time: 20 ms \\ + + & REFIB \\ + + & Time: 640 ms \\ + +refib(80); & 37889062373143906 \\ + + & Time: 10940 ms +\end{Examples} +\begin{Comments} +Note that the compiled procedure runs faster. Your time messages will +differ depending upon which system you have. Compiled functions remain so +for the duration of the REDUCE session, and are then lost. They must be +recompiled if wanted in another session. With the switch \nameref{time} on +as shown above, the CPU time used in executing the command is returned in +milliseconds. Be careful not to leave \name{comp} on unless you want it, +as it makes the processing of procedures much slower. + +\end{Comments} +\end{Switch} + + +\begin{Switch}{COMPLEX} +\index{complex} +When the \name{complex} switch is on, full complex arithmetic is used in +simplification, function evaluation, and factorization. Default is \name{off}. + +\begin{Examples} + +factorize(a**2 + b**2); & \{A^{2} + B^{2} \} \\ +on complex; \\ + +factorize(a**2 + b**2); & \{A - I*B,A + I*B\} \\ + +(x**2 + y**2)/(x + i*y); & X - I*Y \\ + +on rounded; & + + *** Domain mode COMPLEX changed to COMPLEX\_FLOAT \\ + +sqrt(-17); & 4.12310562562*I \\ + +log(7*i); & 1.94591014906 + 1.57079632679*I +\end{Examples} + +\begin{Comments} +Complex floating-point can be done by turning on \nameref{rounded} in +addition to \name{complex}. With \name{complex} off however, REDUCE knows +that \IFTEX{$i$}{i} is the square root of \IFTEX{$-1$}{-1} but will not +carry out more complicated complex operations. If you want complex +denominators cleared by multiplication by their conjugates, turn on the +switch \nameref{rationalize}. +\end{Comments} +\end{Switch} + + +\begin{Switch}{CREF} +\index{cross reference} +The switch \name{cref} invokes the CREF cross-reference program that +processes a set of procedure definitions to produce a summary of their +entry points, undefined procedures, non-local variables and so on. The +program will also check that procedures are called with a consistent +number of arguments, and print a diagnostic message otherwise. + +The output is alphabetized on the first seven characters of each function +name. + +To invoke the cross-reference program, \name{cref} is first turned on. +This causes the program to load and the cross-referencing process to +begin. After all the required definitions are loaded, turning \name{cref} +off will cause a cross-reference listing to be produced. + +\begin{Comments} + +Algebraic procedures in REDUCE are treated as if they were symbolic, so +that algebraic constructs will actually appear as calls to symbolic +functions, such as \name{aeval}. +\end{Comments} + +\end{Switch} + + +\begin{Switch}{CRAMER} +\index{matrix}\index{linear system}\index{solve} +When the \name{cramer} switch is on, \nameref{matrix} inversion +and linear equation +solving (operator \nameref{solve}) is done by Cramer's rule, through exterior +multiplication. Default is \name{off}. + +\begin{Examples} +on time; & Time: 80 ms \\ +off output; & Time: 100 ms \\[4mm] +\begin{multilineinput} +mm := mat((a,b,c,d,f),(a,a,c,f,b),(b,c,a,c,d), (c,c,a,b,f), + (d,a,d,e,f)); +\end{multilineinput} & Time: 300 ms \\ +inverse := 1/mm; & Time: 18460 ms \\ +on cramer; & Time: 80 ms \\ +cramersinv := 1/mm; & Time: 9260 ms +\end{Examples} + +\begin{Comments} +Your time readings will vary depending on the REDUCE version you use. +After you invert the matrix, turn on \nameref{output} and ask for one of +the elements of the inverse matrix, such as \name{cramersinv(3,2)}, so that +you can see the size of the expressions produced. + +Inversion of matrices and the solution of linear equations with dense +symbolic entries in many variables is generally considerably faster with +\name{cramer} on. However, inversion of numeric-valued matrices is +slower. Consider the matrices you're inverting before deciding whether to +turn \name{cramer} on or off. A substantial portion of the time in matrix +inversion is given to formatting the results for printing. To save this +time, turn \name{output} off, as shown in this example or terminate the +expression with a dollar sign instead of a semicolon. The results are +still available to you in the workspace associated with your prompt +number, or you can assign them to an identifier for further use. +\end{Comments} +\end{Switch} + + +\begin{Switch}{DEFN} +\index{lisp} +When the switch \name{defn} is on, the Standard Lisp equivalent of the +input statement or procedure is printed, but not evaluated. Default is +\name{off}. + +\begin{Examples} + +on defn; \\ + +17/3; & (AEVAL (LIST 'QUOTIENT 17 3)) \\ + +df(sin(x),x,2); + & (AEVAL (LIST 'DF (LIST 'SIN 'X) 'X 2)) \\ +\begin{multilineinput} +procedure coshval(a); + begin scalar g; + g := (exp(a) + exp(-a))/2; + return g + end; +\end{multilineinput} & +\begin{multilineoutput}{7cm} +(AEVAL + (PROGN + (FLAG '(COSHVAL) 'OPFN) + (DE COSHVAL (A) + (PROG (G) + (SETQ G + (AEVAL + (LIST + 'QUOTIENT + (LIST + 'PLUS + (LIST 'EXP A) + (LIST 'EXP (LIST 'MINUS A))) + 2))) + (RETURN G)))) ) +\end{multilineoutput} \\ + +coshval(1); & (AEVAL (LIST 'COSHVAL 1)) \\ + +off defn; \\ + +coshval(1); & Declare COSHVAL operator? (Y or N) \\ + +n \\ +\begin{multilineinput} +procedure coshval(a); + begin scalar g; + g := (exp(a) + exp(-a))/2; + return g + end; +\end{multilineinput} & COSHVAL \\ + +on rounded; \\ + +coshval(1); & 1.54308063482 +\end{Examples} + +\begin{Comments} +The above function \name{coshval} finds the hyperbolic cosine (cosh) of its +argument. When \name{defn} is on, you can see the Standard Lisp equivalent +of the function, but it is not entered into the system as shown by the +message \name{Declare COSHVAL operator?}. It must be reentered with +\name{defn} off to be recognized. This procedure is used as an example; a +more efficient procedure would eliminate the unnecessary local variable +with +\begin{verbatim} + procedure coshval(a); + (exp(a) + exp(-a))/2; +\end{verbatim} + +\end{Comments} +\end{Switch} + + +\begin{Switch}{DEMO} +\index{interactive}\index{output} +The \name{demo} switch is used for interactive files, causing the system +to pause after each command in the file until you type a \key{Return}. +Default is \name{off}. + +\begin{Comments} +The switch \name{demo} has no effect on top level interactive +statements. Use it when you want to slow down operations in a file so +you can see what is happening. + +You can either include the \name{on demo} command in the file, or enter +it from the top level before bringing in any file. Unlike the +\nameref{pause} command, \name{on demo} does not permit you to interrupt +the file for questions of your own. + +\end{Comments} +\end{Switch} + + +\begin{Switch}{DFPRINT} +\index{output}\index{derivative} +When \name{dfprint} is on, expressions in the differentiation operator +\nameref{df} are printed in a more ``natural'' notation, with the +differentiation variables appearing as subscripts. In addition, if the +switch \nameref{noarg} is on (the default), the arguments of the +differentiated operator are suppressed. + +\begin{Examples} +operator f; \\ +df(f x,x); & DF(F(X),X); \\ +on dfprint; \\ +ws; & F_{X} \\ +df(f(x,y),x,y); & F_{X}_{,}_{Y} \\ +off noarg; \\ +ws; & F(X,Y)_{X} +\end{Examples} + +\end{Switch} + + +\begin{Switch}{DIV} +\index{output} +When \name{div} is on, the system divides any simple factors found in +the denominator of an expression into the numerator. Default is \name{off}. + +\begin{Examples} + +on div; \\ + +a := x**2/y**2; & A := X^{2} *Y^{-2} \\ + +b := a/(3*z); & B := \rfrac{1}{3}*X^{2} *Y^{-2} *Z^{-1} \\ + +off div; \\ + +a; & \rfrac{X^{2}}{Y^{2}}\\ + +b; & \rfrac{X^{2}}{3*Y^{2} *Z} + +\end{Examples} + +\begin{Comments} +The \name{div} switch only has effect when the \nameref{pri} switch is on. +When \name{pri} is off, regardless of the setting of \name{div}, the +printing behavior is as if \name{div} were off. +\end{Comments} +\end{Switch} + + +\begin{Switch}{ECHO} +\index{output} +The \name{echo} switch is normally off for top-level entry, and on when files +are brought in. If \name{echo} is turned on at the top level, your input +statements are echoed to the screen (thus appearing twice). Default +\name{off} (but note default \name{on} for files). + +\begin{Comments} +If you want to display certain portions of a file and not others, use the +commands \name{off echo} and \name{on echo} inside the file. If you want +no display of the file, use the input command + + \name{in} {\em filename}\name{\$} + +rather than using the semicolon delimiter. + +Be careful when you use commands within a file to generate another file. +Since \name{echo} is on for files, the output file echoes input statements +(unlike its behavior from the top level). You should explicitly turn off +\name{echo} when writing output, and turn it back on when you're done. +\end{Comments} +\end{Switch} + + +\begin{Switch}{ERRCONT} +\index{error handling} +When the \name{errcont} switch is on, error conditions do not stop file +execution. Error messages will be printed whether \name{errcont} is on or +off. + +Default is \name{off}. + +\begin{Comments} +\begin{TEX} +The table below shows REDUCE behavior under the settings of \name{errcont} and +\name{int} : + + \begin{center} + \begin{tabular}{|l|l|p{9.5cm}|} +\hline +\multicolumn{3}{|c|}{Behavior in Case of Error in Files}\\ +\hline +\multicolumn{1}{|c|}{errcont} & + \multicolumn{1}{c|}{int} & + \multicolumn{1}{c|}{Behavior when errors in files are encountered}\\ +\hline +off & off & +Message is printed and parsing continues, but no further statements are +executed; no commands from keyboard accepted except \verb|bye| or +\verb|end| \\ +off & on & +Message is printed, and you are asked if you wish to continue. (This is the +default behavior) \\ +on & off & +Message is printed, and file continues to execute without pause \\ +on & on & +Message is printed, and file continues to execute without pause\\ +\hline + \end{tabular} + \end{center} +\end{TEX} +\begin{INFO} +The following describes what happens when an error occurs in a file under +each setting of \name{errcont} and \name{int}: + +Both off: Message is printed and parsing continues, but no further +statements are executed; no commands from keyboard accepted except bye or +end; + +\name{errcont} off, \name{int} on: Message is printed, and you are asked +if you wish to continue. (This is the default behavior); + +\name{errcont} on, \name{int} off: Message is printed, and file continues +to execute without pause; + +Both on: Message is printed, and file continues to execute without pause. +\end{INFO} +\end{Comments} +\end{Switch} + + +\begin{Switch}{EVALLHSEQP} +\index{equation} +Under normal circumstances, the right-hand-side of an \nameref{equation} +is evaluated but not the left-hand-side. This also applies to any +substitutions made by the \nameref{sub} operator. If both sides are to be +evaluated, the switch \name{evallhseqp} should be turned on. + +\end{Switch} + + +\begin{Switch}{EXP} +\index{simplification} +When the \name{exp} switch is on, powers and products of expressions are +expanded. Default is \name{on}. + +\begin{Examples} +(x+1)**3; & X^{3} + 3*X^{2} + 3*X + 1 \\ +(a + b*i)*(c + d*i); & A*C + A*D*I + B*C*I - B*D \\ +off exp; \\ +(x+1)**3; & (X + 1)^{3} \\ +(a + b*i)*(c + d*i); & (A + B*I)*(C + D*I) \\ +length((x+1)**2/(y+1)); & 2 +\end{Examples} + +\begin{Comments} +Note that REDUCE knows that \IFTEX{$i^2 = -1$}{i^2 = -1}. +When \name{exp} is off, equivalent expressions may not simplify to the same +form, although zero expressions still simplify to zero. Several operators +that expect a polynomial argument behave differently when \name{exp} is +off, such as \nameref{length}. Be cautious about leaving \name{exp} off. +\end{Comments} +\end{Switch} + + +\begin{Switch}{EXPANDLOGS} +\index{logarithm} +In many cases it is desirable to expand product arguments of logarithms, +or collect a sum of logarithms into a single logarithm. Since these are +inverse operations, it is not possible to provide rules for doing both at +the same time and preserve the REDUCE concept of idempotent evaluation. +As an alternative, REDUCE provides two switches \name{expandlogs} and +\nameref{combinelogs} to carry out these operations. Both are off by default. +\begin{Examples} +on expandlogs; \\ +log(x*y); & LOG(X) + LOG(Y) \\ +on combinelogs; \\ +ws; & LOG(X*Y) +\end{Examples} + +\begin{Comments} +At the present time, it is possible to have both switches on at once, +which could lead to infinite recursion. However, an expression is +switched from one form to the other in this case. Users should not rely +on this behavior, since it may change in the next release. +\end{Comments} + +\end{Switch} + + +\begin{Switch}{EZGCD} +\index{greatest common divisor}\index{polynomial} +When \name{ezgcd} and \nameref{gcd} are on, greatest common divisors are +computed using the EZ GCD algorithm that uses modular arithmetic (and is +usually faster). Default is \name{off}. + +\begin{Comments} +As a side effect of the gcd calculation, the expressions involved are +factored, though not the heavy-duty factoring of \nameref{factorize}. The +EZ GCD algorithm was introduced in a paper by J. Moses and D.Y.Y. Yun in +\meta{Proceedings of the ACM}, 1973, pp. 159-166. + +Note that the \nameref{gcd} switch must also be on for \name{ezgcd} to have +effect. +\end{Comments} +\end{Switch} + + +\begin{Switch}{FACTOR} +\index{output} +When the \name{factor} switch is on, input expressions and results are +automatically factored. + +\begin{Examples} + +on factor; \\ + +aa := 3*x**3*a + 6*x**2*y*a + 3*x**3*b + 6*x**2*y*b\\ ++ x*y*a + 2*y**2*a + x*y*b + 2*y**2*b; + & AA := (A + B)*(3*X^{2} + Y)*(X + 2*Y) \\ +off factor; \\ +aa; & + 3*A*X^{3} + 6*A*X^{2}*Y + A*X*Y + 2*A*Y^{2} + 3*B*X^{3} + 6*B*X^{2}*Y\\ ++ B*X*Y + 2*B*Y^{2} \\ +on factor; \\ +ab := x**2 - 2; & AB := X^{2} - 2 +\end{Examples} + +\begin{Comments} +REDUCE factors univariate and multivariate polynomials with +integer coefficients, finding any factors that also have integer coefficients. +The factoring is done by reducing multivariate problems to univariate +ones with symbolic coefficients, and then solving the univariate ones modulo +small primes. The results of these calculations are merged to +determine the factors of the original polynomial. The factorizer normally +selects evaluation points and primes using a random number generator. +Thus, the detailed factoring behavior may be different each time any +particular problem is tackled. + +When the \name{factor} switch is turned on, the \nameref{exp} switch is +turned off, and when the \name{factor} switch is turned off, the +\nameref{exp} switch is turned on, whether it was on previously or not. + +When the switch \nameref{trfac} is on, informative messages are generated at +each call to the factorizer. The \nameref{trallfac} switch causes the +production of a more verbose trace message. It takes precedence over +\name{trfac} if they are both on. + +To factor a polynomial explicitly and store the results, use the operator +\nameref{factorize}. +\end{Comments} +\end{Switch} + + +\begin{Switch}{FAILHARD} +\index{integration} +When the \name{failhard} switch is on, the integration operator \nameref{int} +terminates with an error message if the integral cannot be done in closed +terms. +Default is off. + +\begin{Comments} +Use the \name{failhard} switch when you are dealing with complicated integrals +and want to know immediately if REDUCE was unable to handle them. The +integration operator sometimes returns a formal integration form that is +more complicated than the original expression, when it is unable to +complete the integration. +\end{Comments} +\end{Switch} + + +\begin{Switch}{FORT} +\index{FORTRAN} +When \name{fort} is on, output is given Fortran-compatible syntax. Default +is \name{off}. + +\begin{Examples} +on fort; \\ +df(sin(7*x + y),x); & ANS=7.*COS(7*X+Y) \\ +on rounded; \\ +b := log(sin(pi/5 + n*pi)); & + B=LOG(SIN(3.14159265359*N+0.628318530718)) +\end{Examples} + +\begin{Comments} +REDUCE results can be written to a file (using \nameref{out}) and used as data +by Fortran programs when \name{fort} is in effect. \name{fort} knows about +correct statement length, continuation characters, defining a symbol when +it is first used, and other Fortran details. + +The \nameref{GENTRAN} package offers many more possibilities than the +\name{fort} switch. It produces Fortran (or C or Ratfor) code from REDUCE +procedures or structured specifications, including facilities for producing +double precision output. +\end{Comments} +\end{Switch} + +\begin{Switch}{FORTUPPER} +\index{FORTRAN} +When \name{fortupper} is on, any Fortran-style output appears in upper case. +Default is \name{off}. + +\begin{Examples} +on fort; \\ +df(sin(7*x + y),x); & ans=7.*cos(7*x+y) \\ +on fortupper; \\ +df(sin(7*x + y),x); & ANS=7.*COS(7*X+Y) \\ +\end{Examples} +\end{Switch} + + +\begin{Switch}{FULLPREC} +\index{precision}\index{rounded} +Trailing zeroes of rounded numbers to the full system precision are +normally not printed. If this information is needed, for example to get a +more understandable indication of the accuracy of certain data, the switch +\name{fullprec} can be turned on. + +\begin{Examples} +on rounded; \\ +1/2; & 0.5 \\ +on fullprec; \\ +ws; & 0.500000000000 +\end{Examples} + +\begin{Comments} +This is just an output options which neither influences +the accuracy of the computation nor does it give additional +information about the precision of the results. +See also \nameref{scientific_notation}. +\end{Comments} +\end{Switch} + +\begin{Switch}{FULLROOTS} +\index{solve}\index{polynomial} +Since roots of cubic and quartic polynomials can often be very +messy, a switch \name{fullroots} controls the production +of results in closed form. \nameref{solve} will apply the +formulas for explicit forms for degrees 3 and 4 only if +\name{fullroots} is \name{on}. Otherwise the result forms +are built using \nameref{root\_of}. Default is \name{off}. +\end{Switch} + +\begin{Switch}{GC} +\index{memory} +With the \name{gc} switch, you can turn the garbage collection messages on +or off. The form of the message depends on the particular Lisp used for +the REDUCE implementation. + +\begin{Comments} +See \nameref{reclaim} for an explanation of garbage collection. REDUCE does +garbage collection when needed even if you have turned the notices off. +\end{Comments} +\end{Switch} + + +\begin{Switch}{GCD} +\index{greatest common divisor}\index{rational expression} +When \name{gcd} is on, common factors in numerators and denominators of +expressions are canceled. Default is \name{off}. + +\begin{Examples} +\begin{multilineinput} + +(2*(f*h)**2 - f**2*g*h - (f*g)**2 - f*h**3 + f*h*g**2 + - h**4 + g*h**3)/(f**2*h - f**2*g - f*h**2 + 2*f*g*h + - f*g**2 - g*h**2 + g**2*h); +\end{multilineinput} & +\rfrac{F^{2}*G^{2} + F^{2}*G*H - 2*F^{2}*H^{2} - F*G^{2}*H + F*H^{3} - G*H^{3} + + H^{4}} + {F^{2}*G - F^{2}*H + F*G^{2} - 2*F*G*H + F*H^{2} - G^{2}*H + G*H^{2}} \\ +on gcd; \\ +ws; & \rfrac{F*G + 2*F*H + H^{2}}{F + G} \\ +e2 := a*c + a*d + b*c + b*d; & E2 := A*C + A*D + B*C + B*D \\ +off exp; \\ +e2; & (A + B)*(C + D) +\end{Examples} + +\begin{Comments} +Even with \name{gcd} off, a check is automatically made for common variable +and numerical products in the numerators and denominators of expression, +and the appropriate cancellations made. Thus the example demonstrating the +use of \name{gcd} is somewhat complicated. Note when \nameref{exp} is off, +\name{gcd} has the side effect of factoring the expression. +\end{Comments} +\end{Switch} + + +\begin{Switch}{HORNER} +\index{output}\index{polynomial} +When the \name{horner} switch is on, polynomial expressions are printed +in Horner's form for faster and safer numerical evaluation. Default +is \name{off}. The leading variable of the expression is selected as +Horner variable. To select the Horner variable explicitly use the +\nameref{korder} declaration. + +\begin{Examples} +on horner;\\ +(13p-4q)^3;& +( - 64)*q^3 + p*(624*q^2 + p*(( - 2028)*q + p*2197))\\ +korder q;\\ +ws;& +2197*p^3 + q*(( - 2028)*p^2 + q*(624*p + q*(-64))) +\end{Examples} +\end{Switch} + + +\begin{Switch}{IFACTOR} +\index{integer}\index{factorize} +When the \name{ifactor} switch is on, any integer terms appearing as a result +of the \nameref{factorize} command are factored themselves into primes. Default +is \name{off}. If the argument of \name{factorize} is an integer, +\name{ifactor} has no effect, since the integer is always factored. + +\begin{Examples} +factorize(4*x**2 + 28*x + 48); & \{4,X + 3,X + 4\} \\ +factorize(22587); & \{3,7529\} \\ +on ifactor; \\ +factorize(4*x**2 + 28*x + 48); & \{2,2,X + 4,X + 3\} \\ +factorize(22587); & \{3,7529\} +\end{Examples} + +\begin{Comments} +Constant terms that appear within nonconstant +polynomial factors are not factored. + +The \name{ifactor} switch affects only factoring done specifically +with \nameref{factorize}, not on factoring done automatically when the +\nameref{factor} switch is on. +\end{Comments} +\end{Switch} + + +\begin{Switch}{INT} +\index{interactive} +The \name{int} switch specifies an interactive mode of operation. Default +\name{on}. + +\begin{Comments} +There is no reason to turn \name{int} off during interactive calculations, +since there are no benefits to be gained. If you do have \name{int} off +while inputting a file, and REDUCE finds an error, it prints the message +``Continuing with parsing only." In this state, REDUCE accepts only +\nameref{end}\name{;} or \nameref{bye}\name{;} from the keyboard; +everything else is ignored, even the command \name{on int}. +\end{Comments} +\end{Switch} + + +\begin{Switch}{INTSTR} +\index{output} +If \name{intstr} (for ``internal structure'') is on, arguments of an +operator are printed in a more structured form. + +\begin{Examples} +operator f; \\ +f(2x+2y); & F(2*X + 2*Y) \\ +on intstr; \\ +ws; & F(2*(X + Y)) +\end{Examples} + +\end{Switch} + + +\begin{Switch}{LCM} +\index{rational expression} +The \name{lcm} switch instructs REDUCE to compute the least common multiple +of denominators whenever rational expressions occur. Default is \name{on}. + +\begin{Examples} +off lcm; \\ +z := 1/(x**2 - y**2) + 1/(x-y)**2; + & Z := \rfrac{2*X*(X - Y)}{X^{4} - 2*X^{3}*Y + +2*X*Y^{3} - Y^{4}} \\ +on lcm; \\ +z; & \rfrac{2*X*(X - Y)}{X^{4} - 2*X^{3}*Y + 2*X*Y +^{3} - Y^{4}} \\ +zz := 1/(x**2 - y**2) + 1/(x-y)**2; + & ZZ := \rfrac{2*X}{X^{3} - X^{2}*Y - X*Y^{2} + + Y^{3}} \\ +on gcd; \\ +z; & \rfrac{2*X}{X^{3} - X^{2}*Y - X*Y^{2} + Y^{3} +} +\end{Examples} + +\begin{Comments} +Note that \name{lcm} has effect only when rational expressions are first +combined. It does not examine existing structures for simplifications on +display. That is shown above when \IFTEX{$z$}{z} is entered with +\name{lcm} off. It remains unsimplified even after \name{lcm} is turned +back on. However, a new variable containing the same expression is +simplified on entry. The switch \nameref{gcd} does examine existing +structures, as shown in the last example line above. + +Full greatest common divisor calculations become expensive if work with +large rational expressions is required. A considerable savings of time +can be had if a full gcd check is made only when denominators are combined, +and only a partial check for numerators. This is the effect of the \name{lcm} +switch. +\end{Comments} +\end{Switch} + + +\begin{Switch}{LESSSPACE} +\index{output} +You can turn on the switch \name{lessspace} if you want fewer +blank lines in your output. +\end{Switch} + + +\begin{Switch}{LIMITEDFACTORS} +\index{factorize}\index{polynomial} +To get limited factorization in cases where it is too expensive to use +full multivariate polynomial factorization, the switch +\name{limitedfactors} can be turned on. In that case, only ``inexpensive'' +factoring operations, such as square-free factorization, will be used +when \nameref{factorize} is called. + +\begin{Examples} +a := (y-x)^2*(y^3+2x*y+5)*(y^2-3x*y+7)$ \\ +factorize a; & +\begin{multilineoutput}{7cm} +\{ - X + Y, + X - Y, + 2*X*Y + Y^{3} + 5, + 3*X*Y - Y^{2} - 7\} +\end{multilineoutput} \\ +on limitedfactors; \\ +factorize a; & +\begin{multilineoutput}{7cm} +\{ - X + Y, + X - Y, + 6*X^{2}*Y^{2} + 3*X*Y^{4} - 2*X*Y^{3} + X*Y - Y^{5} - 7*Y^{3} - 5*Y^{2} - 35\} +\end{multilineoutput} +\end{Examples} + +\end{Switch} + + +\begin{Switch}{LIST} +The \name{list} switch causes REDUCE to print each term in any sum on +separate lines. + +\begin{Examples} +x**2*(y**2 + 2*y) + x*(y**2 + z)/(2*a); + & \rfrac{X*(2*A*X*Y^{2} + 4*A*X*Y + Y^{2} + +Z)}{2*A} \\ +on list; \\ +ws; & +\begin{multilineoutput}{6cm} +(X*(2*A*X*Y^{2} + + 4*A*X*Y + + Y^{2} + + Z))/(2*A) +\end{multilineoutput} +\end{Examples} +\end{Switch} + + +\begin{Switch}{LISTARGS} +\index{list}\index{argument}\index{operator} +If an operator other than those specifically defined for lists is given a +single argument that is a list, then the result of this operation will be +a list in which that operator is applied to each element of the list. +This process can be inhibited globally by turning on the switch +\name{listargs}. + +\begin{Examples} +log {a,b,c}; & {LOG(A),LOG(B),LOG(C)} \\ +on listargs; \\ +log {a,b,c}; & LOG({A,B,C}) +\end{Examples} + +\begin{Comments} +It is possible to inhibit such distribution for a specific operator by +using the declaration \nameref{listargp}. In addition, if an operator has +more than one argument, no such distribution occurs, so \name{listargs} +has no effect. +\end{Comments} + +\end{Switch} + + +\begin{Switch}{MCD} +\index{rational expression} +When \name{mcd} is on, sums and differences of rational expressions are put +on a common denominator. Default is \name{on}. + +\begin{Examples} +a/(x+1) + b/5; & \rfrac{5*A + B*X + B}{5*(X + 1)} \\ +off mcd; \\ +a/(x+1) + b/5; & (X + 1)^{-1}*A + 1/5*B \\ +1/6 + 1/7; & 13/42 +\end{Examples} + +\begin{Comments} +Even with \name{mcd} off, rational expressions involving only numbers are still +put over a common denominator. + +Turning \name{mcd} off is useful when explicit negative powers are needed, +or if no greatest common divisor calculations are desired, or when +differentiating complicated rational expressions. Results when \name{mcd} +is off are no longer in canonical form, and expressions equivalent to zero +may not simplify to 0. Some operations, such as factoring cannot be done +while \name{mcd} is off. This option should therefore be used with some +caution. Turning \name{mcd} off is most valuable in intermediate parts of +a complicated calculation, and should be turned back on for the last stage. +\end{Comments} +\end{Switch} + + +\begin{Switch}{MODULAR} +\index{modular} +When \name{modular} is on, polynomial coefficients are reduced by the +modulus set by \nameref{setmod}. If no modulus has been set, \name{modular} +has no effect. + +\begin{Examples} +setmod 2; & 1 \\ +on modular; \\ +(x+y)**2; & X^{2} + Y^{2} \\ +145*x**2 + 20*x**3 + 17 + 15*x*y; + & X^{2} + X*Y + 1 +\end{Examples} + +\begin{Comments} +Modular operations are only conducted on the coefficients, not the +exponents. The modulus is not restricted to being prime. When the modulus +is prime, division by a number not relatively prime to the modulus results +in a \meta{Zero divisor} error message. When the modulus is a composite +number, division by a power of the modulus results in an error message, but +division by an integer which is a factor of the modulus does not. +The representation of modular number can be influenced by +\nameref{balanced\_mod}. +\end{Comments} +\end{Switch} + + +\begin{Switch}{MSG} +\index{output} +When \name{msg} is off, the printing of warning messages is suppressed. Error +messages are still printed. + +\begin{Comments} +Warning messages include those about redimensioning an \nameref{array} +or declaring an \nameref{operator} where one is expected. +\end{Comments} +\end{Switch} + + +\begin{Switch}{MULTIPLICITIES} +\index{solve} +When \nameref{solve} is applied to a set of equations with multiple roots, +solution multiplicities are normally stored in the global variable +\nameref{root\_multiplicities} rather than the solution list. If you want +the multiplicities explicitly displayed, the switch \name{multiplicities} +should be turned on. In this case, \name{root_multiplicities} has no value. + +\begin{Examples} +solve(x^2=2x-1,x); & {X=1} \\ +root_multiplicities; & {2} \\ +on multiplicities; \\ +solve(x^2=2x-1,x); & {X=1,X=1} \\ +root_multiplicities; & +\end{Examples} + +\end{Switch} + + +\begin{Switch}{NAT} +\index{output} +When \name{nat} is on, output is printed to the screen in natural form, with +raised exponents. \name{nat} should be turned off when outputting expressions +to a file for future input. Default is \name{on}. + +\begin{Examples} +(x + y)**3; & X^{3} + 3*X^{2}*Y + 3*X*Y^{2} + Y^{3} \\ +off nat; \\ +(x + y)**3; & X**3 + 3*X**2*Y + 3*X*Y**2 + Y**3\$ \\ +on fort; \\ +(x + y)**3; & ANS=X**3+3.*X**2*Y+3.*X*Y**2+Y**3 +\end{Examples} +\begin{Comments} +With \name{nat} off, a dollar sign is printed at the end of each expression. +An output file written with \name{nat} off is ready to be read into REDUCE +using the command \nameref{in}. +\end{Comments} +\end{Switch} + + +\begin{Switch}{NERO} +\index{output} +When \name{nero} is on, zero assignments (such as matrix elements) are not +printed. + +\begin{Examples} +matrix a; +a := mat((1,0),(0,1)); & \begin{multilineoutput}{6cm} +A(1,1) := 1 +A(1,2) := 0 +A(2,1) := 0 +A(2,2) := 1 +\end{multilineoutput}\\ +on nero; \\ +a; & \begin{multilineoutput}{6cm} +MAT(1,1) := 1 +MAT(2,2) := 1 +\end{multilineoutput}\\ +a(1,2); & \explanationo{nothing is printed.} \\ +b := 0; & \explanationo{nothing is printed.} \\ +off nero; \\ +b := 0; & B := 0 +\end{Examples} +\begin{Comments} +\name{nero} is often used when dealing with large sparse matrices, to avoid +being overloaded with zero assignments. +\end{Comments} +\end{Switch} + + +\begin{Switch}{NOARG} +\index{output}\index{derivative} +When \nameref{dfprint} is on, expressions in the differentiation operator +\nameref{df} are printed in a more ``natural'' notation, with the +differentiation variables appearing as subscripts. When \name{noarg} +is on (the default), the arguments of the differentiated operator are also +suppressed. + +\begin{Examples} +operator f; \\ +df(f x,x); & DF(F(X),X); \\ +on dfprint; \\ +ws; & F_{X} \\ +off noarg; \\ +ws; & F(X)_{X} +\end{Examples} + +\end{Switch} + + +\begin{Switch}{NOLNR} +\index{integration} +When \name{nolnr} is on, the linear properties of the integration operator +\nameref{int} are suppressed if the integral cannot be found in closed terms. + +\begin{Comments} +REDUCE uses the linear properties of integration to attempt to break down +an integral into manageable pieces. If an integral cannot be found in +closed terms, these pieces are returned. When the \name{nolnr} switch is off, +as many of the pieces as possible are integrated. When it is on, if any piece +fails, the rest of them remain unevaluated. +\end{Comments} +\end{Switch} + + +%\begin{Switch}{NORNDBF} +% +%***** To be added ***** +% +%\end{Switch} + + +\begin{Switch}{NOSPLIT} +\index{output} +Under normal circumstances, the printing routines try to break an expression +across lines at a natural point. This is a fairly expensive process. If +you are not overly concerned about where the end-of-line breaks come, you +can speed up the printing of expressions by turning off the switch +\name{nosplit}. This switch is normally on. + +\end{Switch} + + +\begin{Switch}{NUMVAL} +\index{rounded} +With \nameref{rounded} on, elementary functions with numerical arguments +will return a numerical answer where appropriate. If you wish to inhibit +this evaluation, \name{numval} should be turned off. It is normally on. + +\begin{Examples} +on rounded; \\ +cos 3.4; & - 0.966798192579 \\ +off numval; \\ +cos 3.4; & COS(3.4) +\end{Examples} + +\end{Switch} + + +\begin{Switch}{OUTPUT} +\index{output} +When \name{output} is off, no output is printed from any REDUCE calculation. +The calculations have their usual effects other than printing. Default is +\name{on}. + +\begin{Comments} +Turn output \name{off} if you do not wish to see output when executing +large files, or to save the time REDUCE spends formatting large expressions +for display. Results are still available with \nameref{ws}, or in their +assigned variables. +\end{Comments} +\end{Switch} + + +\begin{Switch}{OVERVIEW} +\index{factorize} +When \name{overview} is on, the amount of detail reported by the factorizer +switches \nameref{trfac} and \nameref{trallfac} is reduced. + +\end{Switch} + + +\begin{Switch}{PERIOD} +\index{output}\index{integer} +When \name{period} is on, periods are added after integers in +Fortran-compatible output (when \nameref{fort} is on). There is no effect +when \name{fort} is off. Default is \name{on}. +\end{Switch} + + +\begin{Switch}{PRECISE} +\index{simplification}\index{square root} +When the \name{precise} switch is on, simplification of roots of even +powers returns absolute values, a more precise answer mathematically. +Default is \name{on}. + +\begin{Examples} +sqrt(x**2); & X \\ +(x**2)**(1/4); & SQRT(X) \\ +on precise; \\ +sqrt(x**2); & ABS(X) \\ +(x**2)**(1/4); & SQRT(ABS(X)) +\end{Examples} + +\begin{Comments} +In many types of mathematical work, simplification of powers and surds can +proceed by the fastest means of simplifying the exponents arithmetically. +When it is important to you that the positive root be returned, turn +\name{precise} on. One situation where this is important is when graphing +square-root expressions such as \IFTEX{$\sqrt{x^2+y^2}$}{sqrt(x^2+y^2)} to +avoid a spike caused by REDUCE simplifying +\IFTEX{$\sqrt{y^2}$}{sqrt(y^2)} to \IFTEX{$y$}{y} when \IFTEX{$x$}{x} is +zero. +\end{Comments} +\end{Switch} + + +\begin{Switch}{PRET} +\index{output} +When \name{pret} is on, input is printed in standard REDUCE format and then +evaluated. + +\begin{Examples} +on pret; \\ + (x+1)^3; & +\begin{multilineoutput}{6cm} + (x + 1)**3; +X^{3} + 3*X^{2} + 3*X + 1 +\end{multilineoutput} \\ +\begin{multilineinput} + +procedure fac(n); + if not (fixp(n) and n>=0) + then rederr "Choose nonneg. integer only" + else for i := 0:n-1 product i+1; +\end{multilineinput} & +\begin{multilineoutput}{8cm} +procedure fac n; + if not (fixp n and n>=0) + then rederr "Choose nonneg. integer only" + else for i := 0:n - 1 product i + 1; + +FAC +\end{multilineoutput}\\ + +fac 5; & \begin{multilineoutput}{6cm} +fac 5; +120 +\end{multilineoutput} + +\end{Examples} + +\begin{Comments} +Note that all input is converted to lower case except strings (which keep +the same case) all operators with a single argument have had the +parentheses removed, and all infix operators have had a space added on each +side. In addition, syntactical constructs like +\name{if}\ldots\name{then}\ldots\name{else} are printed in a standard format. +\end{Comments} +\end{Switch} + + +\begin{Switch}{PRI} +\index{output} +When \name{pri} is on, the declarations \nameref{order} and \nameref{factor} can +be used, and the switches \nameref{allfac}, \nameref{div}, \nameref{rat}, +and \nameref{revpri} take effect when they are on. Default is \name{on}. + +\begin{Comments} +Printing of expressions is faster with \name{pri} off. The expressions are +then returned in one standard form, without any of the display options that +can be used to feature or display various parts of the expression. You can +also gain insight into REDUCE's representation of expressions with +\name{pri} off. +\end{Comments} +\end{Switch} + + +\begin{Switch}{RAISE} +\index{input}\index{character} +When \name{raise} is on, lower case letters are automatically converted to +upper case on input. \name{raise} is normally on. + +\begin{Comments} +This conversion affects the internal representation of the letter, and is +independent of the case with which a letter is printed, which is normally +lower case. +\end{Comments} + +\end{Switch} + + +\begin{Switch}{RAT} +\index{output} +When the \name{rat} switch is on, and kernels have been selected to display +with the \nameref{factor} declaration, the denominator is printed with each +term rather than one common denominator at the end of an expression. + +\begin{Examples} +(x+1)/x + x**2/sin y; + & \rfrac{SIN(Y)*X + SIN(Y) + X^{3}}{SIN(Y)*X} \ +\ +factor x; \\ +(x+1)/x + x**2/sin y; + & \rfrac{X^{3} + X*SIN(Y) + SIN(Y)}{X*SIN(Y)} \ +\ +on rat; \\ +(x+1)/x + x**2/sin y; + & \rfrac{X^{2}}{SIN(Y)} + 1 + X^{-1} +\end{Examples} + +\begin{Comments} +The \name{rat} switch only has effect when the \nameref{pri} switch is on. +When \name{pri} is off, regardless of the setting of \name{rat}, the +printing behavior is as if \name{rat} were off. \name{rat} only has +effect upon the display of expressions, not their internal form. +\end{Comments} +\end{Switch} + + +\begin{Switch}{RATARG} +\index{rational expression}\index{polynomial} +When \name{ratarg} is on, rational expressions can be given to operators +such as \nameref{coeff} and \nameref{lterm} that normally require +polynomials in one of their arguments. When \name{ratarg} is off, rational +expressions cause an error message. + +\begin{Examples} +aa := x/y**2 + 1/x + y/x**2; + & AA := \rfrac{X^{3} + X*Y^{2} + Y^{3}}{X^{2}*Y^{2}} \\ +coeff(aa,x); & + ***** \rfrac{X^{3} + X*Y^{2} + Y^{3}}{X^{2}*Y^{2}} invalid as POLYNOMIAL\\ +on ratarg; \\ +coeff(aa,x); + & \{\rfrac{Y}{X^{2}},\rfrac{1}{X^{2}},0,\rfrac{1}{X^{2}*Y^{2}}\} +\end{Examples} +\end{Switch} + + +\begin{Switch}{RATIONAL} +\index{rational expression}\index{polynomial} +When \name{rational} is on, polynomial expressions with rational coefficients +are produced. + +\begin{Examples} +x/2 + 3*y/4; & \rfrac{2*X + 3*Y}{4} \\ +(x**2 + 5*x + 17)/2; & \rfrac{X^{2} + 5*X + 17}{2} \\ +on rational; \\ +x/2 + 3y/4; & \rfrac{1}{2}*(X + \rfrac{3}{2}*Y) \\ +(x**2 + 5*x + 17)/2; & \rfrac{1}{2}*(X^{2} + 5*X + 17) +\end{Examples} + +\begin{Comments} +By using \name{rational}, polynomial expressions with rational +coefficients can be used in some commands that expect polynomials. With +\name{rational} off, such a polynomial becomes a rational expression, with +denominator the least common multiple of the denominators of the rational +number coefficients. % The \nameref{factorize} command does not accept +% polynomials with rational coefficients. +\end{Comments} +\end{Switch} + + +\begin{Switch}{RATIONALIZE} +\index{rational expression}\index{simplification}\index{complex} +When the \name{rationalize} switch is on, denominators of rational expressions +that contain complex numbers or root expressions are simplified by +multiplication by their conjugates. + +\begin{Examples} +qq := (1+sqrt(3))/(sqrt(3)-7); & QQ := \rfrac{SQRT(3) + 1}{SQRT(3) - 7} \\ +on rationalize; \\ +qq; & \rfrac{- 4*SQRT(3) - 5}{23} \\ +2/(4 + 6**(1/3)); & \rfrac{6^{2/3} - 4*6^{1/3} + 16}{35} \\ +(i-1)/(i+3); & \rfrac{2*I - 1}{5} \\ +off rationalize; \\ +(i-1)/(i+3); & \rfrac{I - 1}{I + 3} +\end{Examples} + +\end{Switch} + + +\begin{Switch}{RATPRI} +\index{output}\index{rational expression} +When the \name{ratpri} switch is on, rational expressions and fractions are +printed as two lines separated by a fraction bar, rather than in a linear +style. Default is \name{on}. + +\begin{Examples} +3/17; & \rfrac{3}{17} \\ +2/b + 3/y; & \rfrac{3*B + 2*Y}{B*Y} \\ +off ratpri; \\ +3/17; & 3/17 \\ +2/b + 3/y; & (3*B + 2*Y)/(B*Y) +\end{Examples} +\end{Switch} + + +\begin{Switch}{REVPRI} +\index{output} +When the \name{revpri} switch is on, terms are printed in reverse order from +the normal printing order. + +\begin{Examples} +x**5 + x**2 + 18 + sqrt(y); & SQRT(Y) + X^{5} + X^{2} + 18 \\ +a + b + c + w; & A + B + C + W \\ +on revpri; \\ +x**5 + x**2 + 18 + sqrt(y); & 17 + X^{2} + X^{5} + SQRT(Y) \\ +a + b + c + w; & W + C + B + A +\end{Examples} + +\begin{Comments} +Turn \name{revpri} on when you want to display a polynomial in ascending +rather than descending order. +\end{Comments} +\end{Switch} + + +\begin{Switch}{RLISP88} +\index{lisp} +Rlisp '88 is a superset of the Rlisp that has been traditionally used for +the support of REDUCE. It is fully documented in the book Marti, J.B., +``{RLISP} '88: An Evolutionary Approach to Program Design and Reuse'', +World Scientific, Singapore (1993). It supports different looping +constructs from the traditional Rlisp, and treats ``-'' as a letter unless +separated by spaces. Turning on the switch \name{rlisp88} converts to +Rlisp '88 parsing conventions in symbolic mode, and enables the use of +Rlisp '88 extensions. Turning off the switch reverts to the traditional +Rlisp and the previous mode ( (\nameref{symbolic} or \nameref{algebraic}) +in force before \name{rlisp88} was turned on. + +\end{Switch} + + +\begin{Switch}{ROUNDALL} +\index{rounded}\index{rational expression}\index{floating point} +In \nameref{rounded} mode, rational numbers are normally converted to a +floating point representation. If \name{roundall} is off, this conversion +does not occur. \name{roundall} is normally \name{on}. + +\begin{Examples} +on rounded; \\ +1/2; & 0.5 \\ +off roundall; \\ +1/2; \rfrac{1}{2} +\end{Examples} + +\end{Switch} + + +\begin{Switch}{ROUNDBF} +When \nameref{rounded} is on, the normal defaults cause underflows to be +converted to zero. If you really want the small number that results in +such cases, \name{roundbf} can be turned on. + +\begin{Examples} +on rounded; \\ +exp(-100000.1^2); & 0 \\ +on roundbf; \\ +exp(-100000.1^2); & 1.18441281937E-4342953505 +\end{Examples} + +\begin{Comments} +If a polynomial is input in \nameref{rounded} mode at the default +precision into any \nameref{roots} function, and it is not possible to +represent any of the coefficients of the polynomial precisely in the +system floating point representation, the switch \name{roundbf} will be +automatically turned on. All rounded computation will use the internal +bigfloat representation until the user subsequently turns \name{roundbf} +off. (A message is output to indicate that this condition is in effect.) +\end{Comments} +\end{Switch} + + +\begin{Switch}{ROUNDED} +\index{floating point} +When \name{rounded} is on, floating-point arithmetic is enabled, with +precision initially at a system default value, which is usually 12 digits. +The precise number can be found by the command \nameref{precision}(0). +\begin{Examples} +pi; & PI \\ +35/217; & \rfrac{5}{31} \\ +on rounded; \\ +pi; & 3.14159265359 \\ +35/217; & 0.161 \\ +sqrt(3); & 1.73205080756 +\end{Examples} +\begin{Comments} +If more than the default number of decimal places are required, use the +\nameref{precision} command to set the required number. +\end{Comments} +\end{Switch} + + +\begin{Switch}{SAVESTRUCTR} +\index{STRUCTR OPERATOR} +When \name{savestructr} is on, results of the \nameref{structr} command are +returned as a list whose first element is the representation for the +expression and the remaining elements are equations showing the +relationships of the generated variables. + +\begin{Examples} +off exp; \\ +structr((x+y)^3 + sin(x)^2); & +\begin{multilineoutput}{6cm} +ANS3 + where + ANS3 := ANS1^{3} + ANS2^{2} + ANS2 := SIN(X) + ANS1 := X + Y +\end{multilineoutput}\\ +ans3; & ANS3 \\ +on savestructr; \\ +structr((x+y)^{3} + sin(x)^{2}); & +{ANS3,ANS3=ANS1^{3} + ANS2^{2},ANS2=SIN(X),ANS1=X + Y} \\ +ans3 where rest ws; & +(X + Y)^{3} + SIN(X)^{2} +\end{Examples} +\begin{Comments} +In normal operation, \nameref{structr} is only a display command. With +\name{savestructr} on, you can access the various parts of the expression +produced by \name{structr}. + +The generic system names use the stem \name{ANS}. You can change this to your +own stem by the command \nameref{varname}. REDUCE adds integers to this stem +to make unique identifiers. +\end{Comments} +\end{Switch} + + +\begin{Switch}{SOLVESINGULAR} +\index{solve} +When \name{solvesingular} is on, singular or underdetermined systems of +linear equations are solved, using arbitrary real, complex or integer +variables in the answer. Default is \name{on}. + +\begin{Examples} +solve({2x + y,4x + 2y},{x,y}); & + \{\{X= - \rfrac{ARBCOMPLEX(1)}{2},Y=ARBCOMPLEX(1)\}\} \\ +solve({7x + 15y - z,x - y - z},{x,y,z}); & +\begin{multilineoutput}{6cm} +\{\{X=\rfrac{8*ARBCOMPLEX(3)}{11} + Y= - \rfrac{3*ARBCOMPLEX(3)}{11} + Z=ARBCOMPLEX(3)\}\} +\end{multilineoutput}\\ +off solvesingular; \\ +solve({2x + y,4x + 2y},{x,y}); & + ***** SOLVE given singular equations \\ +solve({7x + 15y - z,x - y - z},{x,y,z}); & + ***** SOLVE given singular equations +\end{Examples} +\begin{Comments} + +The integer following the identifier \nameref{arbcomplex} above is assigned by +the system, and serves to identify the variable uniquely. It has no other +significance. +\end{Comments} +\end{Switch} + + +\begin{Switch}{TIME} +\index{time} +When \name{time} is on, the system time used in executing each REDUCE +statement is printed after the answer is printed. + +\begin{Examples} +on time; & Time: 4940 ms \\ +df(sin(x**2 + y),y); & +\begin{multilineoutput}{6cm} +COS(X + Y^{2}) +Time: 180 ms +\end{multilineoutput}\\ +solve(x**2 - 6*y,x); & +\begin{multilineoutput}{6cm} +\{X= - SQRT(Y)*SQRT(6), + X=SQRT(Y)*SQRT(6)\} +Time: 320 ms +\end{multilineoutput} +\end{Examples} +\begin{Comments} +When \name{time} is first turned on, the time since the beginning of the +REDUCE session is printed. After that, the time used in computation, +(usually in milliseconds, though this is system dependent) is printed after +the results of each command. Idle time or time spent typing in commands is +not counted. If \name{time} is turned off, the first reading after it is +turned on again gives the time elapsed since it was turned off. The time +printed is CPU or wall clock time, depending on the system. +\end{Comments} +\end{Switch} + + +\begin{Switch}{TRALLFAC} +\index{factorize} +When \name{trallfac} is on, a more detailed trace of factorizer calls is +generated. + +\begin{Comments} +The \name{trallfac} switch takes precedence over \nameref{trfac} if they are +both on. \name{trfac} gives a factorization trace with less detail in it. +When the \nameref{factor} switch is on also, all input polynomials are sent to +the factorizer automatically and trace information is generated. The +\nameref{out} command saves the results of the factoring, but not the trace. +% You need to use the \name{dribble} command to save the trace text to a file. +\end{Comments} +\end{Switch} + + +\begin{Switch}{TRFAC} +\index{factorize} +When \name{trfac} is on, a narrative trace of any calls to the factorizer is +generated. Default is \name{off}. + +\begin{Comments} +When the switch \nameref{factor} is on, and \name{trfac} is on, every input +polynomial is sent to the factorizer, and a trace generated. With +\name{factor} off, only polynomials that are explicitly factored with the +command \nameref{factorize} generate trace information. + +% Use the \name{dribble} or \name{logfile} command to save the trace text to +% a file. +The \nameref{out} command saves the results of the factoring, but not +the trace. The \nameref{trallfac} switch gives trace information to a +greater level of detail. +\end{Comments} +\end{Switch} + +\begin{Switch}{TRIGFORM} +\index{solve}\index{polynomial} +When \nameref{fullroots} is on, \nameref{solve} will compute the +roots of a cubic or quartic polynomial is closed form. When +\name{trigform} is on, the roots will be expressed by trigonometric +forms. Otherwise nested surds are used. Default is \name{on}. +\end{Switch} + + +\begin{Switch}{TRINT} +\index{integration} +When \name{trint} is on, a narrative tracing various steps in the +integration process is produced. + +\begin{Comments} +%Use the \name{dribble} or \name{logfile} command to save this text to a file. +The \nameref{out} command saves the results of the integration, but not the +trace. +\end{Comments} +\end{Switch} + +\begin{Switch}{TRNONLNR} +\index{solve} +When \name{trnonlnr} is on, a narrative tracing various steps in +the process for solving non-linear equations is produced. + +\begin{Comments} +\name{trnonlnr} can only be used after the solve package has been loaded +(e.g., by an explicit call of \nameref{load\_package}). The \nameref{out} +command saves the results of the equation solving, but not the trace. +\end{Comments} +\end{Switch} + + +\begin{Switch}{VAROPT} +\index{solve} +When \name{varopt} is on, the sequence of variables is optimized by +\nameref{solve} with respect to execution speed. Otherwise, the sequence +given in the call to \nameref{solve} is preserved. Default is \name{on}. + +In combination with the switch \nameref{arbvars}, \name{varopt} can be used +to control variable elimination. + +\begin{Examples} +off arbvars; \\ +solve({x+2z,x-3y},{x,y,z}); & + \{\{y=\rfrac{x}{3},z= - \rfrac{x}{2}\}\} \\ +solve({x*y=1,z=x},{x,y,z}); & + \{\{z=x,y=\rfrac{1}{x}\}\} \\ +off varopt; \\ +solve({x+2z,x-3y},{x,y,z}); & + \{\{x= - 2*z,y= - \rfrac{2*z}{3}\}\} \\ +solve({x*y=1,z=x},{x,y,z}); & + \{\{y=\rfrac{1}{z},x=z\}\} \\ +\end{Examples} +\end{Switch} + Index: r36/help/syntax.tex ================================================================== --- r36/help/syntax.tex +++ r36/help/syntax.tex @@ -1,1710 +1,1710 @@ -\section{Syntax} - -\begin{Command}[semicolon]{;} -The semicolon is a statement delimiter, indicating results are to be printed -when used in interactive mode. - -\begin{Examples} -(x+1)**2; & X^{2} + 2*X + 1 \\ -df(x**2 + 1,x); & 2*X -\end{Examples} - -\begin{Comments} -Entering a \key{Return} without a semicolon or dollar sign results in a -prompt on the following line. A semicolon or dollar sign can be -added at this point to execute the statement. In interactive mode, a -statement that is ended with a semicolon and \key{Return} has its results -printed on the screen. - -Inside a group statement \name{<<}\ldots\name{>>} -or a \name{begin}\ldots\name{end} block, a -semicolon or dollar sign separates individual REDUCE statements. Since -results are not printed from a block without a specific \name{return} -statement, there is no difference between using the semicolon or dollar -sign. In a group statement, the last value produced is the value -returned by the group statement. Thus, if a semicolon or dollar sign is -placed between the last statement and the ending brackets, the group -statement returns the value 0 or {\em nil}, rather than the value of the -last statement. -\end{Comments} -\end{Command} - - -\begin{Command}[dollar]{$} -The dollar sign is a statement delimiter, indicating results are not to be -printed when used in interactive mode. - -\begin{Examples} - -(x+1)**2$ & -\explanationo{The workspace is set to $x^{2} + 2x + 1$ - but nothing shows on the screen} \\ -ws; & X^{2} + 2*X + 1 -\end{Examples} - -\begin{Comments} -Entering a \key{Return} without a semicolon or dollar sign results in a -prompt on the following line. A semicolon or dollar sign can -be added at this point to execute the statement. In interactive mode, a -statement that ends with a dollar sign \name{\$} and a \key{Return} is -executed, but the results not printed. - -Inside a \nameref{group} statement \name{<<}\ldots\name{>>} -or a \name{begin}\ldots\name{end} \nameref{block}, a -semicolon or dollar sign separates individual REDUCE statements. Since -results are not printed from a \nameref{block} without a specific -\nameref{return} -statement, there is no difference between using the semicolon or dollar -sign. - -In a group statement, the last value produced is the value returned by the -group statement. Thus, if a semicolon or dollar sign is placed between the -last statement and the ending brackets, the group statement returns the -value 0 or {\em nil}, rather than the value of the last statement. - -\end{Comments} -\end{Command} - -\begin{Command}[percent]{%} -The percent sign is used to precede comments; everything from a percent -to the end of the line is ignored. - -\begin{Examples} - -df(x**3 + y,x);\% This is a comment \key{Return} & 3*X^{2} \\ -int(3*x**2,x) \%This is a comment; \key{Return} \\ - -\explanation{A prompt is given, waiting for the semicolon that was not -detected in the comment} -\end{Examples} - -\begin{Comments} -Statement delimiters \name{;} and \name{\$} are not detected between a -percent sign and the end of the line. -\end{Comments} -\end{Command} - - -% \begin{Operator}[ampersand]{&} -% -% ***** To be added ***** -% -% \end{Operator} -% -% -\begin{Operator}[dot]{.} -\index{list} -The . (dot) infix binary operator adds a new item to the beginning of an -existing \nameref{list}. In high energy physics expressions, -it can also be used -to represent the scalar product of two Lorentz four-vectors. - -\begin{Syntax} -\meta{item} \name{.} \meta{list} -\end{Syntax} - -\meta{item} can be any REDUCE scalar expression, including a list; -\meta{list} must be a \nameref{list} to avoid producing an error message. -The dot operator is right associative. - -\begin{Examples} - -liss := a . \{\}; & LISS := \{A\} \\ -liss := b . liss; & LISS := \{B,A\} \\ -newliss := liss . liss; & NEWLISS := \{\{B,A\},B,A\} \\ -firstlis := a . b . \{c\}; & FIRSTLIS := \{A,B,C\} \\ -secondlis := x . y . \{z\}; & SECONDLIS := \{X,Y,Z\} \\ -for i := 1:3 sum part(firstlis,i)*part(secondlis,i); - & A*X + B*Y + C*Z -\end{Examples} -\end{Operator} - - -\begin{Operator}[assign]{:=} -\index{assign} -The \name{:=} is the assignment operator, assigning the value on the right-hand -side to the identifier or other valid expression on the left-hand side. - -\begin{Syntax} - \meta{restricted\_expression} \name{:=} \meta{expression} -\end{Syntax} - -\meta{restricted\_expression} is ordinarily a single identifier, though simple -expressions may be used (see Comments below). \meta{expression} is any -valid REDUCE expression. If \meta{expression} is a \nameref{matrix} -identifier, then -\meta{restricted\_expression} can be a matrix identifier (redimensioned if -necessary) which has each element set to the corresponding elements -of the identifier on the right-hand side. - -\begin{Examples} -a := x**2 + 1; & A := X^{2} + 1 \\ -a; & X^{2} + 1 \\ -first := second := third; & FIRST := SECOND := THIRD \\ -first; & THIRD \\ -second; & THIRD \\ -b := for i := 1:5 product i; & B := 120 \\ -b; & 120 \\ -w + (c := x + 3) + z; & W + X + Z + 3 \\ -c; & X + 3 \\ -y + b := c; & Y + B := C \\ -y; & - (B - C) -\end{Examples} - -\begin{Comments} -The assignment operator is right associative, as shown in the second and -third examples. A string of such assignments has all but the last -item set to the value of the last item. Embedding an assignment statement -in another expression has the side effect of making the assignment, as well -as causing the given replacement in the expression. - -Assignments of values to expressions rather than simple identifiers (such as in -the last example above) can also be done, subject to the following remarks: -\begin{itemize} - -\item[(i)] -If the left-hand side is an identifier, an operator, or a power, the -substitution rule is added to the rule table. - -\item[(ii)] -If the operators \name{- + /} appear on the left-hand side, all but the first -term of the expression is moved to the right-hand side. - -\item[(iii)] -If the operator \name{*} appears on the left-hand side, any constant terms are -moved to the right-hand side, but the symbolic factors remain. -\end{itemize} - -Assignment is valid for \nameref{array} elements, but not for entire arrays. -The assignment operator can also be used to attach functionality to operators. - -A recursive construction such as \name{a := a + b} is allowed, but when -\name{a} is referenced again, the process of resubstitution continues -until the expression stack overflows (you get an error message). -Recursive assignments can be done safely inside controlled loop -expressions, such as \nameref{for}\ldots or \nameref{repeat}\ldots\name{until}. - -\end{Comments} -\end{Operator} - - -\begin{Operator}[equalsign]{=} -The \name{=} operator is a prefix or infix equality comparison operator. - -\begin{Syntax} - \name{=}\(\meta{expression}\name{,}\meta{expression}\) - or - \meta{expression} \name{=} \meta{expression} -\end{Syntax} - -\meta{expression} can be any REDUCE scalar expression. - -\begin{Examples} -a := 4; & A := 4 \\ -if =(a,10) then write "yes" else write "no"; - & no \\ -b := c; & B := C \\ -if b = c then write "yes" else write "no"; - & yes \\ -on rounded; \\ -if 4.0 = 4 then write "yes" else write "no"; - & yes -\end{Examples} - -\begin{Comments} -This logical equality operator can only be used inside a conditional -statement, such as \nameref{if}\ldots\name{then}\ldots\name{else} -or \nameref{repeat}\ldots\name{until}. In other places the equal -sign establishes an algebraic object of type \nameref{equation}. - -\end{Comments} -\end{Operator} - - -\begin{Operator}[replace]{=>} - -The \name{=>} operator is a binary operator used in \ref{rule} lists to -denote replacements. - -\begin{Examples} -operator f; \\ -let f(x) => x^2; \\ -f(x); & x^{2} -\end{Examples} -\end{Operator} - - -\begin{Operator}[plussign]{+} -The \name{+} operator is a prefix or infix n-ary addition operator. - -\begin{Syntax} -\meta{expression} \{ \name{+}\meta{expression}\}\repeated - -{\em or} \name{+}\(\meta{expression} \{,\meta{expression}\}\repeated\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -x**4 + 4*x**2 + 17*x + 1; & X^{4} + 4*X^{2} + 17*X + 1 \\ -14 + 15 + x; & X + 29 \\ -+(1,2,3,4,5); & 15 -\end{Examples} - -\begin{Comments} -\name{+} is also valid as an addition operator for \nameref{matrix} variables -that are of the same dimensions and for \nameref{equation}s. -\end{Comments} -\end{Operator} - - -\begin{Operator}[minussign]{-} -The \name{-} operator is a prefix or infix binary subtraction operator, as well -as the unary minus operator. - -\begin{Syntax} -\meta{expression} \name{-} \meta{expression} -or \name{-}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -15 - 4; & 11 \\ -x*(-5); & - 5*X \\ -a - b - 15; & A - B - 15 \\ --(a,4); & A - 4 -\end{Examples} - -\begin{Comments} -The subtraction operator is left associative, so that a - b - c is equivalent -to (a - b) - c, as shown in the third example. The subtraction operator is -also valid with \nameref{matrix} expressions of the correct dimensions -and with \nameref{equation}s. -\end{Comments} -\end{Operator} - - -\begin{Operator}[asterisk]{*} -The \name{*} operator is a prefix or infix n-ary multiplication operator. - -\begin{Syntax} -\meta{expression} \{ \name{*} \meta{expression}\}\repeated - - or \name{*}\(\meta{expression} \{,\meta{expression}\}\repeated\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -15*3; & 45 \\ -24*x*yvalue*2; & 48*X*YVALUE \\ -*(6,x); & 6*X \\ -on rounded; \\ -3*1.5*x*x*x; & 4.5*X^{3} \\ -off rounded; \\ -2x**2; & 2*X^{2} -\end{Examples} - -\begin{Comments} -REDUCE assumes you are using an implicit multiplication operator when an -identifier is preceded by a number, as shown in the last line above. Since -no valid identifiers can begin with numbers, there is no ambiguity in -making this assumption. - -The multiplication operator is also valid with \nameref{matrix} expressions -of the -proper dimensions: matrices \IFTEX{$A$}{A} and \IFTEX{$B$}{B} -can be multiplied if -\IFTEX{$A$}{A} is \IFTEX{$n \times m$}{n x m} and \IFTEX{$B$}{B} is -\IFTEX{$m \times p$}{m x p}. Matrices and \nameref{equation}s can also be -multiplied by scalars: the -result is as if each element was multiplied by the scalar. -\end{Comments} -\end{Operator} - - -\begin{Operator}[slash]{/} -The \name{/} operator is a prefix or infix binary division operator or -prefix unary \nameref{recip}rocal operator. - -\begin{Syntax} -\meta{expression}\name{/}\meta{expression} {\em or} - \name{/}\meta{expression} - -or \name{/}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -20/5; & 4 \\ -100/6; & \rfrac{50}{3} \\ -16/2/x; & \rfrac{8}{X} \\ -/b; & \rfrac{1}{B} \\ -/(y,5); & \rfrac{Y}{5} \\ -on rounded; \\ -35/4; & 8.75 \\ -/20; & 0.05 -\end{Examples} - -\begin{Comments} -The division operator is left associative, so that \name{a/b/c} is equivalent -to \name{(a/b)/c}. The division operator is also valid with square -\nameref{matrix} expressions of the same dimensions: With \IFTEX{$A$}{A} and -\IFTEX{$B$}{B} both \IFTEX{$n \times n$}{n x n} matrices and \IFTEX{$B$}{B} -invertible, \IFTEX{$A/B$}{A/B} is -given by \IFTEX{$A \times B^{-1}$}{A*B^{-1}}. -Division of a matrix by a scalar is defined, with the results being the -division of each element of the matrix by the scalar. Division of a -scalar by a matrix is defined if the matrix is invertible, and has the -effect of multiplying the scalar by the inverse of the matrix. When -\name{/} is used as a reciprocal operator for a matrix, the inverse of -the matrix is returned if it exists. -\end{Comments} -\end{Operator} - - -\begin{Operator}[power]{**} -The \name{**} operator is a prefix or infix binary exponentiation operator. - -\begin{Syntax} -\meta{expression} \name{**}\meta{expression} - or \name{**}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -x**15; & X^{15} \\ -x**y**z; & X^{Y*Z} \\ -x**(y**z); & X^{Y^{Z}} \\ - **(y,4); & Y^{4} \\ -on rounded; \\ -2**pi; & 8.82497782708 -\end{Examples} - -\begin{Comments} -The exponentiation operator is left associative, so that \name{a**b**c} is -equivalent to \name{(a**b)**c}, as shown in the second example. Note -that this is {\em not} \name{a**(b**c)}, which would be right associative. - -When \nameref{nat} is on (the default), REDUCE output produces raised -exponents, as shown. The symbol \name{^}, which is the upper-case 6 on -most keyboards, may be used in the place of \name{**}. - -A square \nameref{matrix} may also be raised to positive and negative powers -with the exponentiation operator (negative powers require the matrix to be -invertible). Scalar expressions and \nameref{equation}s may be raised to -fractional and floating-point powers. -\end{Comments} -\end{Operator} - -\begin{Operator}[caret]{^} -The \name{^} operator is a prefix or infix binary exponentiation operator. -It is equivalent to \nameref{power} or **. - -\begin{Syntax} -\meta{expression} \name{^}\meta{expression} - or \name{^}\(\meta{expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} may be any valid REDUCE expression. - -\begin{Examples} -x^15; & X^{15} \\ -x^y^z; & X^{Y*Z} \\ -x^(y^z); & X^{Y^{Z}} \\ -^(y,4); & Y^{4} \\ -on rounded; \\ -2^pi; & 8.82497782708 -\end{Examples} - -\begin{Comments} -The exponentiation operator is left associative, so that \name{a^b^c} is -equivalent to \name{(a^b)^c}, as shown in the second example. Note -that this is \meta{not} \name{a^(b^c)}, which would be right associative. - -When \nameref{nat} is on (the default), REDUCE output produces raised -exponents, as shown. - -A square \nameref{matrix} may also be raised to positive -and negative powers with -the exponentiation operator (negative powers require the matrix to be -invertible). Scalar expressions and \nameref{equation}s -may be raised to fractional and floating-point powers. -\end{Comments} -\end{Operator} - - - -\begin{Operator}[geqsign]{>=} -\name{>=} is an infix binary comparison operator, which returns {\em true} if -its first argument is greater than or equal to its second argument. - -\begin{Syntax} -\meta{expression} \name{>=} \meta{expression} -\end{Syntax} - -\meta{expression} must evaluate to an integer or floating-point number. - -\begin{Examples} -if (3 >= 2) then yes; & yes \\ -a := 15; & A := 15 \\ -if a >= 20 then big else small; - & small \\ -\end{Examples} - -\begin{Comments} - -The binary comparison operators can only be used for comparisons between -numbers or variables that evaluate to numbers. The truth values returned -by such a comparison can only be used inside programming constructs, such -as \nameref{if}\ldots\name{then}\ldots\name{else} -or \nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. -\end{Comments} -\end{Operator} - - -\begin{Operator}[greater]{>} -The \name{>} is an infix binary comparison operator that returns -{\em true} if its first argument is strictly greater than its second. - -\begin{Syntax} -\meta{expression} \name{>} \meta{expression} -\end{Syntax} - -\meta{expression} must evaluate to a number, e.g., integer, rational or -floating point number. - -\begin{Examples} -on rounded; \\ -if 3.0 > 3 then write "different" else write "same"; & same \\ -off rounded; \\ -a := 20; & A := 20 \\ -if a > 20 then write "bigger" else write "not bigger"; & not bigger \\ -\end{Examples} - -\begin{Comments} -The binary comparison operators can only be used for comparisons between -numbers or variables that evaluate to numbers. The truth values returned -by such a comparison can only be used inside programming constructs, such -as \nameref{if}\ldots\name{then}\ldots\name{else} or -\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. -\end{Comments} -\end{Operator} - - -\begin{Operator}[leqsign]{<=} -\name{<=} is an infix binary comparison operator that returns -{\em true} if its first argument is less than or equal to its second argument. - -\begin{Syntax} -\meta{expression} \name{<=} \meta{expression} -\end{Syntax} - -\meta{expression} must evaluate to a number, e.g., integer, rational or -floating point number. - -\begin{Examples} -a := 10; & A := 10 \\ -if a <= 10 then true; & true -\end{Examples} - -\begin{Comments} - -The binary comparison operators can only be used for comparisons between -numbers or variables that evaluate to numbers. The truth values returned -by such a comparison can only be used inside programming constructs, such -as \nameref{if}\ldots\name{then}\ldots\name{else} or -\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. -\end{Comments} -\end{Operator} - - -\begin{Operator}[less]{<} -\name{<} is an infix binary logical comparison operator that -returns {\em true} if its first argument is strictly less than its second -argument. - -\begin{Syntax} -\meta{expression} \name{<} \meta{expression} -\end{Syntax} - -\meta{expression} must evaluate to a number, e.g., integer, rational or -floating point number. - -\begin{Examples} -f := -3; & F := -3 \\ -if f < -3 then write "yes" else write "no"; & no -\end{Examples} - -\begin{Comments} -The binary comparison operators can only be used for comparisons between -numbers or variables that evaluate to numbers. The truth values returned -by such a comparison can only be used inside programming constructs, such -as \nameref{if}\ldots\name{then}\ldots\name{else} -or \nameref{repeat}\ldots\name{until} or -\nameref{while}\ldots\name{do}. -\end{Comments} -\end{Operator} - -\begin{Operator}[tilde]{~} -The \name{~} is used as a unary prefix operator in the left-hand -sides of \nameref{rule}s to mark \nameref{free variable}s. A double tilde -marks an optional \nameref{free variable}. -\end{Operator} - - -\begin{Command}[group]{<<} -The \name{<<}\ldots\name{>>} command is a group statement, -used to group statements -together where REDUCE expects a single statement. - -%%%INCONSISTENT??? \name{or} -\begin{Syntax} -\name{<<}\meta{statement}\{; \meta{statement} \name{or} - \$\meta{statement}\}\optional \name{>>} -\end{Syntax} - -\meta{statement} may be any valid REDUCE statement or expression. - -\begin{Examples} -a := 2; & A := 2 \\ -if a < 5 then <>; & 12 \\ -<>; - & \rfrac{C^{2} + 90*C + 202}{225} -\end{Examples} - -\begin{Comments} -The value returned from a group statement is the value of the last -individual statement executed inside it. Note that when a semicolon is -placed between the last statement and the closing brackets, 0 or -{\em nil} is returned. Group statements are often used in the -consequence portions of \nameref{if}\ldots\name{then}, -\nameref{repeat}\ldots\name{until}, and -\nameref{while}\ldots\name{do} -clauses. They may also be used in interactive -operation to execute several statements at one time. Statements inside -the group statement are separated by semicolons or dollar signs. - -\end{Comments} -\end{Command} - - -\begin{Operator}{AND} -The \name{and} binary logical operator returns {\em true} if both of its -arguments are {\em true}. - -\begin{Syntax} -\meta{logical\_expression} \name{and} \meta{logical\_expression} -\end{Syntax} - -\meta{logical\_expression} must evaluate to {\em true} or {\em nil}. - -\begin{Examples} -a := 12; & A := 12 \\ -if numberp a and a < 15 then write a**2 else write "no"; - & 144 \\ -clear a; \\ -if numberp a and a < 15 then write a**2 else write "no"; - & no -\end{Examples} - -\begin{Comments} -Logical operators can only be used inside conditional statements, such as -\nameref{while}\ldots\name{do} or -\nameref{if}\ldots\name{then}\ldots\name{else}. \name{and} examines each of -its arguments in order, and quits, returning {\em nil}, on finding an -argument that is not {\em true}. An error results if it is used in other -contexts. - -\name{and} is left associative: \name{x and y and z} is equivalent to -\name{(x and y) and z}. -\end{Comments} -\end{Operator} - - -\begin{Command}{BEGIN} -\name{begin} is used to start a \nameref{block} statement, which is closed with -\name{end}. - -\begin{Syntax} -\name{begin} \meta{statement}\{\name{;} \meta{statement}\}\optional \ \name{end} -\end{Syntax} - -\meta{statement} is any valid REDUCE statement. - -\begin{Examples} -begin for i := 1:3 do write i end; & -\begin{multilineoutput}{1cm} -1 -2 -3 -\end{multilineoutput} \\ -begin scalar n;n:=1;b:=for i:=1:4 product(x-i);return n end; - & 1 \\ -b; & - X^{4} - 10*X^{3} + 35*X^{2} - 50*X + 24 -\end{Examples} - -\begin{Comments} -A \name{begin}\ldots\name{end} block can do actions (such as \name{write}), but -does not -return a value unless instructed to by a \nameref{return} statement, which must -be the last statement executed in the block. It is unnecessary to insert -a semicolon before the \name{end}. - -Local variables, if any, are declared in the first statement immediately -after \name{begin}, and may be defined as \name{scalar, integer,} or -\name{real}. \nameref{array} variables declared -within a \name{begin}\ldots\name{end} block -are global in every case, and \nameref{let} statements have global -effects. A \nameref{let} statement involving a formal parameter affects -the calling parameter that corresponds to it. \nameref{let} statements -involving local variables make global assignments, overwriting outside -variables by the same name or creating them if they do not exist. You -can use this feature to affect global variables from procedures, but be -careful that you do not do it inadvertently. - -\end{Comments} -\end{Command} - - -\begin{Command}{block} -A \name{block} is a sequence of statements enclosed by -commands \nameref{begin} and \nameref{end}. - -\begin{Syntax} -\name{begin} \meta{statement}\{\name{;} \meta{statement}\}\optional \ \name{end} -\end{Syntax} -For more details see \nameref{begin}. -\end{Command} - - -\begin{Command}{COMMENT} -Beginning with the word \name{comment}, all text until the next statement -terminator (\name{;} or \name{\$}) is ignored. - -\begin{Examples} - -x := a**2 comment--a is the velocity of the particle;; - & X := A^{2} -\end{Examples} - -\begin{Comments} -Note that the first semicolon ends the comment and the second one -terminates the original REDUCE statement. - -Multiple-line comments are often needed in interactive files. The -\name{comment} command allows a normal-looking text to accompany the -REDUCE statements in the file. -\end{Comments} -\end{Command} - - -\begin{Operator}{CONS} -The \name{cons} operator adds a new element to the beginning of a -\nameref{list}. Its -operation is identical to the symbol \nameref{dot} (dot). It can be used -infix or prefix. - -\begin{Syntax} -\name{cons}\(\meta{item},\meta{list}\) or \meta{item} \name{cons} \meta{list} -\end{Syntax} - -\meta{item} can be any REDUCE scalar expression, including a list; \meta{list} -must be a list. - -\begin{Examples} - -liss := cons(a,{b}); & \{A,B\} \\ - -liss := c cons liss; & \{C,A,B\} \\ - -newliss := for each y in liss collect cons(y,list x); - & NEWLISS := \{\{C,X\},\{A,X\},\{B,X\}\} \\ - -for each y in newliss sum (first y)*(second y); - & X*(A + B + C) -\end{Examples} - -\begin{Comments} -If you want to use \name{cons} to put together two elements into a new list, -you must make the second one into a list with curly brackets or the \name{list} -command. You can also start with an empty list created by \name{\{\}}. - -The \name{cons} operator is right associative: \name{a cons b cons c} is valid -if \name{c} is a list; \name{b} need not be a list. The list produced is -\name{\{a,b,c\}}. - -\end{Comments} -\end{Operator} - - -\begin{Command}{END} -The command \name{end} has two main uses: -\begin{itemize} -\item[(i)] -as the ending of a \nameref{begin}\ldots\name{end} \nameref{block}; and -\item[(ii)] -to end input from a file. -\end{itemize} - -\begin{Comments} -In a \name{begin}\ldots\name{end} \nameref{block}, there need not be a delimiter -(\name{;} or \name{\$}) before the \name{end}, though there must be one -after it, or a right bracket matching an earlier left bracket. - -Files to be read into REDUCE should end with \name{end;}, which must be -preceded by a semicolon (usually the last character of the previous line). -The additional semicolon avoids problems with mistakes in the files. If -you have suspended file operation by answering \name{n} to a \name{pause} -command, you are still, technically speaking, ``in" the file. Use -\name{end} to exit the file. - -An \name{end} at the top level of a program is ignored. -\end{Comments} -\end{Command} - - -\begin{Type}{EQUATION} -\index{equation}\index{equal}\index{arithmetic} -An \name{equation} is an expression where two algebraic expressions -are connected by the (infix) operator \nameref{equal} or by \nameindex{=}. -For access to the components of an \name{equation} the operators -\nameref{lhs}, \nameref{rhs} or \nameref{part} can be used. The -evaluation of the left-hand side of an \name{equation} is controlled -by the switch \nameref{evallhseqp}, while the right-hand side is -evaluated unconditionally. When an \name{equation} is part of a -logical expression, e.g. in a \nameref{if} or \nameref{while} statement, -the equation is evaluated by subtracting both sides can comparing -the result with zero. - -Equations occur in many contexts, e.g. as arguments of the \nameref{sub} -operator and in the arguments and the results -of the operator \nameref{solve}. An equation can be member of a \nameref{list} -and you may assign an equation to a variable. Elementary arithmetic is supported -for equations: if \nameref{evallhseqp} is on, you may add and subtract -equations, and you can combine an equation with a scalar expression by -addition, subtraction, multiplication, division and raise an equation -to a power. -\begin{Examples} -on evallhseqp;\\ -u:=x+y=1$\\ -v:=2x-y=0$\\ -2*u-v; & - 3*y=-2\\ -ws/3; & y=\rfrac{2}{3}\\ -\end{Examples} -Important: the equation must occur in the leftmost term of such an expression. -For other operations, e.g. taking function values of both sides, use the -\nameref{map} operator. - -\end{Type} - -\begin{Operator}{FIRST} -\index{list}\index{decomposition} -The \name{first} operator returns the first element of a \nameref{list}. -\begin{Syntax} -\name{first}\(\meta{list}\) or \name{first} \meta{list} -\end{Syntax} - -\meta{list} must be a non-empty list to avoid an error message. - -\begin{Examples} -alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ -first alist; & A \\ -blist := \{x,y,\{ww,aa,qq\},z\}; & BLIST := \{X,Y,\{WW,AA,QQ\},Z\} \\ -first third blist; & WW -\end{Examples} -\end{Operator} - - -\begin{Command}{FOR} -\index{loop} -The \name{for} command is used for iterative loops. There are many -possible forms it can take. -\begin{INFO} -{ -\begin{verbatim} - / \ - / |STEP UNTIL| \ - |:=| || -FOR| | : | | - | \ / | - |EACH IN | - \ / - - where ::= DO|PRODUCT|SUM|COLLECT|JOIN. -\end{verbatim} -} -\end{INFO} -\begin{TEX} -\begin{Syntax} - \name{for} - \begin{alternative} - \meta{var} \name{:=} \meta{start} \name{:} \meta{stop}\\ - \meta{var} \name{:=} \meta{start} \name{step} \meta{inc} - \name{until} \meta{stop}\\ - \name{each} \meta{var} \name{in} \meta{list} - \end{alternative} - \begin{alternative} - \name{collect}\\ - \name{do}\\ - \name{join}\\ - \name{product}\\ - \name{sum} - \end{alternative} - \meta{expression} -\end{Syntax} -\end{TEX} - -\meta{var} can be any valid REDUCE identifier except \name{t} or -\name{nil}, \meta{inc}, \meta{start} and \meta{stop} can be any expression -that evaluates to a positive or negative integer. \meta{list} must be a -valid \nameref{list} structure. -The action taken must be one of the actions shown -above, each of which is followed by a single REDUCE expression, statement -or a \nameref{group} (\name{<<}\ldots\name{>>}) or \nameref{block} -(\nameref{begin}\ldots\nameref{end}) statement. - -\begin{Examples} -for i := 1:10 sum i; - & 55 \\ -for a := -2 step 3 until 6 product a; - & -8 \\ -a := 3; & A := 3 \\ -for iter := 4:a do write iter; \\ -m := 0; & M := 0 \\ -for s := 10 step -1 until 3 do <>; \\ -m; & 520 \\ -for each x in {q,r,s} sum x**2; & Q^{2} + R^{2} + S^{2} \\ -for i := 1:4 collect 1/i; - & \{1,\rfrac{1}{2},\rfrac{1}{3},\rfrac{1}{4}\} \\ -for i := 1:3 join list solve(x**2 + i*x + 1,x); - & \begin{multilineoutput}{5cm} -\{\{X= -\rfrac{SQRT(3)*I + 1}{2}, - X= -\rfrac{SQRT(3)*I - 1}{2}\} - \{X=-1\}, - \{X= - \rfrac{SQRT(5) + 3}{2},X=\rfrac{SQRT(5) - 3}{2}\}\} -\end{multilineoutput} -\end{Examples} - -\begin{Comments} -The behavior of each of the five action words follows: - -\begin{TEX} -\begin{center} -\begin{tabular}{|l|p{5cm}|p{5cm}|} -\hline -\multicolumn{3}{|c|}{Action Word Behavior}\\ -\hline -\multicolumn{1}{|c|}{Keyword} & - \multicolumn{1}{c|}{Argument Type} & \multicolumn{1}{c|}{Action} \\ -\hline -do & statement, command, group or block & -Evaluates its argument once for each iteration of the loop, not saving -results \\ -collect & expression, statement, command, group, block, list & -Evaluates its argument once for each iteration of the loop, storing the results -in a list which is returned by the \verb|for| statement when done \\ -join & list or an operator which produces a list & -Evaluates its argument once for each iteration of the loop, appending the -elements in each individual result list onto the overall result list \\ -product & expression, statement, command, -\nameref{group} or \nameref{block} & -Evaluates its argument once for each iteration of the loop, multiplying the -results together and returning the overall product \\ -sum & expression, statement, command, group or block & -Evaluates its argument once for each iteration of the loop, adding the results -together and returning the overall sum\\ -\hline -\end{tabular} -\end{center} -\end{TEX} -\begin{INFO} -{\begin{verbatim} - Action Word Behavior -Keyword Argument Type Action - do statement, command, group Evaluates its argument once - or block for each iteration of the loop, - not saving results -collect expression, statement, Evaluates its argument once for - command, group, block, list each iteration of the loop, - storing the results in a list - which is returned by the for - statement when done - join list or an operator which Evaluates its argument once for - produces a list each iteration of the loop, - appending the elements in each - individual result list onto the - overall result list -product expression, statement, Evaluates its argument once for - command, group or block each iteration of the loop, - multiplying the results together - and returning the overall product - sum expression, statement, Evaluates its argument once for - command, group or block each iteration of the loop, - adding the results together and - returning the overall sum -\end{verbatim} } -\end{INFO} - -For number-driven \name{for} statements, if the ending limit is smaller -than the beginning limit (larger in the case of negative steps) the action -statement is not executed at all. The iterative variable is local to the -\name{for} statement, and does not affect the value of an identifier with -the same name. For list-driven \name{for} statements, if the list is -empty, the action statement is not executed, but no error occurs. - -You can use nested \name{for} statements, with the inner \name{for} -statement after the action keyword. You must make sure that your inner -statement returns an expression that the outer statement can handle. -\end{Comments} -\end{Command} - - -\begin{Command}{FOREACH} -\index{loop} -\name{foreach} is a synonym for the \name{for each} variant of the -\nameref{for} construct. It is designed to iterate down a list, and an -error will occur if a list is not used. The use of \name{for each} is -preferred to \name{foreach}. - -\begin{Syntax} -\name{foreach} \meta{variable} in \meta{list} \meta{action} \meta{expression} \\ - where \meta{action} ::= \name{do | product | sum | collect | join} -\end{Syntax} - -\begin{Examples} -foreach x in {q,r,s} sum x**2; & Q^{2} + R^{2} + S^{2} -\end{Examples} - -\end{Command} - - -\begin{Operator}{GEQ} -The \name{geq} operator is a binary infix or prefix logical operator. It -returns true if its first argument is greater than or equal to its second -argument. As an infix operator it is identical with \name{>=}. -\begin{Syntax} -\name{geq}\(\meta{expression},\meta{expression}\) or \meta{expression} -\name{geq} \meta{expression} -\end{Syntax} - -\meta{expression} can be any valid REDUCE expression that evaluates to a -number. - -\begin{Examples} -a := 20; & A := 20 \\ -if geq(a,25) then write "big" else write "small"; - & small \\ -if a geq 20 then write "big" else write "small"; - & big \\ -if (a geq 18) then write "big" else write "small"; - & big -\end{Examples} - -\begin{Comments} -Logical operators can only be used in conditional statements such as \\ -\nameref{if}\ldots\name{then}\ldots\name{else} or -\nameref{repeat}\ldots\name{until}. -\end{Comments} -\end{Operator} - - -\begin{Command}{GOTO} -Inside a \name{begin}\ldots\name{end} \nameref{block}, \name{goto}, or -preferably, \name{go to}, transfers flow of control to a labeled statement. -\begin{Syntax} -\name{go to} \meta{labeled_statement} or \name{goto} \meta{labeled_statement} -\end{Syntax} -\meta{labeled_statement} is of the form \meta{label} \name{:}\meta{statement} - -\begin{Examples} -\begin{multilineinput} - procedure dumb(a); - begin scalar q; - go to lab; - q := df(a**2 - sin(a),a); - write q; - lab: return a - end; -\end{multilineinput} & DUMB \\ - -dumb(17); & 17 -\end{Examples} - -\begin{Comments} -\name{go to} can only be used inside a \name{begin}\ldots\name{end} -\nameref{block}, and inside -the block only statements at the top level can be labeled, not ones inside -\name{<<}\ldots\name{>>}, \nameref{while}\ldots\name{do}, etc. -\end{Comments} -\end{Command} - - -\begin{Operator}{GREATERP} -The \name{greaterp} logical operator returns true if its first argument is -strictly greater than its second argument. As an infix operator it is -identical with \name{>}. -\begin{Syntax} -\name{greaterp}\(\meta{expression},\meta{expression}\) or \meta{expression} -\name{greaterp} \meta{expression} -\end{Syntax} - -\meta{expression} can be any valid REDUCE expression that evaluates to a -number. - -\begin{Examples} - -a := 20; & A := 20 \\ -if greaterp(a,25) then write "big" else write "small"; - & small \\ -if a greaterp 20 then write "big" else write "small"; - & small \\ -if (a greaterp 18) then write "big" else write "small"; - & big -\end{Examples} - -\begin{Comments} -Logical operators can only be used in conditional statements such as \\ -\nameref{if}\ldots\name{then}\ldots\name{else} -or \nameref{repeat}\ldots\nameref{while}. -\end{Comments} -\end{Operator} - - -\begin{Command}{IF} -The \name{if} command is a conditional statement that executes a statement -if a condition is true, and optionally another statement if it is not. -\begin{Syntax} -\name{if} \meta{condition} \name{then} \meta{statement} -\ \&option\(\name{else}\ \meta{statement}\) -\end{Syntax} - -\meta{condition} must be a logical or comparison operator that evaluates to -a \nameref{boolean value}. -\meta{statement} must be a single REDUCE statement or a -\nameref{group} (\name{<<}\ldots\name{>>}) or -\nameref{block} (\name{begin}\ldots\name{end}) statement. - -\begin{Examples} -if x = 5 then a := b+c else a := d+f; - & D + F \\ -x := 9; & X := 9 \\ -if numberp x and x<20 then y := sqrt(x) else write "illegal"; - & 3 \\ -clear x; \\ -if numberp x and x<20 then y := sqrt(x) else write "illegal"; - & illegal \\ -x := 12; & X := 12 \\ -a := if x < 5 then 100 else 150; - & A := 150 \\ -b := u**(if x < 10 then 2); - & B := 1 \\ -bb := u**(if x > 10 then 2); - & BB := U^{2} -\end{Examples} - -\begin{Comments} -An \name{if} statement may be used inside an assignment statement and sets -its value depending on the conditions, or used anywhere else an -expression would be valid, as shown in the last example. If there is no -\nameindex{else} clause, the value is 0 if a number is expected, and nothing -otherwise. - -The \name{else} clause may be left out if no action is to be taken if the -condition is false. - -The condition may be a compound conditional statement using \nameref{and} or -\nameref{or}. If a non-conditional statement, such as a constant, is used by -accident, it is assumed to have value {\em true}. - -Be sure to use \nameref{group} or \nameref{block} statements after -\nameindex{then} or \name{else}. - -The \name{if} operator is right associative. The following constructions are -examples: -\begin{itemize} -\item[(1)] -\begin{Syntax} -\name{if} \meta{condition} \name{then} \name{if} \meta{condition} \name{then} - \meta{action} \name{else} \meta{action} -\end{Syntax} -%\end{itemize} - -which is equivalent to -\begin{Syntax} -\name{if} \meta{condition} \name{then} \(\name{if}\ \meta{condition} -\ \name{then}\ \meta{action}\ \name{else}\ \meta{action}\); -\end{Syntax} -%\begin{itemize} - -\item[(2)] -\begin{Syntax} -\name{if} \meta{condition} \name{then} \meta{action} \name{else if} - \meta{condition} \name{then} \meta{action} \name{else} \meta{action} -\end{Syntax} -which is equivalent to -\begin{Syntax} -\name{if}\ \meta{condition} \name{then} \meta{action} \name{else} \\ - \(\name{if}\ \meta{condition}\ \name{then}\ \meta{action} -\ \name{else}\ \meta{action}\). -\end{Syntax} -\end{itemize} -\end{Comments} -\end{Command} - - -\begin{Operator}{LIST} -\index{list} -The \name{list} operator constructs a list from its arguments. -\begin{Syntax} -\name{list}\(\meta{item} \{,\meta{item}\}\optional\) or - \name{list}\(\) to construct an empty list. -\end{Syntax} - -\meta{item} can be any REDUCE scalar expression, including another list. -Left and right curly brackets can also be used instead of the operator -\name{list} to construct a list. - -\begin{Examples} -liss := list(c,b,c,\{xx,yy\},3x**2+7x+3,df(sin(2*x),x)); - & LISS := \{C,B,C,\{XX,YY\},3*X^{2} + 7*X + 3,2*COS(2*X)\} \\ -length liss; & 6 \\ -liss := \{c,b,c,\{xx,yy\},3x**2+7x+3,df(sin(2*x),x)\}; - & LISS := \{C,B,C,\{XX,YY\},3*X^{2} + 7*X + 3,2*COS(2*X)\} \\ -emptylis := list(); & EMPTYLIS := \{\} \\ -a . emptylis; & \{A\} -\end{Examples} - -\begin{Comments} -Lists are ordered, hierarchical structures. The elements stay where you -put them, and only change position in the list if you specifically change -them. Lists can have nested sublists to any (reasonable) level. The -\nameref{part} operator can be used to access elements anywhere within a list -hierarchy. The \nameref{length} operator counts the -number of top-level elements -of its list argument; elements that are themselves lists still only -count as one element. -\end{Comments} -\end{Operator} - - -\begin{Operator}{OR} -The \name{or} binary logical operator returns {\it true} if either one or -both of its arguments is {\it true}. -\begin{Syntax} -\meta{logical expression} \name{or} \meta{logical expression} -\end{Syntax} - -\meta{logical expression} must evaluate to {\it true} or {\it nil}. - -\begin{Examples} -a := 10; & A := 10 \\ -\begin{multilineinput} -if a<0 or a>140 then write "not a valid human age" else - write "age = ",a; -\end{multilineinput} \\ -& age = 10 \\ -a := 200; & A := 200 \\ -if a < 0 or a > 140 then write "not a valid human age"; - & not a valid human age -\end{Examples} - -\begin{Comments} -The \name{or} operator is left associative: \name{x or y or z} is equivalent to -\name{(x or y)} \name{or z}. - -Logical operators can only be used in conditional expressions, such as \\ -\nameref{if}\ldots\name{then}\ldots\name{else} -and \nameref{while}\ldots\name{do}. -\name{or} evaluates its arguments in order and quits, returning {\it true}, -on finding the first {\it true} statement. -\end{Comments} -\end{Operator} - - -\begin{Command}{PROCEDURE} -The \name{procedure} command allows you to define a mathematical operation as a -function with arguments. -\begin{Syntax} -\&\meta{option} \name{procedure} \meta{identifier} - \(\meta{arg}\{,\meta{arg}\}\repeated\)\name{;}\meta{body} -\end{Syntax} - -The \meta{option} may be \nameref{algebraic} or \nameref{symbolic}, -indicating the -mode under which the procedure is executed, or \nameref{real} or -\nameref{integer}, indicating the type of answer expected. The default is -algebraic. Real or integer procedures are subtypes of algebraic -procedures; type-checking is done on the results of integer procedures, but -not on real procedures (in the current REDUCE release). \meta{identifier} -may be any valid REDUCE identifier that is not already a procedure name, -operator, \nameref{array} or \nameref{matrix}. -\meta{arg} is a formal parameter that may be any -valid REDUCE identifier. \meta{body} is a single statement (a \nameref{group} -or \nameref{block} statement may be used) with the desired activities in it. - -\begin{Examples} -\begin{multilineinput} -procedure fac(n); - if not (fixp(n) and n>=0) - then rederr "Choose nonneg. integer only" - else for i := 0:n-1 product i+1; -\end{multilineinput} - & FAC \\ -fac(0); & 1 \\ -fac(5); & 120 \\ -fac(-5); & ***** choose nonneg. integer only -\end{Examples} - -\begin{Comments} -Procedures are automatically declared as operators upon definition. When -REDUCE has parsed the procedure definition and successfully converted it to -a form for its own use, it prints the name of the procedure. Procedure -definitions cannot be nested. Procedures can call other procedures, or can -recursively call themselves. Procedure identifiers can be cleared as you -would clear an operator. Unlike \nameref{let} statements, new definitions -under the same procedure name replace the previous definitions completely. - -Be careful not to use the name of a system operator for your own procedure. -REDUCE may or may not give you a warning message. If you redefine a system -operator in your own procedure, the original function of the system operator -is lost for the remainder of the REDUCE session. - -Procedures may have none, one, or more than one parameter. A REDUCE -parameter is a formal parameter only; the use of {\it x} as a parameter in -a \name{procedure} definition has no connection with a value of {\it x} in -the REDUCE session, and the results of calling a procedure have no effect -on the value of {\it x}. If a procedure is {\it called} with {\it x} as a -parameter, the current value of {\it x} is used as specified in the -computation, but is not changed outside the procedure. -Making an assignment statement by \name{:=} with a -formal parameter on the left-hand side only changes the value of the -calling parameter within the procedure. - -Using a \nameref{let} statement inside a procedure always changes the value -globally: a \name{let} with a formal parameter makes the change to the calling -parameter. \name{let} statements cannot be made on local variables inside -\nameref{begin}\ldots\name{end} \nameref{block}\name{s}. -When \nameref{clear} statements are used on formal -parameters, the calling variables associated with them are cleared globally too. -The use of \name{let} or \name{clear} statements inside procedures -should be done with extreme caution. - -Arrays and operators may be used as parameters to procedures. The body of the -procedure can contain statements that appropriately manipulate these -arguments. Changes are made to values of the calling arrays or operators. -Simple expressions can also be used as arguments, in the place of scalar -variables. Matrices may {\it not} be used as arguments to procedures. - -A procedure that has no parameters is called by the procedure name, -immediately followed by empty parentheses. The empty parentheses may be left -out when writing a procedure with no parameters, but must appear in a call of -the procedure. If this is a nuisance to you, use a \nameref{let} statement on -the name of the procedure (i.e., \name{let noargs = noargs()}) after which -you can call the procedure by just its name. - -Procedures that have a single argument can leave out the parentheses around -it both in the definition and procedure call. (You can use the parentheses if -you wish.) Procedures with more than one argument must use parentheses, with -the arguments separated by commas. - -Procedures often have a \name{begin}\ldots\name{end} block in them. Inside the -block, local variables are declared using \name{scalar}, \name{real} or -\name{integer} declarations. -The declarations must be made immediately after the word -\name{begin}, and if more than one type of declaration is made, they are -separated by semicolons. REDUCE currently does no type checking on local -variables; \name{real} and \name{integer} are treated just like \name{scalar}. -Actions take place as specified in the statements inside the block statement. -Any identifiers that are not formal parameters or local variables are treated -as global variables, and activities involving these identifiers are global in -effect. - -If a return value is desired from a procedure call, a specific -\nameref{return} command must be the last statement executed before exiting -from the procedure. If no \name{return} is used, a procedure returns a -zero or no value. - -Procedures are often written in a file using an editor, then the file -is input using the command \nameref{in}. This method allows easy changes in -development, and also allows you to load the named procedures whenever -you like, by loading the files that contain them. -\end{Comments} -\end{Command} - - -\begin{Command}{REPEAT} -\index{loop} -The \nameref{repeat} command causes repeated execution of a statement -\nameindex{until} -the given condition is found to be true. The statement is always executed -at least once. -\begin{Syntax} -\name{repeat} \meta{statement} \name{until} \meta{condition} -\end{Syntax} - -\meta{statement} can be a single statement, \nameref{group} statement, or -a \name{begin}\ldots\name{end} \nameref{block}. \meta{condition} must be -a logical operator that evaluates to {\it true} or {\it nil}. - -\begin{Examples} -<> until m = 0>>; - & \begin{multilineoutput}{6cm} -400*X -300*X -200*X -100*X -\end{multilineoutput}\\ - -<> until m <= 0>>; - & -1 - -\end{Examples} -\begin{Comments} -\name{repeat} must always be followed by an \name{until} with a condition. -Be careful not to generate an infinite loop with a condition that is never -true. In the second example, if the condition had been \name{m = 0}, it -would never have been true since \name{m} already had value -2 when the -condition was first evaluated. -\end{Comments} -\end{Command} - - -\begin{Operator}{REST} -\index{list}\index{decomposition} -The \name{rest} operator returns a \nameref{list} containing all but the first -element of the list it is given. -\begin{Syntax} -\name{rest}\(\meta{list}\) or \name{rest} \meta{list} - - -\end{Syntax} -\meta{list} must be a non-empty list, but need not have more than one element. - -\begin{Examples} -alist := {a,b,c,d}; & ALIST := \{A,B,C,D\}; \\ -rest alist; & \{B,C,D\} \\ -blist := {x,y,{aa,bb,cc},z}; & BLIST := \{X,Y,\{AA,BB,CC\},Z\} \\ -second rest blist; & \{AA,BB,CC\} \\ -clist := {c}; & CLIST := C \\ -rest clist; & \{\} -\end{Examples} - -\end{Operator} - - -\begin{Command}{RETURN} -The \name{return} command causes a value to be returned from inside a -\name{begin}\ldots\name{end} \nameref{block}. -\begin{TEX} -\begin{Syntax} -\name{begin} \meta{statements} \name{return} \meta{\&option(expression)} - \name{end} -\end{Syntax} -\end{TEX} -\begin{INFO} -{\begin{Syntax} -\name{begin} \meta{statements} \name{return} \meta{(expression)} - \name{end} -\end{Syntax} -}\end{INFO} - -\meta{statements} can be any valid REDUCE statements. The value of -\meta{expression} is returned. - -\begin{Examples} -begin write "yes"; return a end; & -\begin{multilineoutput}{5cm} -yes -A -\end{multilineoutput}\\ -\begin{multilineinput} -procedure dumb(a); - begin if numberp(a) then return a else return 10 end; -\end{multilineinput} - & DUMB \\ -dumb(x); & 10 \\ -dumb(-5); & -5 \\ -\begin{multilineinput} -procedure dumb2(a); - begin c := a**2 + 2*a + 1; d := 17; c*d; return end; -\end{multilineinput} & DUMB2 \\ -dumb2(4); \\ -c; & 25 \\ -d; & 17 -\end{Examples} - -\begin{Comments} -Note in \name{dumb2} above that the assignments were made as requested, but -the product \name{c*d} cannot be accessed. Changing the procedure to read -\name{return c*d} would remedy this problem. - -The \name{return} statement is always the last statement executed before -leaving the block. If \name{return} has no argument, the block is exited but -no value is returned. A block statement does not need a \name{return} ; -the statements inside terminate in their normal fashion without one. -In that case no value is returned, although the specified actions inside the -block take place. - -The \name{return} command can be used inside \name{<<}\ldots\name{>>} -\nameref{group} statements and -\nameref{if}\ldots\name{then}\ldots\name{else} commands that -are inside \name{begin}\ldots\name{end} \nameref{block}s. -It is not valid in these constructions that are not inside -a \name{begin}\ldots\name{end} - block. It is not valid inside \nameref{for}, -\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do} - loops in any construction. To force early termination from loops, the -\name{go to}(\nameref{goto}) command must be used. -When you use nested block statements, a -\name{return} from an inner block exits returning a value to the next-outermost -block, rather than all the way to the outside. -\end{Comments} -\end{Command} - - -\begin{Operator}{REVERSE} -\index{list} -The \name{reverse} operator returns a \nameref{list} that is the reverse of the -list it is given. -\begin{Syntax} -\name{reverse}\(\meta{list}\) or \name{reverse} \meta{list} -\end{Syntax} - -\meta{list} must be a \nameref{list}. - -\begin{Examples} -aa := \{c,b,a,\{x**2,z**3\},y\}; & AA := \{C,B,A,\{X^{2},Z^{3}\},Y\} \\ -reverse aa; & \{Y,\{X^{2},Z^{3}\},A,B,C\} \\ -reverse(q . reverse aa); & \{C,B,A,\{X^{2},Z^{3}\},Y,Q\} -\end{Examples} - -\begin{Comments} -\name{reverse} and \nameref{cons} can be used together to add a new element to -the end of a list (\name{.} adds its new element to the beginning). The -\name{reverse} operator uses a noticeable amount of system resources, -especially if the list is long. If you are doing much heavy-duty list -manipulation, you should probably design your algorithms to avoid much -reversing of lists. A moderate amount of list reversing is no problem. -\end{Comments} -\end{Operator} - - -\begin{Type}{RULE} -\index{rule}\index{rule list} -A \name{rule} is an instruction to replace an algebraic expression -or a part of an expression by another one. -\begin{Syntax} -\meta{lhs} => \meta{rhs} or -\meta{lhs} => \meta{rhs} \name{when} \meta{cond} -\end{Syntax} -\meta{lhs} is an algebraic expression used as search pattern and -\meta{rhs} is an algebraic expression which replaces matches of -\meta{rhs}. \name{=>} is the operator \nameref{replace}. - -\meta{lhs} can contain \nameref{free variable}s which are -symbols preceded by a tilde \nameindex{~} in their leftmost position -in \meta{lhs}. -A double tilde marks an \nameref{optional free variable}. -If a rule has a \name{when} \meta{cond} -part it will fire only if the evaluation of \meta{cond} has a -result \nameref{true}. \meta{cond} may contain references to -free variables of \meta{lhs}. - -Rules can be collected in a \nameref{list} which then forms a -\nameindex{rule list}. \name{Rule lists} can be used to collect -algebraic knowledge for a specific evaluation context. - -\name{Rules} and \name{rule lists} are globally activated and -deactivated by \nameref{let}, \nameref{forall}, \nameref{clearrules}. -For a single evaluation they can be locally activate by \nameref{where}. -The active rules for an operator can be visualized by \nameref{showrules}. - -\begin{Examples} -operator f,g,h; \\ -let f(x) => x^2; \\ -f(x); & x^{2}\\ -g_rules:={g(~n,~x)=>h(n/2,x) when evenp n,\\ -g(~n,~x)=>h((1-n)/2,x) when not evenp n}$\\ -let g_rules;\\ -g(3,x); & h(-1,x) -\end{Examples} - -\end{Type} - -\begin{Type}{Free Variable} -\index{variable} -A variable preceded by a tilde is considered as \name{free variable} -and stands for an arbitrary part in an algebraic form during -pattern matching. Free variables occur in the left-hand sides -of \nameref{rule}s, in the side relations for \nameref{compact} -and in the first arguments of \nameref{map} and \nameref{select} -calls. See \nameref{rule} for examples. - -In rules also \nameref{optional free variable}s may occur. -\end{Type} - -\begin{Type}{Optional Free Variable} -\index{variable} -A variable preceded by a double tilde is considered as -\name{optional free variable} -and stands for an arbitrary part part in an algebraic form during -pattern matching. In contrast to ordinary \nameref{free variable}s -an operator pattern with an \name{optional free variable} -matches also if the operand for the variable is missing. In such -a case the variable is bound to a neutral value. -Optional free variables can be used as - - term in a sum: set to 0 if missing, - - factor in a product: set to 1 if missing, - - exponent: set to 1 if missing - -\begin{Examples} - sin(~~u + ~~n * pi) => sin(u) when evenp u; -\end{Examples} - -Optional free variables are allowed only in the left-hand sides -of \nameref{rule}s. -\end{Type} - -\begin{Operator}{SECOND} -\index{list}\index{decomposition} -The \name{second} operator returns the second element of a list. -\begin{Syntax} -\name{second}\(\meta{list}\) or \name{second} \meta{list} - - -\end{Syntax} - -\meta{list} must be a list with at least two elements, to avoid an error -message. - -\begin{Examples} -alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ -second alist; & B \\ -blist := \{x,\{aa,bb,cc\},z\}; & BLIST := \{X,\{AA,BB,CC\},Z\} \\ -second second blist; & BB -\end{Examples} -\end{Operator} - - -\begin{Operator}{SET} -\index{assign} -The \name{set} operator is used for assignments when you want both sides of -the assignment statement to be evaluated. -%%% INCONSISTENT??? hyphen after restricted -\begin{Syntax} -\name{set}\(\meta{restricted\_expression},\meta{expression}\) -\end{Syntax} - -\meta{expression} can be any REDUCE expression; \meta{restricted\_expression} -must be an identifier or an expression that evaluates to an identifier. - -\begin{Examples} -a := y; & A := Y \\ -set(a,sin(x^2)); & SIN(X^{2}) \\ -a; & SIN(X^{2}) \\ -y; & SIN(X^{2}) \\ -a := b + c; & A := B + C \\ -set(a-c,z); & Z \\ -b; & Z -\end{Examples} - -\begin{Comments} -Using an \nameref{array} or \nameref{matrix} reference as the first -argument to \name{set} has -the result of setting the {\it contents} of the designated element to -\name{set}'s second argument. You should be careful to avoid unwanted -side effects when you use this facility. -\end{Comments} -\end{Operator} - - -\begin{Operator}{SETQ} -\index{assign} -The \name{setq} operator is an infix or prefix binary assignment operator. -It is identical to \name{:=}. -\begin{Syntax} -\name{setq}\(\meta{restricted\_expression},\meta{expression}\) or \\ -\meta{restricted\_expression} \name{setq} \meta{expression} -\end{Syntax} - -\meta{restricted expression} is ordinarily a single identifier, though -simple expressions may be used (see Comments below). \meta{expression} can -be any valid REDUCE expression. If \meta{expression} is a \nameref{matrix} -identifier, then \meta{restricted\_expression} can be a matrix identifier -(redimensioned if necessary), which has each element set to the -corresponding elements of the identifier on the right-hand side. - -\begin{Examples} -setq(b,6); & B := 6 \\ -c setq sin(x); & C := SIN(X) \\ -w + setq(c,x+3) + z; & W + X + Z + 3 \\ -c; & X + 3 \\ -setq(a1 + a2,25); & A1 + A2 := 25 \\ -a1; & - (A2 - 25) -\end{Examples} -\begin{Comments} -Embedding a \name{setq} statement in an expression has the side effect of making -the assignment, as shown in the third example above. - -Assignments are generally done for identifiers, but may be done for simple -expressions as well, subject to the following remarks: -\begin{itemize} - -\item[(i)] -If the left-hand side is an identifier, an operator, or a power, the rule -is added to the rule table. - -\item[(ii)] -If the operators \name{- + /} appear on the left-hand side, all but the first -term of the expression is moved to the right-hand side. - -\item[(iii)] -If the operator \name{*} appears on the left-hand side, any constant terms are -moved to the right-hand side, but the symbolic factors remain. -\end{itemize} - -Be careful not to make a recursive \name{setq} assignment that is not -controlled inside a loop statement. The process of resubstitution -continues until you get a stack overflow message. \name{setq} can be used -to attach functionality to operators, as the \name{:=} does. -\end{Comments} -\end{Operator} - - -\begin{Operator}{THIRD} -\index{list}\index{decomposition} -The \name{third} operator returns the third item of a \nameref{list}. -\begin{Syntax} -\name{third}\(\meta{list}\) or \name{third} \meta{list} - -\end{Syntax} - - -\meta{list} must be a list containing at least three items to avoid an error -message. - -\begin{Examples} -alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ -third alist; & C \\ -blist := \{x,\{aa,bb,cc\},y,z\}; & BLIST := \{X,\{AA,BB,CC\},Y,Z\}; \\ -third second blist; & CC \\ -third blist; & Y -\end{Examples} - -\end{Operator} - -\begin{Operator}{WHEN} -\index{rule} -The \name{when} operator is used inside a \name{rule} to make the -execution of the rule depend on a boolean condition which is -evaluated at execution time. For the use see \nameref{rule}. -\end{Operator} - +\section{Syntax} + +\begin{Command}[semicolon]{;} +The semicolon is a statement delimiter, indicating results are to be printed +when used in interactive mode. + +\begin{Examples} +(x+1)**2; & X^{2} + 2*X + 1 \\ +df(x**2 + 1,x); & 2*X +\end{Examples} + +\begin{Comments} +Entering a \key{Return} without a semicolon or dollar sign results in a +prompt on the following line. A semicolon or dollar sign can be +added at this point to execute the statement. In interactive mode, a +statement that is ended with a semicolon and \key{Return} has its results +printed on the screen. + +Inside a group statement \name{<<}\ldots\name{>>} +or a \name{begin}\ldots\name{end} block, a +semicolon or dollar sign separates individual REDUCE statements. Since +results are not printed from a block without a specific \name{return} +statement, there is no difference between using the semicolon or dollar +sign. In a group statement, the last value produced is the value +returned by the group statement. Thus, if a semicolon or dollar sign is +placed between the last statement and the ending brackets, the group +statement returns the value 0 or {\em nil}, rather than the value of the +last statement. +\end{Comments} +\end{Command} + + +\begin{Command}[dollar]{$} +The dollar sign is a statement delimiter, indicating results are not to be +printed when used in interactive mode. + +\begin{Examples} + +(x+1)**2$ & +\explanationo{The workspace is set to $x^{2} + 2x + 1$ + but nothing shows on the screen} \\ +ws; & X^{2} + 2*X + 1 +\end{Examples} + +\begin{Comments} +Entering a \key{Return} without a semicolon or dollar sign results in a +prompt on the following line. A semicolon or dollar sign can +be added at this point to execute the statement. In interactive mode, a +statement that ends with a dollar sign \name{\$} and a \key{Return} is +executed, but the results not printed. + +Inside a \nameref{group} statement \name{<<}\ldots\name{>>} +or a \name{begin}\ldots\name{end} \nameref{block}, a +semicolon or dollar sign separates individual REDUCE statements. Since +results are not printed from a \nameref{block} without a specific +\nameref{return} +statement, there is no difference between using the semicolon or dollar +sign. + +In a group statement, the last value produced is the value returned by the +group statement. Thus, if a semicolon or dollar sign is placed between the +last statement and the ending brackets, the group statement returns the +value 0 or {\em nil}, rather than the value of the last statement. + +\end{Comments} +\end{Command} + +\begin{Command}[percent]{%} +The percent sign is used to precede comments; everything from a percent +to the end of the line is ignored. + +\begin{Examples} + +df(x**3 + y,x);\% This is a comment \key{Return} & 3*X^{2} \\ +int(3*x**2,x) \%This is a comment; \key{Return} \\ + +\explanation{A prompt is given, waiting for the semicolon that was not +detected in the comment} +\end{Examples} + +\begin{Comments} +Statement delimiters \name{;} and \name{\$} are not detected between a +percent sign and the end of the line. +\end{Comments} +\end{Command} + + +% \begin{Operator}[ampersand]{&} +% +% ***** To be added ***** +% +% \end{Operator} +% +% +\begin{Operator}[dot]{.} +\index{list} +The . (dot) infix binary operator adds a new item to the beginning of an +existing \nameref{list}. In high energy physics expressions, +it can also be used +to represent the scalar product of two Lorentz four-vectors. + +\begin{Syntax} +\meta{item} \name{.} \meta{list} +\end{Syntax} + +\meta{item} can be any REDUCE scalar expression, including a list; +\meta{list} must be a \nameref{list} to avoid producing an error message. +The dot operator is right associative. + +\begin{Examples} + +liss := a . \{\}; & LISS := \{A\} \\ +liss := b . liss; & LISS := \{B,A\} \\ +newliss := liss . liss; & NEWLISS := \{\{B,A\},B,A\} \\ +firstlis := a . b . \{c\}; & FIRSTLIS := \{A,B,C\} \\ +secondlis := x . y . \{z\}; & SECONDLIS := \{X,Y,Z\} \\ +for i := 1:3 sum part(firstlis,i)*part(secondlis,i); + & A*X + B*Y + C*Z +\end{Examples} +\end{Operator} + + +\begin{Operator}[assign]{:=} +\index{assign} +The \name{:=} is the assignment operator, assigning the value on the right-hand +side to the identifier or other valid expression on the left-hand side. + +\begin{Syntax} + \meta{restricted\_expression} \name{:=} \meta{expression} +\end{Syntax} + +\meta{restricted\_expression} is ordinarily a single identifier, though simple +expressions may be used (see Comments below). \meta{expression} is any +valid REDUCE expression. If \meta{expression} is a \nameref{matrix} +identifier, then +\meta{restricted\_expression} can be a matrix identifier (redimensioned if +necessary) which has each element set to the corresponding elements +of the identifier on the right-hand side. + +\begin{Examples} +a := x**2 + 1; & A := X^{2} + 1 \\ +a; & X^{2} + 1 \\ +first := second := third; & FIRST := SECOND := THIRD \\ +first; & THIRD \\ +second; & THIRD \\ +b := for i := 1:5 product i; & B := 120 \\ +b; & 120 \\ +w + (c := x + 3) + z; & W + X + Z + 3 \\ +c; & X + 3 \\ +y + b := c; & Y + B := C \\ +y; & - (B - C) +\end{Examples} + +\begin{Comments} +The assignment operator is right associative, as shown in the second and +third examples. A string of such assignments has all but the last +item set to the value of the last item. Embedding an assignment statement +in another expression has the side effect of making the assignment, as well +as causing the given replacement in the expression. + +Assignments of values to expressions rather than simple identifiers (such as in +the last example above) can also be done, subject to the following remarks: +\begin{itemize} + +\item[(i)] +If the left-hand side is an identifier, an operator, or a power, the +substitution rule is added to the rule table. + +\item[(ii)] +If the operators \name{- + /} appear on the left-hand side, all but the first +term of the expression is moved to the right-hand side. + +\item[(iii)] +If the operator \name{*} appears on the left-hand side, any constant terms are +moved to the right-hand side, but the symbolic factors remain. +\end{itemize} + +Assignment is valid for \nameref{array} elements, but not for entire arrays. +The assignment operator can also be used to attach functionality to operators. + +A recursive construction such as \name{a := a + b} is allowed, but when +\name{a} is referenced again, the process of resubstitution continues +until the expression stack overflows (you get an error message). +Recursive assignments can be done safely inside controlled loop +expressions, such as \nameref{for}\ldots or \nameref{repeat}\ldots\name{until}. + +\end{Comments} +\end{Operator} + + +\begin{Operator}[equalsign]{=} +The \name{=} operator is a prefix or infix equality comparison operator. + +\begin{Syntax} + \name{=}\(\meta{expression}\name{,}\meta{expression}\) + or + \meta{expression} \name{=} \meta{expression} +\end{Syntax} + +\meta{expression} can be any REDUCE scalar expression. + +\begin{Examples} +a := 4; & A := 4 \\ +if =(a,10) then write "yes" else write "no"; + & no \\ +b := c; & B := C \\ +if b = c then write "yes" else write "no"; + & yes \\ +on rounded; \\ +if 4.0 = 4 then write "yes" else write "no"; + & yes +\end{Examples} + +\begin{Comments} +This logical equality operator can only be used inside a conditional +statement, such as \nameref{if}\ldots\name{then}\ldots\name{else} +or \nameref{repeat}\ldots\name{until}. In other places the equal +sign establishes an algebraic object of type \nameref{equation}. + +\end{Comments} +\end{Operator} + + +\begin{Operator}[replace]{=>} + +The \name{=>} operator is a binary operator used in \ref{rule} lists to +denote replacements. + +\begin{Examples} +operator f; \\ +let f(x) => x^2; \\ +f(x); & x^{2} +\end{Examples} +\end{Operator} + + +\begin{Operator}[plussign]{+} +The \name{+} operator is a prefix or infix n-ary addition operator. + +\begin{Syntax} +\meta{expression} \{ \name{+}\meta{expression}\}\repeated + +{\em or} \name{+}\(\meta{expression} \{,\meta{expression}\}\repeated\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +x**4 + 4*x**2 + 17*x + 1; & X^{4} + 4*X^{2} + 17*X + 1 \\ +14 + 15 + x; & X + 29 \\ ++(1,2,3,4,5); & 15 +\end{Examples} + +\begin{Comments} +\name{+} is also valid as an addition operator for \nameref{matrix} variables +that are of the same dimensions and for \nameref{equation}s. +\end{Comments} +\end{Operator} + + +\begin{Operator}[minussign]{-} +The \name{-} operator is a prefix or infix binary subtraction operator, as well +as the unary minus operator. + +\begin{Syntax} +\meta{expression} \name{-} \meta{expression} +or \name{-}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +15 - 4; & 11 \\ +x*(-5); & - 5*X \\ +a - b - 15; & A - B - 15 \\ +-(a,4); & A - 4 +\end{Examples} + +\begin{Comments} +The subtraction operator is left associative, so that a - b - c is equivalent +to (a - b) - c, as shown in the third example. The subtraction operator is +also valid with \nameref{matrix} expressions of the correct dimensions +and with \nameref{equation}s. +\end{Comments} +\end{Operator} + + +\begin{Operator}[asterisk]{*} +The \name{*} operator is a prefix or infix n-ary multiplication operator. + +\begin{Syntax} +\meta{expression} \{ \name{*} \meta{expression}\}\repeated + + or \name{*}\(\meta{expression} \{,\meta{expression}\}\repeated\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +15*3; & 45 \\ +24*x*yvalue*2; & 48*X*YVALUE \\ +*(6,x); & 6*X \\ +on rounded; \\ +3*1.5*x*x*x; & 4.5*X^{3} \\ +off rounded; \\ +2x**2; & 2*X^{2} +\end{Examples} + +\begin{Comments} +REDUCE assumes you are using an implicit multiplication operator when an +identifier is preceded by a number, as shown in the last line above. Since +no valid identifiers can begin with numbers, there is no ambiguity in +making this assumption. + +The multiplication operator is also valid with \nameref{matrix} expressions +of the +proper dimensions: matrices \IFTEX{$A$}{A} and \IFTEX{$B$}{B} +can be multiplied if +\IFTEX{$A$}{A} is \IFTEX{$n \times m$}{n x m} and \IFTEX{$B$}{B} is +\IFTEX{$m \times p$}{m x p}. Matrices and \nameref{equation}s can also be +multiplied by scalars: the +result is as if each element was multiplied by the scalar. +\end{Comments} +\end{Operator} + + +\begin{Operator}[slash]{/} +The \name{/} operator is a prefix or infix binary division operator or +prefix unary \nameref{recip}rocal operator. + +\begin{Syntax} +\meta{expression}\name{/}\meta{expression} {\em or} + \name{/}\meta{expression} + +or \name{/}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +20/5; & 4 \\ +100/6; & \rfrac{50}{3} \\ +16/2/x; & \rfrac{8}{X} \\ +/b; & \rfrac{1}{B} \\ +/(y,5); & \rfrac{Y}{5} \\ +on rounded; \\ +35/4; & 8.75 \\ +/20; & 0.05 +\end{Examples} + +\begin{Comments} +The division operator is left associative, so that \name{a/b/c} is equivalent +to \name{(a/b)/c}. The division operator is also valid with square +\nameref{matrix} expressions of the same dimensions: With \IFTEX{$A$}{A} and +\IFTEX{$B$}{B} both \IFTEX{$n \times n$}{n x n} matrices and \IFTEX{$B$}{B} +invertible, \IFTEX{$A/B$}{A/B} is +given by \IFTEX{$A \times B^{-1}$}{A*B^{-1}}. +Division of a matrix by a scalar is defined, with the results being the +division of each element of the matrix by the scalar. Division of a +scalar by a matrix is defined if the matrix is invertible, and has the +effect of multiplying the scalar by the inverse of the matrix. When +\name{/} is used as a reciprocal operator for a matrix, the inverse of +the matrix is returned if it exists. +\end{Comments} +\end{Operator} + + +\begin{Operator}[power]{**} +The \name{**} operator is a prefix or infix binary exponentiation operator. + +\begin{Syntax} +\meta{expression} \name{**}\meta{expression} + or \name{**}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +x**15; & X^{15} \\ +x**y**z; & X^{Y*Z} \\ +x**(y**z); & X^{Y^{Z}} \\ + **(y,4); & Y^{4} \\ +on rounded; \\ +2**pi; & 8.82497782708 +\end{Examples} + +\begin{Comments} +The exponentiation operator is left associative, so that \name{a**b**c} is +equivalent to \name{(a**b)**c}, as shown in the second example. Note +that this is {\em not} \name{a**(b**c)}, which would be right associative. + +When \nameref{nat} is on (the default), REDUCE output produces raised +exponents, as shown. The symbol \name{^}, which is the upper-case 6 on +most keyboards, may be used in the place of \name{**}. + +A square \nameref{matrix} may also be raised to positive and negative powers +with the exponentiation operator (negative powers require the matrix to be +invertible). Scalar expressions and \nameref{equation}s may be raised to +fractional and floating-point powers. +\end{Comments} +\end{Operator} + +\begin{Operator}[caret]{^} +The \name{^} operator is a prefix or infix binary exponentiation operator. +It is equivalent to \nameref{power} or **. + +\begin{Syntax} +\meta{expression} \name{^}\meta{expression} + or \name{^}\(\meta{expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} may be any valid REDUCE expression. + +\begin{Examples} +x^15; & X^{15} \\ +x^y^z; & X^{Y*Z} \\ +x^(y^z); & X^{Y^{Z}} \\ +^(y,4); & Y^{4} \\ +on rounded; \\ +2^pi; & 8.82497782708 +\end{Examples} + +\begin{Comments} +The exponentiation operator is left associative, so that \name{a^b^c} is +equivalent to \name{(a^b)^c}, as shown in the second example. Note +that this is \meta{not} \name{a^(b^c)}, which would be right associative. + +When \nameref{nat} is on (the default), REDUCE output produces raised +exponents, as shown. + +A square \nameref{matrix} may also be raised to positive +and negative powers with +the exponentiation operator (negative powers require the matrix to be +invertible). Scalar expressions and \nameref{equation}s +may be raised to fractional and floating-point powers. +\end{Comments} +\end{Operator} + + + +\begin{Operator}[geqsign]{>=} +\name{>=} is an infix binary comparison operator, which returns {\em true} if +its first argument is greater than or equal to its second argument. + +\begin{Syntax} +\meta{expression} \name{>=} \meta{expression} +\end{Syntax} + +\meta{expression} must evaluate to an integer or floating-point number. + +\begin{Examples} +if (3 >= 2) then yes; & yes \\ +a := 15; & A := 15 \\ +if a >= 20 then big else small; + & small \\ +\end{Examples} + +\begin{Comments} + +The binary comparison operators can only be used for comparisons between +numbers or variables that evaluate to numbers. The truth values returned +by such a comparison can only be used inside programming constructs, such +as \nameref{if}\ldots\name{then}\ldots\name{else} +or \nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. +\end{Comments} +\end{Operator} + + +\begin{Operator}[greater]{>} +The \name{>} is an infix binary comparison operator that returns +{\em true} if its first argument is strictly greater than its second. + +\begin{Syntax} +\meta{expression} \name{>} \meta{expression} +\end{Syntax} + +\meta{expression} must evaluate to a number, e.g., integer, rational or +floating point number. + +\begin{Examples} +on rounded; \\ +if 3.0 > 3 then write "different" else write "same"; & same \\ +off rounded; \\ +a := 20; & A := 20 \\ +if a > 20 then write "bigger" else write "not bigger"; & not bigger \\ +\end{Examples} + +\begin{Comments} +The binary comparison operators can only be used for comparisons between +numbers or variables that evaluate to numbers. The truth values returned +by such a comparison can only be used inside programming constructs, such +as \nameref{if}\ldots\name{then}\ldots\name{else} or +\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. +\end{Comments} +\end{Operator} + + +\begin{Operator}[leqsign]{<=} +\name{<=} is an infix binary comparison operator that returns +{\em true} if its first argument is less than or equal to its second argument. + +\begin{Syntax} +\meta{expression} \name{<=} \meta{expression} +\end{Syntax} + +\meta{expression} must evaluate to a number, e.g., integer, rational or +floating point number. + +\begin{Examples} +a := 10; & A := 10 \\ +if a <= 10 then true; & true +\end{Examples} + +\begin{Comments} + +The binary comparison operators can only be used for comparisons between +numbers or variables that evaluate to numbers. The truth values returned +by such a comparison can only be used inside programming constructs, such +as \nameref{if}\ldots\name{then}\ldots\name{else} or +\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do}. +\end{Comments} +\end{Operator} + + +\begin{Operator}[less]{<} +\name{<} is an infix binary logical comparison operator that +returns {\em true} if its first argument is strictly less than its second +argument. + +\begin{Syntax} +\meta{expression} \name{<} \meta{expression} +\end{Syntax} + +\meta{expression} must evaluate to a number, e.g., integer, rational or +floating point number. + +\begin{Examples} +f := -3; & F := -3 \\ +if f < -3 then write "yes" else write "no"; & no +\end{Examples} + +\begin{Comments} +The binary comparison operators can only be used for comparisons between +numbers or variables that evaluate to numbers. The truth values returned +by such a comparison can only be used inside programming constructs, such +as \nameref{if}\ldots\name{then}\ldots\name{else} +or \nameref{repeat}\ldots\name{until} or +\nameref{while}\ldots\name{do}. +\end{Comments} +\end{Operator} + +\begin{Operator}[tilde]{~} +The \name{~} is used as a unary prefix operator in the left-hand +sides of \nameref{rule}s to mark \nameref{free variable}s. A double tilde +marks an optional \nameref{free variable}. +\end{Operator} + + +\begin{Command}[group]{<<} +The \name{<<}\ldots\name{>>} command is a group statement, +used to group statements +together where REDUCE expects a single statement. + +%%%INCONSISTENT??? \name{or} +\begin{Syntax} +\name{<<}\meta{statement}\{; \meta{statement} \name{or} + \$\meta{statement}\}\optional \name{>>} +\end{Syntax} + +\meta{statement} may be any valid REDUCE statement or expression. + +\begin{Examples} +a := 2; & A := 2 \\ +if a < 5 then <>; & 12 \\ +<>; + & \rfrac{C^{2} + 90*C + 202}{225} +\end{Examples} + +\begin{Comments} +The value returned from a group statement is the value of the last +individual statement executed inside it. Note that when a semicolon is +placed between the last statement and the closing brackets, 0 or +{\em nil} is returned. Group statements are often used in the +consequence portions of \nameref{if}\ldots\name{then}, +\nameref{repeat}\ldots\name{until}, and +\nameref{while}\ldots\name{do} +clauses. They may also be used in interactive +operation to execute several statements at one time. Statements inside +the group statement are separated by semicolons or dollar signs. + +\end{Comments} +\end{Command} + + +\begin{Operator}{AND} +The \name{and} binary logical operator returns {\em true} if both of its +arguments are {\em true}. + +\begin{Syntax} +\meta{logical\_expression} \name{and} \meta{logical\_expression} +\end{Syntax} + +\meta{logical\_expression} must evaluate to {\em true} or {\em nil}. + +\begin{Examples} +a := 12; & A := 12 \\ +if numberp a and a < 15 then write a**2 else write "no"; + & 144 \\ +clear a; \\ +if numberp a and a < 15 then write a**2 else write "no"; + & no +\end{Examples} + +\begin{Comments} +Logical operators can only be used inside conditional statements, such as +\nameref{while}\ldots\name{do} or +\nameref{if}\ldots\name{then}\ldots\name{else}. \name{and} examines each of +its arguments in order, and quits, returning {\em nil}, on finding an +argument that is not {\em true}. An error results if it is used in other +contexts. + +\name{and} is left associative: \name{x and y and z} is equivalent to +\name{(x and y) and z}. +\end{Comments} +\end{Operator} + + +\begin{Command}{BEGIN} +\name{begin} is used to start a \nameref{block} statement, which is closed with +\name{end}. + +\begin{Syntax} +\name{begin} \meta{statement}\{\name{;} \meta{statement}\}\optional \ \name{end} +\end{Syntax} + +\meta{statement} is any valid REDUCE statement. + +\begin{Examples} +begin for i := 1:3 do write i end; & +\begin{multilineoutput}{1cm} +1 +2 +3 +\end{multilineoutput} \\ +begin scalar n;n:=1;b:=for i:=1:4 product(x-i);return n end; + & 1 \\ +b; & + X^{4} - 10*X^{3} + 35*X^{2} - 50*X + 24 +\end{Examples} + +\begin{Comments} +A \name{begin}\ldots\name{end} block can do actions (such as \name{write}), but +does not +return a value unless instructed to by a \nameref{return} statement, which must +be the last statement executed in the block. It is unnecessary to insert +a semicolon before the \name{end}. + +Local variables, if any, are declared in the first statement immediately +after \name{begin}, and may be defined as \name{scalar, integer,} or +\name{real}. \nameref{array} variables declared +within a \name{begin}\ldots\name{end} block +are global in every case, and \nameref{let} statements have global +effects. A \nameref{let} statement involving a formal parameter affects +the calling parameter that corresponds to it. \nameref{let} statements +involving local variables make global assignments, overwriting outside +variables by the same name or creating them if they do not exist. You +can use this feature to affect global variables from procedures, but be +careful that you do not do it inadvertently. + +\end{Comments} +\end{Command} + + +\begin{Command}{block} +A \name{block} is a sequence of statements enclosed by +commands \nameref{begin} and \nameref{end}. + +\begin{Syntax} +\name{begin} \meta{statement}\{\name{;} \meta{statement}\}\optional \ \name{end} +\end{Syntax} +For more details see \nameref{begin}. +\end{Command} + + +\begin{Command}{COMMENT} +Beginning with the word \name{comment}, all text until the next statement +terminator (\name{;} or \name{\$}) is ignored. + +\begin{Examples} + +x := a**2 comment--a is the velocity of the particle;; + & X := A^{2} +\end{Examples} + +\begin{Comments} +Note that the first semicolon ends the comment and the second one +terminates the original REDUCE statement. + +Multiple-line comments are often needed in interactive files. The +\name{comment} command allows a normal-looking text to accompany the +REDUCE statements in the file. +\end{Comments} +\end{Command} + + +\begin{Operator}{CONS} +The \name{cons} operator adds a new element to the beginning of a +\nameref{list}. Its +operation is identical to the symbol \nameref{dot} (dot). It can be used +infix or prefix. + +\begin{Syntax} +\name{cons}\(\meta{item},\meta{list}\) or \meta{item} \name{cons} \meta{list} +\end{Syntax} + +\meta{item} can be any REDUCE scalar expression, including a list; \meta{list} +must be a list. + +\begin{Examples} + +liss := cons(a,{b}); & \{A,B\} \\ + +liss := c cons liss; & \{C,A,B\} \\ + +newliss := for each y in liss collect cons(y,list x); + & NEWLISS := \{\{C,X\},\{A,X\},\{B,X\}\} \\ + +for each y in newliss sum (first y)*(second y); + & X*(A + B + C) +\end{Examples} + +\begin{Comments} +If you want to use \name{cons} to put together two elements into a new list, +you must make the second one into a list with curly brackets or the \name{list} +command. You can also start with an empty list created by \name{\{\}}. + +The \name{cons} operator is right associative: \name{a cons b cons c} is valid +if \name{c} is a list; \name{b} need not be a list. The list produced is +\name{\{a,b,c\}}. + +\end{Comments} +\end{Operator} + + +\begin{Command}{END} +The command \name{end} has two main uses: +\begin{itemize} +\item[(i)] +as the ending of a \nameref{begin}\ldots\name{end} \nameref{block}; and +\item[(ii)] +to end input from a file. +\end{itemize} + +\begin{Comments} +In a \name{begin}\ldots\name{end} \nameref{block}, there need not be a delimiter +(\name{;} or \name{\$}) before the \name{end}, though there must be one +after it, or a right bracket matching an earlier left bracket. + +Files to be read into REDUCE should end with \name{end;}, which must be +preceded by a semicolon (usually the last character of the previous line). +The additional semicolon avoids problems with mistakes in the files. If +you have suspended file operation by answering \name{n} to a \name{pause} +command, you are still, technically speaking, ``in" the file. Use +\name{end} to exit the file. + +An \name{end} at the top level of a program is ignored. +\end{Comments} +\end{Command} + + +\begin{Type}{EQUATION} +\index{equation}\index{equal}\index{arithmetic} +An \name{equation} is an expression where two algebraic expressions +are connected by the (infix) operator \nameref{equal} or by \nameindex{=}. +For access to the components of an \name{equation} the operators +\nameref{lhs}, \nameref{rhs} or \nameref{part} can be used. The +evaluation of the left-hand side of an \name{equation} is controlled +by the switch \nameref{evallhseqp}, while the right-hand side is +evaluated unconditionally. When an \name{equation} is part of a +logical expression, e.g. in a \nameref{if} or \nameref{while} statement, +the equation is evaluated by subtracting both sides can comparing +the result with zero. + +Equations occur in many contexts, e.g. as arguments of the \nameref{sub} +operator and in the arguments and the results +of the operator \nameref{solve}. An equation can be member of a \nameref{list} +and you may assign an equation to a variable. Elementary arithmetic is supported +for equations: if \nameref{evallhseqp} is on, you may add and subtract +equations, and you can combine an equation with a scalar expression by +addition, subtraction, multiplication, division and raise an equation +to a power. +\begin{Examples} +on evallhseqp;\\ +u:=x+y=1$\\ +v:=2x-y=0$\\ +2*u-v; & - 3*y=-2\\ +ws/3; & y=\rfrac{2}{3}\\ +\end{Examples} +Important: the equation must occur in the leftmost term of such an expression. +For other operations, e.g. taking function values of both sides, use the +\nameref{map} operator. + +\end{Type} + +\begin{Operator}{FIRST} +\index{list}\index{decomposition} +The \name{first} operator returns the first element of a \nameref{list}. +\begin{Syntax} +\name{first}\(\meta{list}\) or \name{first} \meta{list} +\end{Syntax} + +\meta{list} must be a non-empty list to avoid an error message. + +\begin{Examples} +alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ +first alist; & A \\ +blist := \{x,y,\{ww,aa,qq\},z\}; & BLIST := \{X,Y,\{WW,AA,QQ\},Z\} \\ +first third blist; & WW +\end{Examples} +\end{Operator} + + +\begin{Command}{FOR} +\index{loop} +The \name{for} command is used for iterative loops. There are many +possible forms it can take. +\begin{INFO} +{ +\begin{verbatim} + / \ + / |STEP UNTIL| \ + |:=| || +FOR| | : | | + | \ / | + |EACH IN | + \ / + + where ::= DO|PRODUCT|SUM|COLLECT|JOIN. +\end{verbatim} +} +\end{INFO} +\begin{TEX} +\begin{Syntax} + \name{for} + \begin{alternative} + \meta{var} \name{:=} \meta{start} \name{:} \meta{stop}\\ + \meta{var} \name{:=} \meta{start} \name{step} \meta{inc} + \name{until} \meta{stop}\\ + \name{each} \meta{var} \name{in} \meta{list} + \end{alternative} + \begin{alternative} + \name{collect}\\ + \name{do}\\ + \name{join}\\ + \name{product}\\ + \name{sum} + \end{alternative} + \meta{expression} +\end{Syntax} +\end{TEX} + +\meta{var} can be any valid REDUCE identifier except \name{t} or +\name{nil}, \meta{inc}, \meta{start} and \meta{stop} can be any expression +that evaluates to a positive or negative integer. \meta{list} must be a +valid \nameref{list} structure. +The action taken must be one of the actions shown +above, each of which is followed by a single REDUCE expression, statement +or a \nameref{group} (\name{<<}\ldots\name{>>}) or \nameref{block} +(\nameref{begin}\ldots\nameref{end}) statement. + +\begin{Examples} +for i := 1:10 sum i; + & 55 \\ +for a := -2 step 3 until 6 product a; + & -8 \\ +a := 3; & A := 3 \\ +for iter := 4:a do write iter; \\ +m := 0; & M := 0 \\ +for s := 10 step -1 until 3 do <>; \\ +m; & 520 \\ +for each x in {q,r,s} sum x**2; & Q^{2} + R^{2} + S^{2} \\ +for i := 1:4 collect 1/i; + & \{1,\rfrac{1}{2},\rfrac{1}{3},\rfrac{1}{4}\} \\ +for i := 1:3 join list solve(x**2 + i*x + 1,x); + & \begin{multilineoutput}{5cm} +\{\{X= -\rfrac{SQRT(3)*I + 1}{2}, + X= -\rfrac{SQRT(3)*I - 1}{2}\} + \{X=-1\}, + \{X= - \rfrac{SQRT(5) + 3}{2},X=\rfrac{SQRT(5) - 3}{2}\}\} +\end{multilineoutput} +\end{Examples} + +\begin{Comments} +The behavior of each of the five action words follows: + +\begin{TEX} +\begin{center} +\begin{tabular}{|l|p{5cm}|p{5cm}|} +\hline +\multicolumn{3}{|c|}{Action Word Behavior}\\ +\hline +\multicolumn{1}{|c|}{Keyword} & + \multicolumn{1}{c|}{Argument Type} & \multicolumn{1}{c|}{Action} \\ +\hline +do & statement, command, group or block & +Evaluates its argument once for each iteration of the loop, not saving +results \\ +collect & expression, statement, command, group, block, list & +Evaluates its argument once for each iteration of the loop, storing the results +in a list which is returned by the \verb|for| statement when done \\ +join & list or an operator which produces a list & +Evaluates its argument once for each iteration of the loop, appending the +elements in each individual result list onto the overall result list \\ +product & expression, statement, command, +\nameref{group} or \nameref{block} & +Evaluates its argument once for each iteration of the loop, multiplying the +results together and returning the overall product \\ +sum & expression, statement, command, group or block & +Evaluates its argument once for each iteration of the loop, adding the results +together and returning the overall sum\\ +\hline +\end{tabular} +\end{center} +\end{TEX} +\begin{INFO} +{\begin{verbatim} + Action Word Behavior +Keyword Argument Type Action + do statement, command, group Evaluates its argument once + or block for each iteration of the loop, + not saving results +collect expression, statement, Evaluates its argument once for + command, group, block, list each iteration of the loop, + storing the results in a list + which is returned by the for + statement when done + join list or an operator which Evaluates its argument once for + produces a list each iteration of the loop, + appending the elements in each + individual result list onto the + overall result list +product expression, statement, Evaluates its argument once for + command, group or block each iteration of the loop, + multiplying the results together + and returning the overall product + sum expression, statement, Evaluates its argument once for + command, group or block each iteration of the loop, + adding the results together and + returning the overall sum +\end{verbatim} } +\end{INFO} + +For number-driven \name{for} statements, if the ending limit is smaller +than the beginning limit (larger in the case of negative steps) the action +statement is not executed at all. The iterative variable is local to the +\name{for} statement, and does not affect the value of an identifier with +the same name. For list-driven \name{for} statements, if the list is +empty, the action statement is not executed, but no error occurs. + +You can use nested \name{for} statements, with the inner \name{for} +statement after the action keyword. You must make sure that your inner +statement returns an expression that the outer statement can handle. +\end{Comments} +\end{Command} + + +\begin{Command}{FOREACH} +\index{loop} +\name{foreach} is a synonym for the \name{for each} variant of the +\nameref{for} construct. It is designed to iterate down a list, and an +error will occur if a list is not used. The use of \name{for each} is +preferred to \name{foreach}. + +\begin{Syntax} +\name{foreach} \meta{variable} in \meta{list} \meta{action} \meta{expression} \\ + where \meta{action} ::= \name{do | product | sum | collect | join} +\end{Syntax} + +\begin{Examples} +foreach x in {q,r,s} sum x**2; & Q^{2} + R^{2} + S^{2} +\end{Examples} + +\end{Command} + + +\begin{Operator}{GEQ} +The \name{geq} operator is a binary infix or prefix logical operator. It +returns true if its first argument is greater than or equal to its second +argument. As an infix operator it is identical with \name{>=}. +\begin{Syntax} +\name{geq}\(\meta{expression},\meta{expression}\) or \meta{expression} +\name{geq} \meta{expression} +\end{Syntax} + +\meta{expression} can be any valid REDUCE expression that evaluates to a +number. + +\begin{Examples} +a := 20; & A := 20 \\ +if geq(a,25) then write "big" else write "small"; + & small \\ +if a geq 20 then write "big" else write "small"; + & big \\ +if (a geq 18) then write "big" else write "small"; + & big +\end{Examples} + +\begin{Comments} +Logical operators can only be used in conditional statements such as \\ +\nameref{if}\ldots\name{then}\ldots\name{else} or +\nameref{repeat}\ldots\name{until}. +\end{Comments} +\end{Operator} + + +\begin{Command}{GOTO} +Inside a \name{begin}\ldots\name{end} \nameref{block}, \name{goto}, or +preferably, \name{go to}, transfers flow of control to a labeled statement. +\begin{Syntax} +\name{go to} \meta{labeled_statement} or \name{goto} \meta{labeled_statement} +\end{Syntax} +\meta{labeled_statement} is of the form \meta{label} \name{:}\meta{statement} + +\begin{Examples} +\begin{multilineinput} + procedure dumb(a); + begin scalar q; + go to lab; + q := df(a**2 - sin(a),a); + write q; + lab: return a + end; +\end{multilineinput} & DUMB \\ + +dumb(17); & 17 +\end{Examples} + +\begin{Comments} +\name{go to} can only be used inside a \name{begin}\ldots\name{end} +\nameref{block}, and inside +the block only statements at the top level can be labeled, not ones inside +\name{<<}\ldots\name{>>}, \nameref{while}\ldots\name{do}, etc. +\end{Comments} +\end{Command} + + +\begin{Operator}{GREATERP} +The \name{greaterp} logical operator returns true if its first argument is +strictly greater than its second argument. As an infix operator it is +identical with \name{>}. +\begin{Syntax} +\name{greaterp}\(\meta{expression},\meta{expression}\) or \meta{expression} +\name{greaterp} \meta{expression} +\end{Syntax} + +\meta{expression} can be any valid REDUCE expression that evaluates to a +number. + +\begin{Examples} + +a := 20; & A := 20 \\ +if greaterp(a,25) then write "big" else write "small"; + & small \\ +if a greaterp 20 then write "big" else write "small"; + & small \\ +if (a greaterp 18) then write "big" else write "small"; + & big +\end{Examples} + +\begin{Comments} +Logical operators can only be used in conditional statements such as \\ +\nameref{if}\ldots\name{then}\ldots\name{else} +or \nameref{repeat}\ldots\nameref{while}. +\end{Comments} +\end{Operator} + + +\begin{Command}{IF} +The \name{if} command is a conditional statement that executes a statement +if a condition is true, and optionally another statement if it is not. +\begin{Syntax} +\name{if} \meta{condition} \name{then} \meta{statement} +\ \&option\(\name{else}\ \meta{statement}\) +\end{Syntax} + +\meta{condition} must be a logical or comparison operator that evaluates to +a \nameref{boolean value}. +\meta{statement} must be a single REDUCE statement or a +\nameref{group} (\name{<<}\ldots\name{>>}) or +\nameref{block} (\name{begin}\ldots\name{end}) statement. + +\begin{Examples} +if x = 5 then a := b+c else a := d+f; + & D + F \\ +x := 9; & X := 9 \\ +if numberp x and x<20 then y := sqrt(x) else write "illegal"; + & 3 \\ +clear x; \\ +if numberp x and x<20 then y := sqrt(x) else write "illegal"; + & illegal \\ +x := 12; & X := 12 \\ +a := if x < 5 then 100 else 150; + & A := 150 \\ +b := u**(if x < 10 then 2); + & B := 1 \\ +bb := u**(if x > 10 then 2); + & BB := U^{2} +\end{Examples} + +\begin{Comments} +An \name{if} statement may be used inside an assignment statement and sets +its value depending on the conditions, or used anywhere else an +expression would be valid, as shown in the last example. If there is no +\nameindex{else} clause, the value is 0 if a number is expected, and nothing +otherwise. + +The \name{else} clause may be left out if no action is to be taken if the +condition is false. + +The condition may be a compound conditional statement using \nameref{and} or +\nameref{or}. If a non-conditional statement, such as a constant, is used by +accident, it is assumed to have value {\em true}. + +Be sure to use \nameref{group} or \nameref{block} statements after +\nameindex{then} or \name{else}. + +The \name{if} operator is right associative. The following constructions are +examples: +\begin{itemize} +\item[(1)] +\begin{Syntax} +\name{if} \meta{condition} \name{then} \name{if} \meta{condition} \name{then} + \meta{action} \name{else} \meta{action} +\end{Syntax} +%\end{itemize} + +which is equivalent to +\begin{Syntax} +\name{if} \meta{condition} \name{then} \(\name{if}\ \meta{condition} +\ \name{then}\ \meta{action}\ \name{else}\ \meta{action}\); +\end{Syntax} +%\begin{itemize} + +\item[(2)] +\begin{Syntax} +\name{if} \meta{condition} \name{then} \meta{action} \name{else if} + \meta{condition} \name{then} \meta{action} \name{else} \meta{action} +\end{Syntax} +which is equivalent to +\begin{Syntax} +\name{if}\ \meta{condition} \name{then} \meta{action} \name{else} \\ + \(\name{if}\ \meta{condition}\ \name{then}\ \meta{action} +\ \name{else}\ \meta{action}\). +\end{Syntax} +\end{itemize} +\end{Comments} +\end{Command} + + +\begin{Operator}{LIST} +\index{list} +The \name{list} operator constructs a list from its arguments. +\begin{Syntax} +\name{list}\(\meta{item} \{,\meta{item}\}\optional\) or + \name{list}\(\) to construct an empty list. +\end{Syntax} + +\meta{item} can be any REDUCE scalar expression, including another list. +Left and right curly brackets can also be used instead of the operator +\name{list} to construct a list. + +\begin{Examples} +liss := list(c,b,c,\{xx,yy\},3x**2+7x+3,df(sin(2*x),x)); + & LISS := \{C,B,C,\{XX,YY\},3*X^{2} + 7*X + 3,2*COS(2*X)\} \\ +length liss; & 6 \\ +liss := \{c,b,c,\{xx,yy\},3x**2+7x+3,df(sin(2*x),x)\}; + & LISS := \{C,B,C,\{XX,YY\},3*X^{2} + 7*X + 3,2*COS(2*X)\} \\ +emptylis := list(); & EMPTYLIS := \{\} \\ +a . emptylis; & \{A\} +\end{Examples} + +\begin{Comments} +Lists are ordered, hierarchical structures. The elements stay where you +put them, and only change position in the list if you specifically change +them. Lists can have nested sublists to any (reasonable) level. The +\nameref{part} operator can be used to access elements anywhere within a list +hierarchy. The \nameref{length} operator counts the +number of top-level elements +of its list argument; elements that are themselves lists still only +count as one element. +\end{Comments} +\end{Operator} + + +\begin{Operator}{OR} +The \name{or} binary logical operator returns {\it true} if either one or +both of its arguments is {\it true}. +\begin{Syntax} +\meta{logical expression} \name{or} \meta{logical expression} +\end{Syntax} + +\meta{logical expression} must evaluate to {\it true} or {\it nil}. + +\begin{Examples} +a := 10; & A := 10 \\ +\begin{multilineinput} +if a<0 or a>140 then write "not a valid human age" else + write "age = ",a; +\end{multilineinput} \\ +& age = 10 \\ +a := 200; & A := 200 \\ +if a < 0 or a > 140 then write "not a valid human age"; + & not a valid human age +\end{Examples} + +\begin{Comments} +The \name{or} operator is left associative: \name{x or y or z} is equivalent to +\name{(x or y)} \name{or z}. + +Logical operators can only be used in conditional expressions, such as \\ +\nameref{if}\ldots\name{then}\ldots\name{else} +and \nameref{while}\ldots\name{do}. +\name{or} evaluates its arguments in order and quits, returning {\it true}, +on finding the first {\it true} statement. +\end{Comments} +\end{Operator} + + +\begin{Command}{PROCEDURE} +The \name{procedure} command allows you to define a mathematical operation as a +function with arguments. +\begin{Syntax} +\&\meta{option} \name{procedure} \meta{identifier} + \(\meta{arg}\{,\meta{arg}\}\repeated\)\name{;}\meta{body} +\end{Syntax} + +The \meta{option} may be \nameref{algebraic} or \nameref{symbolic}, +indicating the +mode under which the procedure is executed, or \nameref{real} or +\nameref{integer}, indicating the type of answer expected. The default is +algebraic. Real or integer procedures are subtypes of algebraic +procedures; type-checking is done on the results of integer procedures, but +not on real procedures (in the current REDUCE release). \meta{identifier} +may be any valid REDUCE identifier that is not already a procedure name, +operator, \nameref{array} or \nameref{matrix}. +\meta{arg} is a formal parameter that may be any +valid REDUCE identifier. \meta{body} is a single statement (a \nameref{group} +or \nameref{block} statement may be used) with the desired activities in it. + +\begin{Examples} +\begin{multilineinput} +procedure fac(n); + if not (fixp(n) and n>=0) + then rederr "Choose nonneg. integer only" + else for i := 0:n-1 product i+1; +\end{multilineinput} + & FAC \\ +fac(0); & 1 \\ +fac(5); & 120 \\ +fac(-5); & ***** choose nonneg. integer only +\end{Examples} + +\begin{Comments} +Procedures are automatically declared as operators upon definition. When +REDUCE has parsed the procedure definition and successfully converted it to +a form for its own use, it prints the name of the procedure. Procedure +definitions cannot be nested. Procedures can call other procedures, or can +recursively call themselves. Procedure identifiers can be cleared as you +would clear an operator. Unlike \nameref{let} statements, new definitions +under the same procedure name replace the previous definitions completely. + +Be careful not to use the name of a system operator for your own procedure. +REDUCE may or may not give you a warning message. If you redefine a system +operator in your own procedure, the original function of the system operator +is lost for the remainder of the REDUCE session. + +Procedures may have none, one, or more than one parameter. A REDUCE +parameter is a formal parameter only; the use of {\it x} as a parameter in +a \name{procedure} definition has no connection with a value of {\it x} in +the REDUCE session, and the results of calling a procedure have no effect +on the value of {\it x}. If a procedure is {\it called} with {\it x} as a +parameter, the current value of {\it x} is used as specified in the +computation, but is not changed outside the procedure. +Making an assignment statement by \name{:=} with a +formal parameter on the left-hand side only changes the value of the +calling parameter within the procedure. + +Using a \nameref{let} statement inside a procedure always changes the value +globally: a \name{let} with a formal parameter makes the change to the calling +parameter. \name{let} statements cannot be made on local variables inside +\nameref{begin}\ldots\name{end} \nameref{block}\name{s}. +When \nameref{clear} statements are used on formal +parameters, the calling variables associated with them are cleared globally too. +The use of \name{let} or \name{clear} statements inside procedures +should be done with extreme caution. + +Arrays and operators may be used as parameters to procedures. The body of the +procedure can contain statements that appropriately manipulate these +arguments. Changes are made to values of the calling arrays or operators. +Simple expressions can also be used as arguments, in the place of scalar +variables. Matrices may {\it not} be used as arguments to procedures. + +A procedure that has no parameters is called by the procedure name, +immediately followed by empty parentheses. The empty parentheses may be left +out when writing a procedure with no parameters, but must appear in a call of +the procedure. If this is a nuisance to you, use a \nameref{let} statement on +the name of the procedure (i.e., \name{let noargs = noargs()}) after which +you can call the procedure by just its name. + +Procedures that have a single argument can leave out the parentheses around +it both in the definition and procedure call. (You can use the parentheses if +you wish.) Procedures with more than one argument must use parentheses, with +the arguments separated by commas. + +Procedures often have a \name{begin}\ldots\name{end} block in them. Inside the +block, local variables are declared using \name{scalar}, \name{real} or +\name{integer} declarations. +The declarations must be made immediately after the word +\name{begin}, and if more than one type of declaration is made, they are +separated by semicolons. REDUCE currently does no type checking on local +variables; \name{real} and \name{integer} are treated just like \name{scalar}. +Actions take place as specified in the statements inside the block statement. +Any identifiers that are not formal parameters or local variables are treated +as global variables, and activities involving these identifiers are global in +effect. + +If a return value is desired from a procedure call, a specific +\nameref{return} command must be the last statement executed before exiting +from the procedure. If no \name{return} is used, a procedure returns a +zero or no value. + +Procedures are often written in a file using an editor, then the file +is input using the command \nameref{in}. This method allows easy changes in +development, and also allows you to load the named procedures whenever +you like, by loading the files that contain them. +\end{Comments} +\end{Command} + + +\begin{Command}{REPEAT} +\index{loop} +The \nameref{repeat} command causes repeated execution of a statement +\nameindex{until} +the given condition is found to be true. The statement is always executed +at least once. +\begin{Syntax} +\name{repeat} \meta{statement} \name{until} \meta{condition} +\end{Syntax} + +\meta{statement} can be a single statement, \nameref{group} statement, or +a \name{begin}\ldots\name{end} \nameref{block}. \meta{condition} must be +a logical operator that evaluates to {\it true} or {\it nil}. + +\begin{Examples} +<> until m = 0>>; + & \begin{multilineoutput}{6cm} +400*X +300*X +200*X +100*X +\end{multilineoutput}\\ + +<> until m <= 0>>; + & -1 + +\end{Examples} +\begin{Comments} +\name{repeat} must always be followed by an \name{until} with a condition. +Be careful not to generate an infinite loop with a condition that is never +true. In the second example, if the condition had been \name{m = 0}, it +would never have been true since \name{m} already had value -2 when the +condition was first evaluated. +\end{Comments} +\end{Command} + + +\begin{Operator}{REST} +\index{list}\index{decomposition} +The \name{rest} operator returns a \nameref{list} containing all but the first +element of the list it is given. +\begin{Syntax} +\name{rest}\(\meta{list}\) or \name{rest} \meta{list} + + +\end{Syntax} +\meta{list} must be a non-empty list, but need not have more than one element. + +\begin{Examples} +alist := {a,b,c,d}; & ALIST := \{A,B,C,D\}; \\ +rest alist; & \{B,C,D\} \\ +blist := {x,y,{aa,bb,cc},z}; & BLIST := \{X,Y,\{AA,BB,CC\},Z\} \\ +second rest blist; & \{AA,BB,CC\} \\ +clist := {c}; & CLIST := C \\ +rest clist; & \{\} +\end{Examples} + +\end{Operator} + + +\begin{Command}{RETURN} +The \name{return} command causes a value to be returned from inside a +\name{begin}\ldots\name{end} \nameref{block}. +\begin{TEX} +\begin{Syntax} +\name{begin} \meta{statements} \name{return} \meta{\&option(expression)} + \name{end} +\end{Syntax} +\end{TEX} +\begin{INFO} +{\begin{Syntax} +\name{begin} \meta{statements} \name{return} \meta{(expression)} + \name{end} +\end{Syntax} +}\end{INFO} + +\meta{statements} can be any valid REDUCE statements. The value of +\meta{expression} is returned. + +\begin{Examples} +begin write "yes"; return a end; & +\begin{multilineoutput}{5cm} +yes +A +\end{multilineoutput}\\ +\begin{multilineinput} +procedure dumb(a); + begin if numberp(a) then return a else return 10 end; +\end{multilineinput} + & DUMB \\ +dumb(x); & 10 \\ +dumb(-5); & -5 \\ +\begin{multilineinput} +procedure dumb2(a); + begin c := a**2 + 2*a + 1; d := 17; c*d; return end; +\end{multilineinput} & DUMB2 \\ +dumb2(4); \\ +c; & 25 \\ +d; & 17 +\end{Examples} + +\begin{Comments} +Note in \name{dumb2} above that the assignments were made as requested, but +the product \name{c*d} cannot be accessed. Changing the procedure to read +\name{return c*d} would remedy this problem. + +The \name{return} statement is always the last statement executed before +leaving the block. If \name{return} has no argument, the block is exited but +no value is returned. A block statement does not need a \name{return} ; +the statements inside terminate in their normal fashion without one. +In that case no value is returned, although the specified actions inside the +block take place. + +The \name{return} command can be used inside \name{<<}\ldots\name{>>} +\nameref{group} statements and +\nameref{if}\ldots\name{then}\ldots\name{else} commands that +are inside \name{begin}\ldots\name{end} \nameref{block}s. +It is not valid in these constructions that are not inside +a \name{begin}\ldots\name{end} + block. It is not valid inside \nameref{for}, +\nameref{repeat}\ldots\name{until} or \nameref{while}\ldots\name{do} + loops in any construction. To force early termination from loops, the +\name{go to}(\nameref{goto}) command must be used. +When you use nested block statements, a +\name{return} from an inner block exits returning a value to the next-outermost +block, rather than all the way to the outside. +\end{Comments} +\end{Command} + + +\begin{Operator}{REVERSE} +\index{list} +The \name{reverse} operator returns a \nameref{list} that is the reverse of the +list it is given. +\begin{Syntax} +\name{reverse}\(\meta{list}\) or \name{reverse} \meta{list} +\end{Syntax} + +\meta{list} must be a \nameref{list}. + +\begin{Examples} +aa := \{c,b,a,\{x**2,z**3\},y\}; & AA := \{C,B,A,\{X^{2},Z^{3}\},Y\} \\ +reverse aa; & \{Y,\{X^{2},Z^{3}\},A,B,C\} \\ +reverse(q . reverse aa); & \{C,B,A,\{X^{2},Z^{3}\},Y,Q\} +\end{Examples} + +\begin{Comments} +\name{reverse} and \nameref{cons} can be used together to add a new element to +the end of a list (\name{.} adds its new element to the beginning). The +\name{reverse} operator uses a noticeable amount of system resources, +especially if the list is long. If you are doing much heavy-duty list +manipulation, you should probably design your algorithms to avoid much +reversing of lists. A moderate amount of list reversing is no problem. +\end{Comments} +\end{Operator} + + +\begin{Type}{RULE} +\index{rule}\index{rule list} +A \name{rule} is an instruction to replace an algebraic expression +or a part of an expression by another one. +\begin{Syntax} +\meta{lhs} => \meta{rhs} or +\meta{lhs} => \meta{rhs} \name{when} \meta{cond} +\end{Syntax} +\meta{lhs} is an algebraic expression used as search pattern and +\meta{rhs} is an algebraic expression which replaces matches of +\meta{rhs}. \name{=>} is the operator \nameref{replace}. + +\meta{lhs} can contain \nameref{free variable}s which are +symbols preceded by a tilde \nameindex{~} in their leftmost position +in \meta{lhs}. +A double tilde marks an \nameref{optional free variable}. +If a rule has a \name{when} \meta{cond} +part it will fire only if the evaluation of \meta{cond} has a +result \nameref{true}. \meta{cond} may contain references to +free variables of \meta{lhs}. + +Rules can be collected in a \nameref{list} which then forms a +\nameindex{rule list}. \name{Rule lists} can be used to collect +algebraic knowledge for a specific evaluation context. + +\name{Rules} and \name{rule lists} are globally activated and +deactivated by \nameref{let}, \nameref{forall}, \nameref{clearrules}. +For a single evaluation they can be locally activate by \nameref{where}. +The active rules for an operator can be visualized by \nameref{showrules}. + +\begin{Examples} +operator f,g,h; \\ +let f(x) => x^2; \\ +f(x); & x^{2}\\ +g_rules:={g(~n,~x)=>h(n/2,x) when evenp n,\\ +g(~n,~x)=>h((1-n)/2,x) when not evenp n}$\\ +let g_rules;\\ +g(3,x); & h(-1,x) +\end{Examples} + +\end{Type} + +\begin{Type}{Free Variable} +\index{variable} +A variable preceded by a tilde is considered as \name{free variable} +and stands for an arbitrary part in an algebraic form during +pattern matching. Free variables occur in the left-hand sides +of \nameref{rule}s, in the side relations for \nameref{compact} +and in the first arguments of \nameref{map} and \nameref{select} +calls. See \nameref{rule} for examples. + +In rules also \nameref{optional free variable}s may occur. +\end{Type} + +\begin{Type}{Optional Free Variable} +\index{variable} +A variable preceded by a double tilde is considered as +\name{optional free variable} +and stands for an arbitrary part part in an algebraic form during +pattern matching. In contrast to ordinary \nameref{free variable}s +an operator pattern with an \name{optional free variable} +matches also if the operand for the variable is missing. In such +a case the variable is bound to a neutral value. +Optional free variables can be used as + + term in a sum: set to 0 if missing, + + factor in a product: set to 1 if missing, + + exponent: set to 1 if missing + +\begin{Examples} + sin(~~u + ~~n * pi) => sin(u) when evenp u; +\end{Examples} + +Optional free variables are allowed only in the left-hand sides +of \nameref{rule}s. +\end{Type} + +\begin{Operator}{SECOND} +\index{list}\index{decomposition} +The \name{second} operator returns the second element of a list. +\begin{Syntax} +\name{second}\(\meta{list}\) or \name{second} \meta{list} + + +\end{Syntax} + +\meta{list} must be a list with at least two elements, to avoid an error +message. + +\begin{Examples} +alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ +second alist; & B \\ +blist := \{x,\{aa,bb,cc\},z\}; & BLIST := \{X,\{AA,BB,CC\},Z\} \\ +second second blist; & BB +\end{Examples} +\end{Operator} + + +\begin{Operator}{SET} +\index{assign} +The \name{set} operator is used for assignments when you want both sides of +the assignment statement to be evaluated. +%%% INCONSISTENT??? hyphen after restricted +\begin{Syntax} +\name{set}\(\meta{restricted\_expression},\meta{expression}\) +\end{Syntax} + +\meta{expression} can be any REDUCE expression; \meta{restricted\_expression} +must be an identifier or an expression that evaluates to an identifier. + +\begin{Examples} +a := y; & A := Y \\ +set(a,sin(x^2)); & SIN(X^{2}) \\ +a; & SIN(X^{2}) \\ +y; & SIN(X^{2}) \\ +a := b + c; & A := B + C \\ +set(a-c,z); & Z \\ +b; & Z +\end{Examples} + +\begin{Comments} +Using an \nameref{array} or \nameref{matrix} reference as the first +argument to \name{set} has +the result of setting the {\it contents} of the designated element to +\name{set}'s second argument. You should be careful to avoid unwanted +side effects when you use this facility. +\end{Comments} +\end{Operator} + + +\begin{Operator}{SETQ} +\index{assign} +The \name{setq} operator is an infix or prefix binary assignment operator. +It is identical to \name{:=}. +\begin{Syntax} +\name{setq}\(\meta{restricted\_expression},\meta{expression}\) or \\ +\meta{restricted\_expression} \name{setq} \meta{expression} +\end{Syntax} + +\meta{restricted expression} is ordinarily a single identifier, though +simple expressions may be used (see Comments below). \meta{expression} can +be any valid REDUCE expression. If \meta{expression} is a \nameref{matrix} +identifier, then \meta{restricted\_expression} can be a matrix identifier +(redimensioned if necessary), which has each element set to the +corresponding elements of the identifier on the right-hand side. + +\begin{Examples} +setq(b,6); & B := 6 \\ +c setq sin(x); & C := SIN(X) \\ +w + setq(c,x+3) + z; & W + X + Z + 3 \\ +c; & X + 3 \\ +setq(a1 + a2,25); & A1 + A2 := 25 \\ +a1; & - (A2 - 25) +\end{Examples} +\begin{Comments} +Embedding a \name{setq} statement in an expression has the side effect of making +the assignment, as shown in the third example above. + +Assignments are generally done for identifiers, but may be done for simple +expressions as well, subject to the following remarks: +\begin{itemize} + +\item[(i)] +If the left-hand side is an identifier, an operator, or a power, the rule +is added to the rule table. + +\item[(ii)] +If the operators \name{- + /} appear on the left-hand side, all but the first +term of the expression is moved to the right-hand side. + +\item[(iii)] +If the operator \name{*} appears on the left-hand side, any constant terms are +moved to the right-hand side, but the symbolic factors remain. +\end{itemize} + +Be careful not to make a recursive \name{setq} assignment that is not +controlled inside a loop statement. The process of resubstitution +continues until you get a stack overflow message. \name{setq} can be used +to attach functionality to operators, as the \name{:=} does. +\end{Comments} +\end{Operator} + + +\begin{Operator}{THIRD} +\index{list}\index{decomposition} +The \name{third} operator returns the third item of a \nameref{list}. +\begin{Syntax} +\name{third}\(\meta{list}\) or \name{third} \meta{list} + +\end{Syntax} + + +\meta{list} must be a list containing at least three items to avoid an error +message. + +\begin{Examples} +alist := \{a,b,c,d\}; & ALIST := \{A,B,C,D\} \\ +third alist; & C \\ +blist := \{x,\{aa,bb,cc\},y,z\}; & BLIST := \{X,\{AA,BB,CC\},Y,Z\}; \\ +third second blist; & CC \\ +third blist; & Y +\end{Examples} + +\end{Operator} + +\begin{Operator}{WHEN} +\index{rule} +The \name{when} operator is used inside a \name{rule} to make the +execution of the rule depend on a boolean condition which is +evaluated at execution time. For the use see \nameref{rule}. +\end{Operator} + Index: r36/info.tex ================================================================== --- r36/info.tex +++ r36/info.tex @@ -1,414 +1,414 @@ - -% From hearn@rand.orgSat Sep 16 16:54:48 1995 -% Date: Fri, 15 Sep 95 11:15:24 -0700 -% From: Tony Hearn -% To: John Fitch , Arthur Norman , -% Winfried Neun -% Subject: Info package -% -% Here's the latest version. I have incorporated Arthur's suggestions in most -% places. However, I haven't changed the table yet. What I need is -% specific proposals from you guys, like: -% -% Please add the following: -% -% ... -% -% Please delete the following: -% -% ... -% -% Please change the following: -% -% ... -% -% I'll put this on the server now so that it will go this weekend to the -% others. I can then send out the announcement next week. - -% ------------------------------------------------------------------------- - -% -% REDUCE INFORMATION PACKAGE -% -% To produce a printable version of this document, store it as info.tex and -% say: -% latex info -% -% If you prefer, you can obtain a hard copy by sending a request to: -% -% Anthony C. Hearn -% RAND -% 1700 Main Street -% P.O. Box 2138 -% Santa Monica CA 90407-2138 U.S.A. -% Telephone: +1-310-393-0411 Ext. 6615 -% Facsimile: +1-310-393-4818 -% Electronic Mail: reduce@rand.org -% -\documentstyle[11pt]{article} -\textwidth 6.3in -\topmargin -0.4in -\textheight 8.7in -\evensidemargin 0.25in -\oddsidemargin 0.25in -\newcommand{\REDUCE}{REDUCE} -\newlength{\infoboxwidth} -\setlength{\infoboxwidth}{5in} -\begin{document} -\parindent 0pt -\parskip 6pt -\itemsep 0pt -\parsep 0pt -\topsep 0pt -\raggedbottom -\begin{center} -\LARGE -{\bf REDUCE Information Package} -\end{center} -{\REDUCE} is an interactive program designed for general algebraic -computations of interest to mathematicians, scientists and engineers. Its -capabilities include: -\begin{itemize} -\item expansion and ordering of polynomials and rational functions; -\item substitutions and pattern matching in a wide variety of forms; -\item automatic and user controlled simplification of expressions; -\item calculations with symbolic matrices; -\item arbitrary precision integer and real arithmetic; -\item facilities for defining new functions and extending program syntax; -\item analytic differentiation and integration; -\item factorization of polynomials; -\item facilities for the solution of a variety of algebraic equations; -\item facilities for the output of expressions in a variety of formats; -\item facilities for generating optimized numerical programs from symbolic -input; -\item Dirac matrix calculations of interest to high energy physicists. -\end{itemize} -It is often used as an algebraic calculator for problems that are possible -to do by hand. However, the main aim of {\REDUCE} is to support calculations -that are not feasible by hand. Many such calculations take a significant -time to set up and can run for minutes, hours or even days on the most -powerful computers. In support of this goal, {\REDUCE} has the following -characteristics: -\begin{enumerate} -\item Code stability. Various versions of {\REDUCE} have been in use for over -twenty years. There has been a steady stream of improvements and -refinements since then, with the source being subject to wide review by the -user community. {\REDUCE} has thus evolved into a powerful system whose -critical components are highly reliable, stable and efficient. - -\item Wide user base. A particular algebra system is often chosen for a -given calculation because of its widespread use in a particular -application area, with existing packages and templates being used to speed -up problem solving. As evidenced by more than 800 reports listed in the -current bibliography, {\REDUCE} has a large and dedicated user community -working in just about every branch of computational science and -engineering. A large number of special purpose packages are available in -support of this, with many contributed by users. - -\item Full source code availability. From the beginning, it has been -possible to obtain the complete {\REDUCE} source code, including the -``kernel''. Consequently, {\REDUCE} is a valuable educational resource and a -good foundation for experiments in the discipline of computer algebra. Many -users do in fact effectively modify the source code for their own purposes. - -\item Flexible updating. One advantage of making all code accessible to the -user is that it is relatively easy to incorporate patches to correct -small problems or extend the applicability of existing code to new -problem areas. An electronic mail service and gopher and World Wide Web -servers allow users to get such updates and complete new packages as they -become available, without having to wait for a formal system release. - -\item State-of-the-art algorithms. Another advantage of an ``open'' -system is that there is a shared development effort involving both -distributors and users. As a result, it is easier to keep the code -up-to-date, with the best current algorithms being used soon after their -development. At the present time, we believe {\REDUCE} has the best -available code for solving nonlinear polynomial equations using Groebner -bases, real and complex root finding to any precision, exterior calculus -calculations and optimized numerical code generation among others. Its -simplification strategy, using a combination of efficient polynomial -manipulation and flexible pattern matching is focussed on giving users as -natural a result as possible without excessive programming. - -\item Algebraic focus. {\REDUCE} aims at being part of a complete scientific -environment rather than being the complete environment itself. As a -result, users can take advantage of other state-of-the-art systems -specializing in numerical and graphical calculations, rather than depend -on just one system to provide everything. To this end, {\REDUCE} provides -facilities for writing results in a form compatible with common -programming numerical languages (such as Fortran) or document processors -such as TeX. - -\item Portability. Careful design for portability means {\REDUCE} is often -available on new or uncommon machines soon after their release. This has -led to significant user communities throughout the world. At the present -time, {\REDUCE} is readily available on essentially all workstations and -high-end microprocessor-based machines in the market. - -\item Uniformity. Even though {\REDUCE} is supported with different Lisps -on many different platforms, much attention has been paid to making all -versions perform in the same manner regardless of implementation. As a -result, users can have confidence that their calculations will not behave -differently if they move them to a different machine. - -\item Flexible Offerings. To support the differing needs of the user -community, {\REDUCE} is available in a number of different configurations: - -\begin{enumerate} -\item personal system, ready to run, available for a selection of common -personal computers, shipped without source and hence with less easy -updatability between major releases, but at lowest cost for a single user -site; - -\item professional system, which comes with source, and is licensed for -use on one CPU or fileserver and so can be especially attractive for -laboratories or work-groups; - -\item site licenses, which extend the professional system to cover all -similar machines at a single postal address. -\end{enumerate} - -\item Cost. The cost of the complete {\REDUCE} system to the end-user is -moderate, and does not vary substantially from platform to platform. In -addition, the personal system and site licenses are offered on very -generous terms. Moreover, since all systems are derived from the same -source base, they are very compatible from platform to platform (from a PC -to a Cray supercomputer). This makes it possible to have compatible -versions at home and work. -\end{enumerate} - -The most recent release of {\REDUCE} (Version 3.6) is dated 15 July 1995. -It is available for most common computing systems, in some cases in more -than one version for the same machine, through a variety of distributors -listed in this memo. {\REDUCE} is based on a dialect of Lisp called {\em -Standard Lisp}, and the differences between versions are the result of -different implementations of this Lisp; in each case the source code for -{\REDUCE} itself remains the same. The complete source code for {\REDUCE} -is available. On-line versions of the manual and other support documents -and tutorials are also normally included with the distribution. - -In order to help users choose the best version of {\REDUCE} for their -purposes, we shall describe the general characteristics of the available -Lisps. Following this will be a table showing the particular versions -supported on each machine, and finally the full names and addresses of the -{\REDUCE} distributors. - -Since Standard Lisp includes a limited number of functions, it is possible -to run {\REDUCE} on most modern Lisps, since they contain these functions as -a subset. However, the distributed versions of {\REDUCE} are based on two -easily available Lisps, namely: -\begin{itemize} -\item Portable Standard Lisp (PSL). -This is currently the Lisp used most widely for running {\REDUCE}. It -evolved from the original Standard Lisp definition, but now contains many -more facilities. It is quite efficient in its use of both space and time, -and has been optimized for algebraic computation. All PSL versions of -{\REDUCE} are distributed with sufficient PSL support to run on the given -computing system. PSL is supported on many architectures and is an ideal -system for those wanting to run {\REDUCE} as a standalone system. The -current principal developer of PSL is the Konrad Zuse Center, Berlin (ZIB). - -\item Codemist Standard Lisp (CSL). This is a Lisp system written -completely in ANSI C, which makes it very easy to port to a new machine. -Like PSL, it is a faithful implementation of Standard Lisp and has been -optimized for running {\REDUCE}. It requires a very small memory partition -for its Lisp support. Furthermore, most of the {\REDUCE} facilities are -supported as machine independent pseudocode, which is quite compact. In the -worst case, the performance of this system is about a factor of two slower -than PSL, though in many cases it matches PSL performance. However, the -memory use is smaller. All CSL versions are distributed with sufficient CSL -support to run on the given computing system. This is an ideal system for -those wishing to embed algebraic calculations in a C-based programming -environment. The developer of CSL is Codemist Ltd. A version with Japanese -language support is also available from Forbs Ltd. -\end{itemize} -\section*{Demonstration Versions} -Demonstration versions of the CSL-based {\REDUCE} for the IBM PC and -Macintosh described below are available by anonymous ftp from -ftp.bath.ac.uk in the directory pub/jpff/REDUCE . -\newpage -Demonstration versions of the PSL-based {\REDUCE} for the IBM PC described -below are available by anonymous ftp from ftp.zib-berlin.de as follows: -\begin{quote} -pub/reduce/demo/msdos: MS-DOS and Windows 3.1 \\ -pub/reduce/demo/linux: LINUX -\end{quote} - -\section*{Obtaining Further Information about {\REDUCE}} -You can obtain a current copy of this information form at any time by -including the line ``send info-package'' (or ``send info-package.tex'' for -a {\LaTeX} version) in a message to one of the {\REDUCE} network library -servers, namely reduce-netlib@rand.org, reduce-netlib@can.nl or -reduce-netlib@pi.cc.u-tokyo.ac.jp. This message is answered by an -automated server. The library includes packages made available since the -release of {\REDUCE} 3.6 and patches to correct any bugs that have been -discovered. Further information on this library, as well as instructions -on how to join a {\REDUCE} electronic forum, can be obtained by including -``help'' on a separate line in the message. Finally, a set of -introductory examples in {\LaTeX} format can be obtained by including -``send intro.tex'' on a line in your message. - -The same information is available from an Internet gopher server with -the address info.rand.org. The network library files are in a ``REDUCE -Library'' directory under the directory ``Publicly Available Software''. -The relevant URL is gopher://info.rand.org/11/software/reduce . - -A World Wide Web {\REDUCE} server with URL http://www.rrz.uni-koeln.de/REDUCE/ -is also supported. In addition to general information about {\REDUCE}, this -server has pointers to the network library, the demonstration versions, -examples of {\REDUCE} programming, a set of manuals, and the {\REDUCE} online -help system. - -To register for the electronic mail forum, or for further information, -please contact: -\begin{quote} -Anthony C. Hearn \\ -RAND \\ -1700 Main Street \\ -P.O. Box 2138 \\ -Santa Monica CA 90407-2138 \\ -Telephone: +1-310-393-0411 Ext. 6615 \\ -Facsimile: +1-310-393-4818 \\ -Electronic Mail: reduce@rand.org -\end{quote} - -\section*{Versions Available} - -The following table describes the versions of {\REDUCE} supported by the -various distributors. Contact them for detailed price and availability -information. For some machines {\REDUCE} 3.6 may not be available, but 3.5 -still distributed. - -The generic ANSI C version requires some experience with the embedding -language for installation; the machine-specific versions have more -straightforward installation procedures. - -\newpage -\begin{center} -\begin{tabular}{|p{2.8in}|p{2.8in}|} -\hline -\multicolumn{1}{|c|}{{\bf System Description}} & \multicolumn{1}{c|} -{{\bf Distributors (Lisp Used)}} \\ \hline -Generic ANSI C version & Codemist (CSL) \\ \hline - -Acorn Archimedes & Codemist (CSL) \\ \hline - -Apple Macintosh & Codemist (CSL) \\ \hline - -Atari 1040ST and Mega & Codemist (CSL) \\ \hline - -CDC Cyber 910 & ZIB (PSL) \\ \hline - -CDC 4000 series & ZIB (PSL) \\ \hline - -Convex C100, C200 and C300 series& ZIB (PSL) \\ \hline - -Cray X-MP, Y-MP and C90 & ZIB (PSL) \\ \hline - -Data General AViiON series & ZIB (PSL) \\ \hline - -DEC Alpha PC running MS Windows NT & ZIB (PSL) \\ \hline - -DEC Alpha series running OSF-1 or Open VMS& ZIB (PSL) \\ \hline - -DEC DECStation series 2000, 3000 and 5000 & ZIB (PSL) \\ \hline - -DEC VAX running VAX/VMS or Ultrix & ZIB (PSL) \\ \hline - -Fujitsu M Mainframe Unix series & Forbs (CSL) \\ \hline - -Fujitsu 2400 series running UXP/M & ZIB (PSL) \\ \hline - -HP 9000/300 and 400 series & Forbs (CSL); ZIB (PSL) \\ \hline - -HP 9000/700 and 800 series & Forbs (CSL); ZIB (PSL) \\ \hline - -IBM-compatible PCs based on Intel 80286 with extended memory, 80386 and -80486 running MS-DOS & Codemist (CSL); Forbs (CSL) \\ \hline - -IBM-compatible PCs based on Intel 80386 and 80486 running MS-DOS, -MS-Windows 3, OS/2 or Windows NT& ZIB (PSL) \\ \hline - -IBM-compatible PCs based on Intel 80386 and 80486 running UNIX -(SCO-Unix, Interactive, Solaris or LINUX) & ZIB (PSL) \\ \hline - -IBM-compatible PCs based on Intel 80386 and 80486 running Next Step -& ZIB (PSL) \\ \hline - -IBM RISC System/6000 & ZIB (PSL) \\ \hline - -ICL mainframes running VME & Codemist (CSL) \\ \hline - -ICL DRS6000 & Codemist (CSL) \\ \hline - -%\end{tabular} -% -%\begin{tabular}{|p{2.8in}|p{2.8in}|} -%\hline -%\multicolumn{1}{|c|}{{\bf System Description}} & \multicolumn{1}{c|} -%{{\bf Distributors (Lisp Used)}} \\ \hline -NEC EWS 4800 series & Forbs (CSL) \\ \hline - -NEC PC-9800 series & Forbs (CSL) \\ \hline - -NeXTstation & ZIB (PSL) \\ \hline - -Siemens S400/40 series running UXP/M & ZIB (PSL) \\ \hline - -Silicon Graphics IRIS or INDIGO& ZIB (PSL) \\ \hline - -Sony NEWS & Forbs (CSL) \\ \hline - -Sun 3 & Forbs (CSL); ZIB (PSL) \\ \hline - -Sun 4,~~SPARCStation series and compatibles & Forbs (CSL); -ZIB (PSL) \\ \hline - -Thinking Machines CM5 & ZIB (PSL) \\ \hline -\end{tabular} -\end{center} -\newpage -\section*{{\REDUCE} Distributors} -\begin{tabular}{l r} - -Codemist: & \parbox[t]{\infoboxwidth}{ - -Codemist Limited \\ -``Alta'', Horsecombe Vale \\ -Combe Down \\ -Bath BA2 5QR, UNITED KINGDOM \\ -Telephone: +44-1225-837430 \\ -Facsimile: +44-1225-837430 \\ -Electronic Mail: jpff@maths.bath.ac.uk} \\ \\ - -Forbs: & \parbox[t]{\infoboxwidth}{ - -Forbs System Co. Ltd \\ -Kannai JS Building \\ -207 Yamasitachou \\ -Naka-ku \\ -Yokohama 231, JAPAN \\ -Telephone: +81-45-212-5020 \\ -Facsimile: +81-45-212-5023} \\ \\ -% \end{tabular} -% \newpage -% \begin{tabular}{l r} - -ZIB: & \parbox[t]{\infoboxwidth}{ - -Herbert Melenk \\ -Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB) \\ -Heilbronner Str. 10 \\ -D10711 Berlin, GERMANY -Telephone: +49-30-89604-195 \\ -Facsimile: +49-30-89604-125 \\ -Electronic Mail: melenk@sc.zib-berlin.de \\[3mm] -Ordering information for the ZIB versions is available from the URL \\ -http://www.zib-berlin.de/Symbolik/reduce/dist/ or by -anonymous ftp from ftp.zib-berlin.de in pub/reduce/distribution.} - -\end{tabular} \\[0.15in] - -\begin{flushright} \today \end{flushright} -\end{document} + +% From hearn@rand.orgSat Sep 16 16:54:48 1995 +% Date: Fri, 15 Sep 95 11:15:24 -0700 +% From: Tony Hearn +% To: John Fitch , Arthur Norman , +% Winfried Neun +% Subject: Info package +% +% Here's the latest version. I have incorporated Arthur's suggestions in most +% places. However, I haven't changed the table yet. What I need is +% specific proposals from you guys, like: +% +% Please add the following: +% +% ... +% +% Please delete the following: +% +% ... +% +% Please change the following: +% +% ... +% +% I'll put this on the server now so that it will go this weekend to the +% others. I can then send out the announcement next week. + +% ------------------------------------------------------------------------- + +% +% REDUCE INFORMATION PACKAGE +% +% To produce a printable version of this document, store it as info.tex and +% say: +% latex info +% +% If you prefer, you can obtain a hard copy by sending a request to: +% +% Anthony C. Hearn +% RAND +% 1700 Main Street +% P.O. Box 2138 +% Santa Monica CA 90407-2138 U.S.A. +% Telephone: +1-310-393-0411 Ext. 6615 +% Facsimile: +1-310-393-4818 +% Electronic Mail: reduce@rand.org +% +\documentstyle[11pt]{article} +\textwidth 6.3in +\topmargin -0.4in +\textheight 8.7in +\evensidemargin 0.25in +\oddsidemargin 0.25in +\newcommand{\REDUCE}{REDUCE} +\newlength{\infoboxwidth} +\setlength{\infoboxwidth}{5in} +\begin{document} +\parindent 0pt +\parskip 6pt +\itemsep 0pt +\parsep 0pt +\topsep 0pt +\raggedbottom +\begin{center} +\LARGE +{\bf REDUCE Information Package} +\end{center} +{\REDUCE} is an interactive program designed for general algebraic +computations of interest to mathematicians, scientists and engineers. Its +capabilities include: +\begin{itemize} +\item expansion and ordering of polynomials and rational functions; +\item substitutions and pattern matching in a wide variety of forms; +\item automatic and user controlled simplification of expressions; +\item calculations with symbolic matrices; +\item arbitrary precision integer and real arithmetic; +\item facilities for defining new functions and extending program syntax; +\item analytic differentiation and integration; +\item factorization of polynomials; +\item facilities for the solution of a variety of algebraic equations; +\item facilities for the output of expressions in a variety of formats; +\item facilities for generating optimized numerical programs from symbolic +input; +\item Dirac matrix calculations of interest to high energy physicists. +\end{itemize} +It is often used as an algebraic calculator for problems that are possible +to do by hand. However, the main aim of {\REDUCE} is to support calculations +that are not feasible by hand. Many such calculations take a significant +time to set up and can run for minutes, hours or even days on the most +powerful computers. In support of this goal, {\REDUCE} has the following +characteristics: +\begin{enumerate} +\item Code stability. Various versions of {\REDUCE} have been in use for over +twenty years. There has been a steady stream of improvements and +refinements since then, with the source being subject to wide review by the +user community. {\REDUCE} has thus evolved into a powerful system whose +critical components are highly reliable, stable and efficient. + +\item Wide user base. A particular algebra system is often chosen for a +given calculation because of its widespread use in a particular +application area, with existing packages and templates being used to speed +up problem solving. As evidenced by more than 800 reports listed in the +current bibliography, {\REDUCE} has a large and dedicated user community +working in just about every branch of computational science and +engineering. A large number of special purpose packages are available in +support of this, with many contributed by users. + +\item Full source code availability. From the beginning, it has been +possible to obtain the complete {\REDUCE} source code, including the +``kernel''. Consequently, {\REDUCE} is a valuable educational resource and a +good foundation for experiments in the discipline of computer algebra. Many +users do in fact effectively modify the source code for their own purposes. + +\item Flexible updating. One advantage of making all code accessible to the +user is that it is relatively easy to incorporate patches to correct +small problems or extend the applicability of existing code to new +problem areas. An electronic mail service and gopher and World Wide Web +servers allow users to get such updates and complete new packages as they +become available, without having to wait for a formal system release. + +\item State-of-the-art algorithms. Another advantage of an ``open'' +system is that there is a shared development effort involving both +distributors and users. As a result, it is easier to keep the code +up-to-date, with the best current algorithms being used soon after their +development. At the present time, we believe {\REDUCE} has the best +available code for solving nonlinear polynomial equations using Groebner +bases, real and complex root finding to any precision, exterior calculus +calculations and optimized numerical code generation among others. Its +simplification strategy, using a combination of efficient polynomial +manipulation and flexible pattern matching is focussed on giving users as +natural a result as possible without excessive programming. + +\item Algebraic focus. {\REDUCE} aims at being part of a complete scientific +environment rather than being the complete environment itself. As a +result, users can take advantage of other state-of-the-art systems +specializing in numerical and graphical calculations, rather than depend +on just one system to provide everything. To this end, {\REDUCE} provides +facilities for writing results in a form compatible with common +programming numerical languages (such as Fortran) or document processors +such as TeX. + +\item Portability. Careful design for portability means {\REDUCE} is often +available on new or uncommon machines soon after their release. This has +led to significant user communities throughout the world. At the present +time, {\REDUCE} is readily available on essentially all workstations and +high-end microprocessor-based machines in the market. + +\item Uniformity. Even though {\REDUCE} is supported with different Lisps +on many different platforms, much attention has been paid to making all +versions perform in the same manner regardless of implementation. As a +result, users can have confidence that their calculations will not behave +differently if they move them to a different machine. + +\item Flexible Offerings. To support the differing needs of the user +community, {\REDUCE} is available in a number of different configurations: + +\begin{enumerate} +\item personal system, ready to run, available for a selection of common +personal computers, shipped without source and hence with less easy +updatability between major releases, but at lowest cost for a single user +site; + +\item professional system, which comes with source, and is licensed for +use on one CPU or fileserver and so can be especially attractive for +laboratories or work-groups; + +\item site licenses, which extend the professional system to cover all +similar machines at a single postal address. +\end{enumerate} + +\item Cost. The cost of the complete {\REDUCE} system to the end-user is +moderate, and does not vary substantially from platform to platform. In +addition, the personal system and site licenses are offered on very +generous terms. Moreover, since all systems are derived from the same +source base, they are very compatible from platform to platform (from a PC +to a Cray supercomputer). This makes it possible to have compatible +versions at home and work. +\end{enumerate} + +The most recent release of {\REDUCE} (Version 3.6) is dated 15 July 1995. +It is available for most common computing systems, in some cases in more +than one version for the same machine, through a variety of distributors +listed in this memo. {\REDUCE} is based on a dialect of Lisp called {\em +Standard Lisp}, and the differences between versions are the result of +different implementations of this Lisp; in each case the source code for +{\REDUCE} itself remains the same. The complete source code for {\REDUCE} +is available. On-line versions of the manual and other support documents +and tutorials are also normally included with the distribution. + +In order to help users choose the best version of {\REDUCE} for their +purposes, we shall describe the general characteristics of the available +Lisps. Following this will be a table showing the particular versions +supported on each machine, and finally the full names and addresses of the +{\REDUCE} distributors. + +Since Standard Lisp includes a limited number of functions, it is possible +to run {\REDUCE} on most modern Lisps, since they contain these functions as +a subset. However, the distributed versions of {\REDUCE} are based on two +easily available Lisps, namely: +\begin{itemize} +\item Portable Standard Lisp (PSL). +This is currently the Lisp used most widely for running {\REDUCE}. It +evolved from the original Standard Lisp definition, but now contains many +more facilities. It is quite efficient in its use of both space and time, +and has been optimized for algebraic computation. All PSL versions of +{\REDUCE} are distributed with sufficient PSL support to run on the given +computing system. PSL is supported on many architectures and is an ideal +system for those wanting to run {\REDUCE} as a standalone system. The +current principal developer of PSL is the Konrad Zuse Center, Berlin (ZIB). + +\item Codemist Standard Lisp (CSL). This is a Lisp system written +completely in ANSI C, which makes it very easy to port to a new machine. +Like PSL, it is a faithful implementation of Standard Lisp and has been +optimized for running {\REDUCE}. It requires a very small memory partition +for its Lisp support. Furthermore, most of the {\REDUCE} facilities are +supported as machine independent pseudocode, which is quite compact. In the +worst case, the performance of this system is about a factor of two slower +than PSL, though in many cases it matches PSL performance. However, the +memory use is smaller. All CSL versions are distributed with sufficient CSL +support to run on the given computing system. This is an ideal system for +those wishing to embed algebraic calculations in a C-based programming +environment. The developer of CSL is Codemist Ltd. A version with Japanese +language support is also available from Forbs Ltd. +\end{itemize} +\section*{Demonstration Versions} +Demonstration versions of the CSL-based {\REDUCE} for the IBM PC and +Macintosh described below are available by anonymous ftp from +ftp.bath.ac.uk in the directory pub/jpff/REDUCE . +\newpage +Demonstration versions of the PSL-based {\REDUCE} for the IBM PC described +below are available by anonymous ftp from ftp.zib-berlin.de as follows: +\begin{quote} +pub/reduce/demo/msdos: MS-DOS and Windows 3.1 \\ +pub/reduce/demo/linux: LINUX +\end{quote} + +\section*{Obtaining Further Information about {\REDUCE}} +You can obtain a current copy of this information form at any time by +including the line ``send info-package'' (or ``send info-package.tex'' for +a {\LaTeX} version) in a message to one of the {\REDUCE} network library +servers, namely reduce-netlib@rand.org, reduce-netlib@can.nl or +reduce-netlib@pi.cc.u-tokyo.ac.jp. This message is answered by an +automated server. The library includes packages made available since the +release of {\REDUCE} 3.6 and patches to correct any bugs that have been +discovered. Further information on this library, as well as instructions +on how to join a {\REDUCE} electronic forum, can be obtained by including +``help'' on a separate line in the message. Finally, a set of +introductory examples in {\LaTeX} format can be obtained by including +``send intro.tex'' on a line in your message. + +The same information is available from an Internet gopher server with +the address info.rand.org. The network library files are in a ``REDUCE +Library'' directory under the directory ``Publicly Available Software''. +The relevant URL is gopher://info.rand.org/11/software/reduce . + +A World Wide Web {\REDUCE} server with URL http://www.rrz.uni-koeln.de/REDUCE/ +is also supported. In addition to general information about {\REDUCE}, this +server has pointers to the network library, the demonstration versions, +examples of {\REDUCE} programming, a set of manuals, and the {\REDUCE} online +help system. + +To register for the electronic mail forum, or for further information, +please contact: +\begin{quote} +Anthony C. Hearn \\ +RAND \\ +1700 Main Street \\ +P.O. Box 2138 \\ +Santa Monica CA 90407-2138 \\ +Telephone: +1-310-393-0411 Ext. 6615 \\ +Facsimile: +1-310-393-4818 \\ +Electronic Mail: reduce@rand.org +\end{quote} + +\section*{Versions Available} + +The following table describes the versions of {\REDUCE} supported by the +various distributors. Contact them for detailed price and availability +information. For some machines {\REDUCE} 3.6 may not be available, but 3.5 +still distributed. + +The generic ANSI C version requires some experience with the embedding +language for installation; the machine-specific versions have more +straightforward installation procedures. + +\newpage +\begin{center} +\begin{tabular}{|p{2.8in}|p{2.8in}|} +\hline +\multicolumn{1}{|c|}{{\bf System Description}} & \multicolumn{1}{c|} +{{\bf Distributors (Lisp Used)}} \\ \hline +Generic ANSI C version & Codemist (CSL) \\ \hline + +Acorn Archimedes & Codemist (CSL) \\ \hline + +Apple Macintosh & Codemist (CSL) \\ \hline + +Atari 1040ST and Mega & Codemist (CSL) \\ \hline + +CDC Cyber 910 & ZIB (PSL) \\ \hline + +CDC 4000 series & ZIB (PSL) \\ \hline + +Convex C100, C200 and C300 series& ZIB (PSL) \\ \hline + +Cray X-MP, Y-MP and C90 & ZIB (PSL) \\ \hline + +Data General AViiON series & ZIB (PSL) \\ \hline + +DEC Alpha PC running MS Windows NT & ZIB (PSL) \\ \hline + +DEC Alpha series running OSF-1 or Open VMS& ZIB (PSL) \\ \hline + +DEC DECStation series 2000, 3000 and 5000 & ZIB (PSL) \\ \hline + +DEC VAX running VAX/VMS or Ultrix & ZIB (PSL) \\ \hline + +Fujitsu M Mainframe Unix series & Forbs (CSL) \\ \hline + +Fujitsu 2400 series running UXP/M & ZIB (PSL) \\ \hline + +HP 9000/300 and 400 series & Forbs (CSL); ZIB (PSL) \\ \hline + +HP 9000/700 and 800 series & Forbs (CSL); ZIB (PSL) \\ \hline + +IBM-compatible PCs based on Intel 80286 with extended memory, 80386 and +80486 running MS-DOS & Codemist (CSL); Forbs (CSL) \\ \hline + +IBM-compatible PCs based on Intel 80386 and 80486 running MS-DOS, +MS-Windows 3, OS/2 or Windows NT& ZIB (PSL) \\ \hline + +IBM-compatible PCs based on Intel 80386 and 80486 running UNIX +(SCO-Unix, Interactive, Solaris or LINUX) & ZIB (PSL) \\ \hline + +IBM-compatible PCs based on Intel 80386 and 80486 running Next Step +& ZIB (PSL) \\ \hline + +IBM RISC System/6000 & ZIB (PSL) \\ \hline + +ICL mainframes running VME & Codemist (CSL) \\ \hline + +ICL DRS6000 & Codemist (CSL) \\ \hline + +%\end{tabular} +% +%\begin{tabular}{|p{2.8in}|p{2.8in}|} +%\hline +%\multicolumn{1}{|c|}{{\bf System Description}} & \multicolumn{1}{c|} +%{{\bf Distributors (Lisp Used)}} \\ \hline +NEC EWS 4800 series & Forbs (CSL) \\ \hline + +NEC PC-9800 series & Forbs (CSL) \\ \hline + +NeXTstation & ZIB (PSL) \\ \hline + +Siemens S400/40 series running UXP/M & ZIB (PSL) \\ \hline + +Silicon Graphics IRIS or INDIGO& ZIB (PSL) \\ \hline + +Sony NEWS & Forbs (CSL) \\ \hline + +Sun 3 & Forbs (CSL); ZIB (PSL) \\ \hline + +Sun 4,~~SPARCStation series and compatibles & Forbs (CSL); +ZIB (PSL) \\ \hline + +Thinking Machines CM5 & ZIB (PSL) \\ \hline +\end{tabular} +\end{center} +\newpage +\section*{{\REDUCE} Distributors} +\begin{tabular}{l r} + +Codemist: & \parbox[t]{\infoboxwidth}{ + +Codemist Limited \\ +``Alta'', Horsecombe Vale \\ +Combe Down \\ +Bath BA2 5QR, UNITED KINGDOM \\ +Telephone: +44-1225-837430 \\ +Facsimile: +44-1225-837430 \\ +Electronic Mail: jpff@maths.bath.ac.uk} \\ \\ + +Forbs: & \parbox[t]{\infoboxwidth}{ + +Forbs System Co. Ltd \\ +Kannai JS Building \\ +207 Yamasitachou \\ +Naka-ku \\ +Yokohama 231, JAPAN \\ +Telephone: +81-45-212-5020 \\ +Facsimile: +81-45-212-5023} \\ \\ +% \end{tabular} +% \newpage +% \begin{tabular}{l r} + +ZIB: & \parbox[t]{\infoboxwidth}{ + +Herbert Melenk \\ +Konrad-Zuse-Zentrum fuer Informationstechnik Berlin (ZIB) \\ +Heilbronner Str. 10 \\ +D10711 Berlin, GERMANY +Telephone: +49-30-89604-195 \\ +Facsimile: +49-30-89604-125 \\ +Electronic Mail: melenk@sc.zib-berlin.de \\[3mm] +Ordering information for the ZIB versions is available from the URL \\ +http://www.zib-berlin.de/Symbolik/reduce/dist/ or by +anonymous ftp from ftp.zib-berlin.de in pub/reduce/distribution.} + +\end{tabular} \\[0.15in] + +\begin{flushright} \today \end{flushright} +\end{document}  Index: r36/instructions.html ================================================================== --- r36/instructions.html +++ r36/instructions.html @@ -1,104 +1,104 @@ - - INSTRUCTIONS FOR SUBMITTING MATERIAL TO THE REDUCE NETWORK LIBRARY - -We encourage users to send contributions to the REDUCE network library. The -rules are simple, and are designed to increase the effectiveness of the -contribution rather than make more work for the contributor. - -Messages (and also code comments if possible) should be in English. REDUCE -is an international system, used by scientists in many countries who speak -many different languages. The only way to make such a system effective is -to have all dialog in one language, which for obvious reasons is English. - -Lines of code should have a maximum length of 71 characters, and only -contain the symbols listed in the REDUCE User's Manual. Other files -should not contain lines longer than 80 characters. No file should be -more than 100,000 bytes long. This is required so that all known REDUCE -systems can process the code, and electronic mail systems handle the -transmission of the relevant files. - -In the case of a complete package, the following is required: - - 1. A header comment listing - a) the title of the program, - b) the name and address of the author(s), including network address, - c) the date of the program, - d) a brief abstract, - e) the version of REDUCE required, - f) relevant publications, - g) appropriate keywords. - - 2. A separate document file describing the use of the program, preferably - in LaTeX using the style file reduce.sty in the documents directory. - - 3. A test file. This should consist of a sequence of commands that neither - read input nor output to files other than the standard output device. - - 4. A log of the output from running the test file. - - 5. A signed REDUCE Contribution Form giving us rights to the - distribution of the code. - -For smaller code fragments and other material, only the signed form is -needed. This form follows. - - ---------------------------- cut here ---------------------------- - - REDUCE PROGRAM CONTRIBUTION FORM - - -Description of Program Material: - - - - - - - -Principal Author: - - -Organization (if applicable): - - -Postal Address: - - - - - - -Electronic Mail Address: - - -Telephone: - - -Are you the sole author of this software? - - -If not, please write the names of the other authors here and attach their -addresses and telephone numbers. - - - - - - - Acknowledgment and Agreement - -------------- --- --------- - -To the best of my knowledge, I have the right to contribute this program -material without breaching any obligation concerning nondisclosure of -proprietary or confidential information of other persons or organizations. -I am contributing this program material on a nonconfidential, nonobligatory -basis to Anthony C. Hearn ("Hearn") for possible use in the REDUCE algebraic -computation system and its associated program libraries. I agree that Hearn -may use, duplicate, modify, publish, distribute and market the program -material, and authorize others to do so without obligation or liability of -any kind. Hearn may publish my name and address, as the contributor, to -facilitate user inquiries pertaining to this program material. - - - -Signature ____________________________________ Date __________________ + + INSTRUCTIONS FOR SUBMITTING MATERIAL TO THE REDUCE NETWORK LIBRARY + +We encourage users to send contributions to the REDUCE network library. The +rules are simple, and are designed to increase the effectiveness of the +contribution rather than make more work for the contributor. + +Messages (and also code comments if possible) should be in English. REDUCE +is an international system, used by scientists in many countries who speak +many different languages. The only way to make such a system effective is +to have all dialog in one language, which for obvious reasons is English. + +Lines of code should have a maximum length of 71 characters, and only +contain the symbols listed in the REDUCE User's Manual. Other files +should not contain lines longer than 80 characters. No file should be +more than 100,000 bytes long. This is required so that all known REDUCE +systems can process the code, and electronic mail systems handle the +transmission of the relevant files. + +In the case of a complete package, the following is required: + + 1. A header comment listing + a) the title of the program, + b) the name and address of the author(s), including network address, + c) the date of the program, + d) a brief abstract, + e) the version of REDUCE required, + f) relevant publications, + g) appropriate keywords. + + 2. A separate document file describing the use of the program, preferably + in LaTeX using the style file reduce.sty in the documents directory. + + 3. A test file. This should consist of a sequence of commands that neither + read input nor output to files other than the standard output device. + + 4. A log of the output from running the test file. + + 5. A signed REDUCE Contribution Form giving us rights to the + distribution of the code. + +For smaller code fragments and other material, only the signed form is +needed. This form follows. + + ---------------------------- cut here ---------------------------- + + REDUCE PROGRAM CONTRIBUTION FORM + + +Description of Program Material: + + + + + + + +Principal Author: + + +Organization (if applicable): + + +Postal Address: + + + + + + +Electronic Mail Address: + + +Telephone: + + +Are you the sole author of this software? + + +If not, please write the names of the other authors here and attach their +addresses and telephone numbers. + + + + + + + Acknowledgment and Agreement + -------------- --- --------- + +To the best of my knowledge, I have the right to contribute this program +material without breaching any obligation concerning nondisclosure of +proprietary or confidential information of other persons or organizations. +I am contributing this program material on a nonconfidential, nonobligatory +basis to Anthony C. Hearn ("Hearn") for possible use in the REDUCE algebraic +computation system and its associated program libraries. I agree that Hearn +may use, duplicate, modify, publish, distribute and market the program +material, and authorize others to do so without obligation or liability of +any kind. Hearn may publish my name and address, as the contributor, to +facilitate user inquiries pertaining to this program material. + + + +Signature ____________________________________ Date __________________ Index: r36/java/JADECODE.C ================================================================== --- r36/java/JADECODE.C +++ r36/java/JADECODE.C @@ -1,360 +1,360 @@ -/* jadecode.c: Copyright (C) Codemist Ltd., 1996. */ - -#include -#include -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "stream.h" -#include "arith.h" -#include "entries.h" -#include "javahost.h" -#include "javaglb.h" - -static struct { char *opname; } optable[211] = { - "\x00""nop", /* 0 */ - "\x00""aconst_null", /* 1 */ - "\x00""iconst_m1", /* 2 */ - "\x00""iconst_0", /* 3 */ - "\x00""iconst_1", /* 4 */ - "\x00""iconst_2", /* 5 */ - "\x00""iconst_3", /* 6 */ - "\x00""iconst_4", /* 7 */ - "\x00""iconst_5", /* 8 */ - "\x00""lconst_0", /* 9 */ - "\x00""lconst_1", /* 10 */ - "\x00""fconst_0", /* 11 */ - "\x00""fconst_1", /* 12 */ - "\x00""fconst_2", /* 13 */ - "\x00""dconst_0", /* 14 */ - "\x00""dconst_1", /* 15 */ - "\x01""bipush", /* 16 */ - "\x02""sipush", /* 17 */ - "\x11""ldc1", /* 18 */ - "\x12""ldc2", /* 19 */ - "\x12""ldc2w", /* 20 */ - "\x01""iload", /* 21 */ - "\x01""lload", /* 22 */ - "\x01""fload", /* 23 */ - "\x01""dload", /* 24 */ - "\x01""aload", /* 25 */ - "\x00""iload_0", /* 26 */ - "\x00""iload_1", /* 27 */ - "\x00""iload_2", /* 28 */ - "\x00""iload_3", /* 29 */ - "\x00""lload_0", /* 30 */ - "\x00""lload_1", /* 31 */ - "\x00""lload_2", /* 32 */ - "\x00""lload_3", /* 33 */ - "\x00""fload_0", /* 34 */ - "\x00""fload_1", /* 35 */ - "\x00""fload_2", /* 36 */ - "\x00""fload_3", /* 37 */ - "\x00""dload_0", /* 38 */ - "\x00""dload_1", /* 39 */ - "\x00""dload_2", /* 40 */ - "\x00""dload_3", /* 41 */ - "\x00""aload_0", /* 42 */ - "\x00""aload_1", /* 43 */ - "\x00""aload_2", /* 44 */ - "\x00""aload_3", /* 45 */ - "\x00""iaload", /* 46 */ - "\x00""laload", /* 47 */ - "\x00""faload", /* 48 */ - "\x00""daload", /* 49 */ - "\x00""aaload", /* 50 */ - "\x00""baload", /* 51 */ - "\x00""caload", /* 52 */ - "\x00""saload", /* 53 */ - "\x01""istore", /* 54 */ - "\x01""lstore", /* 55 */ - "\x01""fstore", /* 56 */ - "\x01""dstore", /* 57 */ - "\x01""astore", /* 58 */ - "\x00""istore_0", /* 59 */ - "\x00""istore_1", /* 60 */ - "\x00""istore_2", /* 61 */ - "\x00""istore_3", /* 62 */ - "\x00""lstore_0", /* 63 */ - "\x00""lstore_1", /* 64 */ - "\x00""lstore_2", /* 65 */ - "\x00""lstore_3", /* 66 */ - "\x00""fstore_0", /* 67 */ - "\x00""fstore_1", /* 68 */ - "\x00""fstore_2", /* 69 */ - "\x00""fstore_3", /* 70 */ - "\x00""dstore_0", /* 71 */ - "\x00""dstore_1", /* 72 */ - "\x00""dstore_2", /* 73 */ - "\x00""dstore_3", /* 74 */ - "\x00""astore_0", /* 75 */ - "\x00""astore_1", /* 76 */ - "\x00""astore_2", /* 77 */ - "\x00""astore_3", /* 78 */ - "\x00""iastore", /* 79 */ - "\x00""lastore", /* 80 */ - "\x00""fastore", /* 81 */ - "\x00""dastore", /* 82 */ - "\x00""aastore", /* 83 */ - "\x00""bastore", /* 84 */ - "\x00""castore", /* 85 */ - "\x00""sastore", /* 86 */ - "\x00""pop", /* 87 */ - "\x00""pop2", /* 88 */ - "\x00""dup", /* 89 */ - "\x00""dup_x1", /* 90 */ - "\x00""dup_x2", /* 91 */ - "\x00""dup2", /* 92 */ - "\x00""dup2_x1", /* 93 */ - "\x00""dup2_x2", /* 94 */ - "\x00""swap", /* 95 */ - "\x00""iadd", /* 96 */ - "\x00""ladd", /* 97 */ - "\x00""fadd", /* 98 */ - "\x00""dadd", /* 99 */ - "\x00""isub", /* 100 */ - "\x00""lsub", /* 101 */ - "\x00""fsub", /* 102 */ - "\x00""dsub", /* 103 */ - "\x00""imul", /* 104 */ - "\x00""lmul", /* 105 */ - "\x00""fmul", /* 106 */ - "\x00""dmul", /* 107 */ - "\x00""idiv", /* 108 */ - "\x00""ldiv", /* 109 */ - "\x00""fdiv", /* 110 */ - "\x00""ddiv", /* 111 */ - "\x00""irem", /* 112 */ - "\x00""lrem", /* 113 */ - "\x00""frem", /* 114 */ - "\x00""drem", /* 115 */ - "\x00""ineg", /* 116 */ - "\x00""lneg", /* 117 */ - "\x00""fneg", /* 118 */ - "\x00""dneg", /* 119 */ - "\x00""ishl", /* 120 */ - "\x00""ishr", /* 121 */ - "\x00""iushr", /* 122 */ - "\x00""lshl", /* 123 */ - "\x00""lshr", /* 124 */ - "\x00""lushr", /* 125 */ - "\x00""iand", /* 126 */ - "\x00""land", /* 127 */ - "\x00""ior", /* 128 */ - "\x00""lor", /* 129 */ - "\x00""ixor", /* 130 */ - "\x00""lxor", /* 131 */ - "\x03""iinc", /* 132 */ - "\x00""i2l", /* 133 */ - "\x00""i2f", /* 134 */ - "\x00""i2d", /* 135 */ - "\x00""l2i", /* 136 */ - "\x00""l2f", /* 137 */ - "\x00""l2d", /* 138 */ - "\x00""f2i", /* 139 */ - "\x00""f2l", /* 140 */ - "\x00""f2d", /* 141 */ - "\x00""d2i", /* 142 */ - "\x00""d2l", /* 143 */ - "\x00""d2f", /* 144 */ - "\x00""int2byte", /* 145 */ - "\x00""int2char", /* 146 */ - "\x00""int2short", /* 147 */ - "\x00""lcmp", /* 148 */ - "\x00""fcmpl", /* 149 */ - "\x00""fcmpg", /* 150 */ - "\x00""dcmpl", /* 151 */ - "\x00""dcmpg", /* 152 */ - "\x08""ifeq", /* 153 */ - "\x08""ifne", /* 154 */ - "\x08""iflt", /* 155 */ - "\x08""ifge", /* 156 */ - "\x08""ifgt", /* 157 */ - "\x08""ifle", /* 158 */ - "\x08""if_icmpeq", /* 159 */ - "\x08""if_icmpne", /* 160 */ - "\x08""if_icmplt", /* 161 */ - "\x08""if_icmpge", /* 162 */ - "\x08""if_icmpgt", /* 163 */ - "\x08""if_icmple", /* 164 */ - "\x08""if_acmpeq", /* 165 */ - "\x08""if_acmpne", /* 166 */ - "\x08""goto", /* 167 */ - "\x08""jsr", /* 168 */ - "\x01""ret", /* 169 */ - "\x06""tableswitch", /* 170 */ - "\x07""lookupswitch", /* 171 */ - "\x00""ireturn", /* 172 */ - "\x00""lreturn", /* 173 */ - "\x00""freturn", /* 174 */ - "\x00""dreturn", /* 175 */ - "\x00""areturn", /* 176 */ - "\x00""return", /* 177 */ - "\x12""getstatic", /* 178 */ - "\x12""putstatic", /* 179 */ - "\x12""getfield", /* 180 */ - "\x12""putfield", /* 181 */ - "\x12""invokevirtual", /* 182 */ - "\x12""invokenonvirtual", /* 183 */ - "\x12""invokestatic", /* 184 */ - "\x14""invokeinterface", /* 185 */ - "\x00""", /* 186 */ - "\x12""new", /* 187 */ - "\x01""newarray", /* 188 */ - "\x12""anewarray", /* 189 */ - "\x00""arraylength", /* 190 */ - "\x00""athrow", /* 191 */ - "\x12""checkcast", /* 192 */ - "\x12""instanceof", /* 193 */ - "\x00""monitorenter", /* 194 */ - "\x00""monitorexit", /* 195 */ - "\x01""wide", /* 196 */ - "\x13""multinewarray", /* 197 */ - "\x08""ifnull", /* 198 */ - "\x08""ifnonnull", /* 199 */ - "\x09""goto_w", /* 200 */ - "\x09""jsr_w", /* 201 */ - "\x00""breakpoint", /* 202 */ - "\x00""", /* 203 */ - "\x00""", /* 204 */ - "\x00""", /* 205 */ - "\x00""", /* 206 */ - "\x00""", /* 207 */ - "\x00""", /* 208 */ - "\x02""ret_w", /* 209 */ - "\x00""= 210>" }; - -static unsigned char *labtab; - -static void notelab(unsigned32 l) -{ if (l < 0x10000) labtab[l/8] |= 1 << (l%8); - /* err_printf("notelab %d\n", l); */ -} - -static int islab(unsigned32 l) -{ int b = 1 << l%8; - /* err_printf("islab %d\n", l); */ - if (l < 0x10000 && labtab[l/8] & b) - { /* labtab[l/8] ^= b; */ - return 1; - } - return 0; -} - -static int reflab(unsigned32 l) -{ int b = 1 << l%8; - if (l < 0x10000 && labtab[l/8] & b) - { err_printf("L%.4x", l); - return 1; - } - return 0; -} - -#define ztos16(w) (((unsigned32)(w) ^ 0x8000) - 0x8000) - -static void decode_lit(unsigned32 n, Cp_Info *cp, unsigned32 cplen) -{ for (;;) - { if (n == 0 || n >= cplen) - { err_printf("", n); - return; - } - else switch (cp[n].tag) - { -case CONSTANT_Class: err_printf("Class"); goto redo; -case CONSTANT_FieldRef: err_printf("FieldRef"); goto redo2; -case CONSTANT_MethodRef: err_printf("MethodRef"); goto redo2; -case CONSTANT_InterfaceMethodRef: err_printf("InterfaceMethodRef"); goto redo2; -case CONSTANT_String: err_printf("String"); goto redo; -case CONSTANT_Integer: err_printf("Integer:%d",n); return; -case CONSTANT_Float: err_printf("Float:%d",n); return; -case CONSTANT_Long: err_printf("Long:%d",n); return; -case CONSTANT_Double: err_printf("Double:%d",n); return; -case CONSTANT_Utf8: err_printf("Utf8[%d'%*s']", n, - cp[n].len, cp[n].u.utf8); return; -case CONSTANT_Unicode: err_printf("Unicode:%d",n); return; -case CONSTANT_NameAndType: err_printf("NameAndType"); goto redo2; -default: err_printf("", n, cp[n].tag); return; - } -redo: err_printf("[%d]:", n); n = cp[n].u.val; continue; -redo2: err_printf("[%d]:<", n); - decode_lit(cp[n].u.val, cp, cplen); - err_printf(","); - decode_lit(cp[n].len, cp, cplen); - err_printf(">"); return; - } -} - -char *jdecodeopname(unsigned32 op) -{ - if (op >= 210) op = 210; - return optable[op].opname+1; -} - -void javadecode(unsigned8 *code, unsigned32 len, Cp_Info *cp, unsigned32 cplen) -{ unsigned8 *p; - if (labtab == 0) labtab = (unsigned char *)jmalloc(0x10000/8); - memset(labtab, 0, 0x10000/8); - for (p = code; p < code+len;) - { unsigned32 op = *p++; - if (op >= 210) op = 210; - switch (optable[op].opname[0]) - { -default: break; -case 0x11: -case 0x01: p++; break; -case 0x12: -case 0x02: p += 2; break; -case 0x08: notelab(p-1-code + ztos16(p[0]<<8 | p[1])); p += 2; break; -case 0x03: p += 2; break; -case 0x13: p += 3; break; -case 0x14: -case 0x04: p += 4; break; -case 0x09: notelab(p-1-code + (p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3])); p += 4; - break; -case 0x06: ("\ttableswitch!"); break; -case 0x07: ("\tlookupswitch!"); break; - } - } - for (p = code; p < code+len;) - { unsigned32 op = *p++; - unsigned32 off; - if (op >= 210) op = 210; - if (islab(p-1 - code)) err_printf("L%.4x:", p-1 - code); - err_printf("\t%s", optable[op].opname+1); - if (optable[op].opname[0] != 0x00 && strlen(optable[op].opname+1) < 8) - err_printf("\t"); - switch (optable[op].opname[0]) - { -default: break; -case 0x01: err_printf("\t%d", *p++); break; -case 0x11: err_printf("\t"); decode_lit(*p++, cp, cplen); break; -case 0x02: err_printf("\t0x%.4x", p[0]<<8 | p[1]); p += 2; break; -case 0x12: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); p += 2; break; -case 0x08: off = ztos16(p[0]<<8 | p[1]); - err_printf("\t"); - if (!reflab(p-1-code+off)) err_printf("$+0x%.4x", off); - p += 2; break; -case 0x03: err_printf("\t%d,%d", p[0], p[1]); p += 2; break; -case 0x13: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); - err_printf(",%d", p[2]); p += 3; break; -case 0x14: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); - err_printf(",%d,%d", p[2], p[3]); p += 4; break; -case 0x04: err_printf("\t0x%.8x", p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3]); p += 4; - break; -case 0x09: off = p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3]; - err_printf("\t(big)"); - if (!reflab(p-1-code+off)) err_printf("\t$+0x%.8x", off); - p += 4; break; -case 0x06: err_printf("\tswitch!"); - break; -case 0x07: err_printf("\tswitch!"); - break; - } - err_printf("\n"); - } -} - -/* end of jadecode.c */ +/* jadecode.c: Copyright (C) Codemist Ltd., 1996. */ + +#include +#include +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "stream.h" +#include "arith.h" +#include "entries.h" +#include "javahost.h" +#include "javaglb.h" + +static struct { char *opname; } optable[211] = { + "\x00""nop", /* 0 */ + "\x00""aconst_null", /* 1 */ + "\x00""iconst_m1", /* 2 */ + "\x00""iconst_0", /* 3 */ + "\x00""iconst_1", /* 4 */ + "\x00""iconst_2", /* 5 */ + "\x00""iconst_3", /* 6 */ + "\x00""iconst_4", /* 7 */ + "\x00""iconst_5", /* 8 */ + "\x00""lconst_0", /* 9 */ + "\x00""lconst_1", /* 10 */ + "\x00""fconst_0", /* 11 */ + "\x00""fconst_1", /* 12 */ + "\x00""fconst_2", /* 13 */ + "\x00""dconst_0", /* 14 */ + "\x00""dconst_1", /* 15 */ + "\x01""bipush", /* 16 */ + "\x02""sipush", /* 17 */ + "\x11""ldc1", /* 18 */ + "\x12""ldc2", /* 19 */ + "\x12""ldc2w", /* 20 */ + "\x01""iload", /* 21 */ + "\x01""lload", /* 22 */ + "\x01""fload", /* 23 */ + "\x01""dload", /* 24 */ + "\x01""aload", /* 25 */ + "\x00""iload_0", /* 26 */ + "\x00""iload_1", /* 27 */ + "\x00""iload_2", /* 28 */ + "\x00""iload_3", /* 29 */ + "\x00""lload_0", /* 30 */ + "\x00""lload_1", /* 31 */ + "\x00""lload_2", /* 32 */ + "\x00""lload_3", /* 33 */ + "\x00""fload_0", /* 34 */ + "\x00""fload_1", /* 35 */ + "\x00""fload_2", /* 36 */ + "\x00""fload_3", /* 37 */ + "\x00""dload_0", /* 38 */ + "\x00""dload_1", /* 39 */ + "\x00""dload_2", /* 40 */ + "\x00""dload_3", /* 41 */ + "\x00""aload_0", /* 42 */ + "\x00""aload_1", /* 43 */ + "\x00""aload_2", /* 44 */ + "\x00""aload_3", /* 45 */ + "\x00""iaload", /* 46 */ + "\x00""laload", /* 47 */ + "\x00""faload", /* 48 */ + "\x00""daload", /* 49 */ + "\x00""aaload", /* 50 */ + "\x00""baload", /* 51 */ + "\x00""caload", /* 52 */ + "\x00""saload", /* 53 */ + "\x01""istore", /* 54 */ + "\x01""lstore", /* 55 */ + "\x01""fstore", /* 56 */ + "\x01""dstore", /* 57 */ + "\x01""astore", /* 58 */ + "\x00""istore_0", /* 59 */ + "\x00""istore_1", /* 60 */ + "\x00""istore_2", /* 61 */ + "\x00""istore_3", /* 62 */ + "\x00""lstore_0", /* 63 */ + "\x00""lstore_1", /* 64 */ + "\x00""lstore_2", /* 65 */ + "\x00""lstore_3", /* 66 */ + "\x00""fstore_0", /* 67 */ + "\x00""fstore_1", /* 68 */ + "\x00""fstore_2", /* 69 */ + "\x00""fstore_3", /* 70 */ + "\x00""dstore_0", /* 71 */ + "\x00""dstore_1", /* 72 */ + "\x00""dstore_2", /* 73 */ + "\x00""dstore_3", /* 74 */ + "\x00""astore_0", /* 75 */ + "\x00""astore_1", /* 76 */ + "\x00""astore_2", /* 77 */ + "\x00""astore_3", /* 78 */ + "\x00""iastore", /* 79 */ + "\x00""lastore", /* 80 */ + "\x00""fastore", /* 81 */ + "\x00""dastore", /* 82 */ + "\x00""aastore", /* 83 */ + "\x00""bastore", /* 84 */ + "\x00""castore", /* 85 */ + "\x00""sastore", /* 86 */ + "\x00""pop", /* 87 */ + "\x00""pop2", /* 88 */ + "\x00""dup", /* 89 */ + "\x00""dup_x1", /* 90 */ + "\x00""dup_x2", /* 91 */ + "\x00""dup2", /* 92 */ + "\x00""dup2_x1", /* 93 */ + "\x00""dup2_x2", /* 94 */ + "\x00""swap", /* 95 */ + "\x00""iadd", /* 96 */ + "\x00""ladd", /* 97 */ + "\x00""fadd", /* 98 */ + "\x00""dadd", /* 99 */ + "\x00""isub", /* 100 */ + "\x00""lsub", /* 101 */ + "\x00""fsub", /* 102 */ + "\x00""dsub", /* 103 */ + "\x00""imul", /* 104 */ + "\x00""lmul", /* 105 */ + "\x00""fmul", /* 106 */ + "\x00""dmul", /* 107 */ + "\x00""idiv", /* 108 */ + "\x00""ldiv", /* 109 */ + "\x00""fdiv", /* 110 */ + "\x00""ddiv", /* 111 */ + "\x00""irem", /* 112 */ + "\x00""lrem", /* 113 */ + "\x00""frem", /* 114 */ + "\x00""drem", /* 115 */ + "\x00""ineg", /* 116 */ + "\x00""lneg", /* 117 */ + "\x00""fneg", /* 118 */ + "\x00""dneg", /* 119 */ + "\x00""ishl", /* 120 */ + "\x00""ishr", /* 121 */ + "\x00""iushr", /* 122 */ + "\x00""lshl", /* 123 */ + "\x00""lshr", /* 124 */ + "\x00""lushr", /* 125 */ + "\x00""iand", /* 126 */ + "\x00""land", /* 127 */ + "\x00""ior", /* 128 */ + "\x00""lor", /* 129 */ + "\x00""ixor", /* 130 */ + "\x00""lxor", /* 131 */ + "\x03""iinc", /* 132 */ + "\x00""i2l", /* 133 */ + "\x00""i2f", /* 134 */ + "\x00""i2d", /* 135 */ + "\x00""l2i", /* 136 */ + "\x00""l2f", /* 137 */ + "\x00""l2d", /* 138 */ + "\x00""f2i", /* 139 */ + "\x00""f2l", /* 140 */ + "\x00""f2d", /* 141 */ + "\x00""d2i", /* 142 */ + "\x00""d2l", /* 143 */ + "\x00""d2f", /* 144 */ + "\x00""int2byte", /* 145 */ + "\x00""int2char", /* 146 */ + "\x00""int2short", /* 147 */ + "\x00""lcmp", /* 148 */ + "\x00""fcmpl", /* 149 */ + "\x00""fcmpg", /* 150 */ + "\x00""dcmpl", /* 151 */ + "\x00""dcmpg", /* 152 */ + "\x08""ifeq", /* 153 */ + "\x08""ifne", /* 154 */ + "\x08""iflt", /* 155 */ + "\x08""ifge", /* 156 */ + "\x08""ifgt", /* 157 */ + "\x08""ifle", /* 158 */ + "\x08""if_icmpeq", /* 159 */ + "\x08""if_icmpne", /* 160 */ + "\x08""if_icmplt", /* 161 */ + "\x08""if_icmpge", /* 162 */ + "\x08""if_icmpgt", /* 163 */ + "\x08""if_icmple", /* 164 */ + "\x08""if_acmpeq", /* 165 */ + "\x08""if_acmpne", /* 166 */ + "\x08""goto", /* 167 */ + "\x08""jsr", /* 168 */ + "\x01""ret", /* 169 */ + "\x06""tableswitch", /* 170 */ + "\x07""lookupswitch", /* 171 */ + "\x00""ireturn", /* 172 */ + "\x00""lreturn", /* 173 */ + "\x00""freturn", /* 174 */ + "\x00""dreturn", /* 175 */ + "\x00""areturn", /* 176 */ + "\x00""return", /* 177 */ + "\x12""getstatic", /* 178 */ + "\x12""putstatic", /* 179 */ + "\x12""getfield", /* 180 */ + "\x12""putfield", /* 181 */ + "\x12""invokevirtual", /* 182 */ + "\x12""invokenonvirtual", /* 183 */ + "\x12""invokestatic", /* 184 */ + "\x14""invokeinterface", /* 185 */ + "\x00""", /* 186 */ + "\x12""new", /* 187 */ + "\x01""newarray", /* 188 */ + "\x12""anewarray", /* 189 */ + "\x00""arraylength", /* 190 */ + "\x00""athrow", /* 191 */ + "\x12""checkcast", /* 192 */ + "\x12""instanceof", /* 193 */ + "\x00""monitorenter", /* 194 */ + "\x00""monitorexit", /* 195 */ + "\x01""wide", /* 196 */ + "\x13""multinewarray", /* 197 */ + "\x08""ifnull", /* 198 */ + "\x08""ifnonnull", /* 199 */ + "\x09""goto_w", /* 200 */ + "\x09""jsr_w", /* 201 */ + "\x00""breakpoint", /* 202 */ + "\x00""", /* 203 */ + "\x00""", /* 204 */ + "\x00""", /* 205 */ + "\x00""", /* 206 */ + "\x00""", /* 207 */ + "\x00""", /* 208 */ + "\x02""ret_w", /* 209 */ + "\x00""= 210>" }; + +static unsigned char *labtab; + +static void notelab(unsigned32 l) +{ if (l < 0x10000) labtab[l/8] |= 1 << (l%8); + /* err_printf("notelab %d\n", l); */ +} + +static int islab(unsigned32 l) +{ int b = 1 << l%8; + /* err_printf("islab %d\n", l); */ + if (l < 0x10000 && labtab[l/8] & b) + { /* labtab[l/8] ^= b; */ + return 1; + } + return 0; +} + +static int reflab(unsigned32 l) +{ int b = 1 << l%8; + if (l < 0x10000 && labtab[l/8] & b) + { err_printf("L%.4x", l); + return 1; + } + return 0; +} + +#define ztos16(w) (((unsigned32)(w) ^ 0x8000) - 0x8000) + +static void decode_lit(unsigned32 n, Cp_Info *cp, unsigned32 cplen) +{ for (;;) + { if (n == 0 || n >= cplen) + { err_printf("", n); + return; + } + else switch (cp[n].tag) + { +case CONSTANT_Class: err_printf("Class"); goto redo; +case CONSTANT_FieldRef: err_printf("FieldRef"); goto redo2; +case CONSTANT_MethodRef: err_printf("MethodRef"); goto redo2; +case CONSTANT_InterfaceMethodRef: err_printf("InterfaceMethodRef"); goto redo2; +case CONSTANT_String: err_printf("String"); goto redo; +case CONSTANT_Integer: err_printf("Integer:%d",n); return; +case CONSTANT_Float: err_printf("Float:%d",n); return; +case CONSTANT_Long: err_printf("Long:%d",n); return; +case CONSTANT_Double: err_printf("Double:%d",n); return; +case CONSTANT_Utf8: err_printf("Utf8[%d'%*s']", n, + cp[n].len, cp[n].u.utf8); return; +case CONSTANT_Unicode: err_printf("Unicode:%d",n); return; +case CONSTANT_NameAndType: err_printf("NameAndType"); goto redo2; +default: err_printf("", n, cp[n].tag); return; + } +redo: err_printf("[%d]:", n); n = cp[n].u.val; continue; +redo2: err_printf("[%d]:<", n); + decode_lit(cp[n].u.val, cp, cplen); + err_printf(","); + decode_lit(cp[n].len, cp, cplen); + err_printf(">"); return; + } +} + +char *jdecodeopname(unsigned32 op) +{ + if (op >= 210) op = 210; + return optable[op].opname+1; +} + +void javadecode(unsigned8 *code, unsigned32 len, Cp_Info *cp, unsigned32 cplen) +{ unsigned8 *p; + if (labtab == 0) labtab = (unsigned char *)jmalloc(0x10000/8); + memset(labtab, 0, 0x10000/8); + for (p = code; p < code+len;) + { unsigned32 op = *p++; + if (op >= 210) op = 210; + switch (optable[op].opname[0]) + { +default: break; +case 0x11: +case 0x01: p++; break; +case 0x12: +case 0x02: p += 2; break; +case 0x08: notelab(p-1-code + ztos16(p[0]<<8 | p[1])); p += 2; break; +case 0x03: p += 2; break; +case 0x13: p += 3; break; +case 0x14: +case 0x04: p += 4; break; +case 0x09: notelab(p-1-code + (p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3])); p += 4; + break; +case 0x06: ("\ttableswitch!"); break; +case 0x07: ("\tlookupswitch!"); break; + } + } + for (p = code; p < code+len;) + { unsigned32 op = *p++; + unsigned32 off; + if (op >= 210) op = 210; + if (islab(p-1 - code)) err_printf("L%.4x:", p-1 - code); + err_printf("\t%s", optable[op].opname+1); + if (optable[op].opname[0] != 0x00 && strlen(optable[op].opname+1) < 8) + err_printf("\t"); + switch (optable[op].opname[0]) + { +default: break; +case 0x01: err_printf("\t%d", *p++); break; +case 0x11: err_printf("\t"); decode_lit(*p++, cp, cplen); break; +case 0x02: err_printf("\t0x%.4x", p[0]<<8 | p[1]); p += 2; break; +case 0x12: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); p += 2; break; +case 0x08: off = ztos16(p[0]<<8 | p[1]); + err_printf("\t"); + if (!reflab(p-1-code+off)) err_printf("$+0x%.4x", off); + p += 2; break; +case 0x03: err_printf("\t%d,%d", p[0], p[1]); p += 2; break; +case 0x13: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); + err_printf(",%d", p[2]); p += 3; break; +case 0x14: err_printf("\t"); decode_lit(p[0]<<8 | p[1], cp, cplen); + err_printf(",%d,%d", p[2], p[3]); p += 4; break; +case 0x04: err_printf("\t0x%.8x", p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3]); p += 4; + break; +case 0x09: off = p[0]<<24 | p[1]<<16 | p[2]<<8 | p[3]; + err_printf("\t(big)"); + if (!reflab(p-1-code+off)) err_printf("\t$+0x%.8x", off); + p += 4; break; +case 0x06: err_printf("\tswitch!"); + break; +case 0x07: err_printf("\tswitch!"); + break; + } + err_printf("\n"); + } +} + +/* end of jadecode.c */  Index: r36/java/JAVACLFL.C ================================================================== --- r36/java/JAVACLFL.C +++ r36/java/JAVACLFL.C @@ -1,387 +1,387 @@ -/* javaclfl.c: Copyright (C) Codemist Ltd., 1996. */ - -#include -#include -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "stream.h" -#include "arith.h" -#include "entries.h" -#include "javahost.h" -#include "javaglb.h" -/* #include "javatype.h" */ - -#define D_CLASSFILE 1 -#define D_CLASSFILEIO 2 -#define D_CLASSFILECODE 4 - -static int depth; - -static unsigned32 rd1(FILE *f) -{ unsigned32 x = getc(f); - if (debugging & D_CLASSFILEIO) jdebug("rd1 %d", x); - return x; -} - -static unsigned32 rd2(FILE *f) -{ unsigned32 x = getc(f); - x = x<<8 | getc(f); - if (debugging & D_CLASSFILEIO) jdebug("rd2 0x%.4x", x); - return x; -} - -static unsigned32 rd4(FILE *f) -{ unsigned32 x = getc(f); - x = x<<8 | getc(f); - x = x<<8 | getc(f); - x = x<<8 | getc(f); - if (debugging & D_CLASSFILEIO) jdebug("rd4 0x%.8x", x); - return x; -} - -static char *rd1string(FILE *f, unsigned32 n) -{ int i; - unsigned8 *p = (unsigned8 *)jmalloc((n+1) * sizeof(*p)); - for (i=0; iconstant_pool_count) - { Cp_Info *cpitem = &cf->constant_pool[cpx]; - if (cpitem->tag == CONSTANT_Utf8) return cpitem->u.utf8; - return ""; - } - return ""; -} - -static Attribute_Sort lookup_attribute_sort(char *utf8, unsigned32 len) -{ /* Should use 'len' not rely on rd1string() zero padding. */ - if (strcmp(utf8,"SourceFile") == 0) return ATT_SourceFile; - if (strcmp(utf8,"ConstantValue") == 0) return ATT_ConstantValue; - if (strcmp(utf8,"Code") == 0) return ATT_Code; - if (strcmp(utf8,"Exceptions") == 0) return ATT_Exceptions; - if (strcmp(utf8,"LineNumberTable") == 0) return ATT_LineNumberTable; - if (strcmp(utf8,"LocalVariableTable") == 0) return ATT_LocalVariableTable; - return ATT_unknown; -} - -static int rdAttribute_Info(FILE *f, ClassFile *cf, unsigned32 n, Attribute_Info **res); - -static int rdSourceFile_Attribute(FILE *f, ClassFile *cf, - SourceFile_Attribute **res) -{ SourceFile_Attribute *p = (SourceFile_Attribute *)jmalloc(sizeof(*p)); - depth++; - p->sourcefile_index = rd2(f); - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute Sourcefile '%s'", - depth*2, "", cpname(p->sourcefile_index, cf)); - *res = p; - return (depth--, 0); -} - -static int rdConstantValue_Attribute(FILE *f, ClassFile *cf, - ConstantValue_Attribute **res) -{ ConstantValue_Attribute *p = (ConstantValue_Attribute *)jmalloc(sizeof(*p)); - depth++; - p->constantvalue_index = rd2(f); - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute ConstantValue [%d]", - depth*2, "", p->constantvalue_index); - *res = p; - return (depth--, 0); -} - -static int rdCode_Attribute(FILE *f, ClassFile *cf, Code_Attribute **res) -{ Code_Attribute *p = (Code_Attribute *)jmalloc(sizeof(*p)); - unsigned32 i,n; - depth++; - p->max_stack = rd2(f); - p->max_locals = rd2(f); - p->code_length = n = rd4(f); - p->code = (unsigned8 *)jmalloc(n * sizeof(*p->code)); - for (i=0; icode[i] = rd1(f); - p->exception_table_length = n = rd2(f); - p->exception_table = (Exception_Info *)jmalloc(n * sizeof(*p->exception_table)); - for (i=0; iexception_table[i]; - q->start_pc = rd2(f); - q->end_pc = rd2(f); - q->handler_pc = rd2(f); - q->catch_type = rd2(f); - } - p->attributes_count = n = rd2(f); - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute Code \ -(stack %d, locals %d, bytes %d, exceptions %d)", - depth*2, "", - p->max_stack, p->max_locals, - p->code_length, p->exception_table_length); - if (debugging & D_CLASSFILECODE) - javadecode(p->code, p->code_length, - cf->constant_pool, cf->constant_pool_count); - if (rdAttribute_Info(f, cf, n, &p[i].attributes)) return 5; - *res = p; - return (depth--, 0); -} - -static int rdExceptions_Attribute(FILE *f, ClassFile *cf, - Exceptions_Attribute **res) -{ Exceptions_Attribute *p = (Exceptions_Attribute *)jmalloc(sizeof(*p)); - unsigned32 i,n; - depth++; - p->number_of_exceptions = n = rd2(f); - p->exception_index_table = (unsigned16 *)jmalloc(n * sizeof(*p->exception_index_table)); - for (i=0; iexception_index_table[i] = rd2(f); - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute Exceptions (entries %d)", - depth*2, "", p->number_of_exceptions); - *res = p; - return (depth--, 0); -} - -static int rdLineNumberTable_Attribute(FILE *f, ClassFile *cf, - LineNumberTable_Attribute **res) -{ LineNumberTable_Attribute *p = (LineNumberTable_Attribute *)jmalloc(sizeof(*p)); - unsigned32 i,n; - depth++; - p->line_number_table_length = n = rd2(f); - p->line_number_table = (LineNumber_Info *)jmalloc(n * sizeof(*p->line_number_table)); - for (i=0; iline_number_table[i]; - q->start_pc = rd2(f); - q->line_number = rd2(f); - } - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute LineNumberTable (entries %d)", - depth*2, "", p->line_number_table_length); - *res = p; - return (depth--, 0); -} - -static int rdLocalVariableTable_Attribute(FILE *f, ClassFile *cf, - LocalVariableTable_Attribute **res) -{ LocalVariableTable_Attribute *p = (LocalVariableTable_Attribute *)jmalloc(sizeof(*p)); - unsigned32 i,n; - depth++; - p->local_variable_table_length = n = rd2(f); - p->local_variable_table = (LocalVariable_Info *)jmalloc(n * sizeof(*p->local_variable_table)); - for (i=0; ilocal_variable_table[i]; - q->start_pc = rd2(f); - q->length = rd2(f); - q->name_index = rd2(f); - q->signature_index = rd2(f); - q->slot = rd2(f); - } - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute LocalVariableTable (entries %d)", - depth*2, "", p->local_variable_table_length); - *res = p; - return (depth--, 0); -} - -/* 'Attributes' occur more than once in a Classfile, hence they are */ -/* stored in *res (OK/NOK is return value), but reading Attributes */ -/* also requires cf to access the previously read Cp_Info. */ -static int rdAttribute_Info(FILE *f, ClassFile *cf, unsigned32 n, Attribute_Info **res) -{ Attribute_Info *p; - unsigned32 i; - if (n > 0xffff) return 1; - p = (Attribute_Info *)jmalloc(n * sizeof(*p)); - if (debugging & D_CLASSFILE) - jdebug("%*sAttributes_Info %d", depth*2, "", n); - for (i=0; iconstant_pool[cpx]; - if (cpitem->tag != CONSTANT_Utf8) return 3; - switch (p[i].sort = lookup_attribute_sort(cpitem->u.utf8, cpitem->len)) - { -case ATT_Code: - if (rdCode_Attribute(f, cf, &p[i].uattr.code)) return 6; - break; -case ATT_SourceFile: - if (rdSourceFile_Attribute(f, cf, &p[i].uattr.sourcefile)) return 6; - break; -case ATT_ConstantValue: - if (rdConstantValue_Attribute(f, cf, &p[i].uattr.constantvalue)) - return 6; - break; -case ATT_Exceptions: - if (rdExceptions_Attribute(f, cf, &p[i].uattr.exceptions)) - return 6; - break; -case ATT_LineNumberTable: - if (rdLineNumberTable_Attribute(f, cf, &p[i].uattr.linenumbertable)) - return 6; - break; -case ATT_LocalVariableTable: - if (rdLocalVariableTable_Attribute(f, cf, &p[i].uattr.localvariabletable)) - return 6; - break; -default: /* currently ignore other attributes */ - if (debugging & D_CLASSFILE) - jdebug("%*sAttribute '%s' unknown", (depth+1)*2, "", - cpitem->u.utf8); - while (len) rd1(f), len--; - } - } - *res = p; - return 0; -} - -static int rdCp_Info(FILE *f, ClassFile *cf, unsigned32 n) -{ Cp_Info *p; - unsigned32 i, nn; - depth++; - if (n > 0xffff) return 1; - if (debugging & D_CLASSFILE) jdebug("Cp_Info %d", n); - p = (Cp_Info *)jmalloc(n * sizeof(*p)); - /* Yes, the next line really is '1'! */ - for (i=1; i 0xffff) nn = 0; /* EOF */ - p[i].len = nn; p[i].u.utf8 = rd1string(f, nn); - break; -case CONSTANT_Unicode: if ((nn = rd2(f)) > 0xffff) nn = 0; /* EOF */ - p[i].len = nn; p[i].u.utf8 = rd2string(f, nn); - break; -case CONSTANT_NameAndType: - /* stuff signature_index into len */ - p[i].u.val = rd2(f); p[i].len = rd2(f); break; - } - cf->constant_pool = p; - return (depth--, 0); -} - -static int rdInterface_Info(FILE *f, ClassFile *cf, unsigned32 n) -{ unsigned16 *p; - unsigned32 i; - depth++; - if (n > 0xffff) return 1; - if (debugging & D_CLASSFILE) jdebug("Interface_Info %d", n); - p = (unsigned16 *)jmalloc(n * sizeof(*p)); - for (i=0; iinterfaces = p; - return (depth--, 0); -} - -static int rdField_Info(FILE *f, ClassFile *cf, unsigned32 n) -{ Field_Info *p; - unsigned32 i; - depth++; - if (n > 0xffff) return 1; - if (debugging & D_CLASSFILE) jdebug("Field_Info %d", n); - p = (Field_Info *)jmalloc(n * sizeof(*p)); - for (i=0; ifields = p; - return (depth--, 0); -} - -static int rdMethod_Info(FILE *f, ClassFile *cf, unsigned32 n) -{ Method_Info *p; - unsigned32 i; - depth++; - if (n > 0xffff) return 1; - if (debugging & D_CLASSFILE) jdebug("Method_Info %d", n); - p = (Method_Info *)jmalloc(n * sizeof(*p)); - for (i=0; imethods = p; - return (depth--, 0); -} - -ClassFile *rdClassFile(char *name) -{ FILE *f = fopen(name, "rb"); - ClassFile *cf = rdClassFILE1(f, name); - fclose(f); - return cf; -} - -ClassFile *rdClassFILE1(FILE *f, char *name) -{ - ClassFile *cf; - unsigned32 n; - depth = 0; - if (f == 0) - { jsyserr("cannot read '%s'", name); return 0; } - if (rd4(f) != JAVA_MAGIC) - { jsyserr("not class file '%s'", name); return 0; } - if ((n = rd2(f)) > JAVA_THIS_MIN) - jdebug("ClassFile '%s' wrong minor vsn %d", name, n); - if ((n = rd2(f)) != JAVA_THIS_MAJ) - jdebug("ClassFile '%s' wrong major vsn %d", name, n); - cf = (ClassFile *)jmalloc(sizeof(ClassFile)); - cf->constant_pool_count = n = rd2(f); - if (rdCp_Info(f, cf, n)) goto corrupt; - cf->access_flags = rd2(f); - cf->this_class = rd2(f); - cf->super_class = rd2(f); - cf->interfaces_count = n = rd2(f); - if (rdInterface_Info(f, cf, n)) goto corrupt; - cf->fields_count = n = rd2(f); - if (rdField_Info(f, cf, n)) goto corrupt; - cf->methods_count = n = rd2(f); - if (rdMethod_Info(f, cf, n)) goto corrupt; - cf->attributes_count = n = rd2(f); - if (rdAttribute_Info(f, cf, n, &cf->attributes)) goto corrupt; - if (rd1(f) != EOF) jdebug("junk at end of ClassFile '%s'", name); - return cf; -corrupt: - jsyserr("ClassFile '%s' corrupted", name); - return 0; -} +/* javaclfl.c: Copyright (C) Codemist Ltd., 1996. */ + +#include +#include +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "stream.h" +#include "arith.h" +#include "entries.h" +#include "javahost.h" +#include "javaglb.h" +/* #include "javatype.h" */ + +#define D_CLASSFILE 1 +#define D_CLASSFILEIO 2 +#define D_CLASSFILECODE 4 + +static int depth; + +static unsigned32 rd1(FILE *f) +{ unsigned32 x = getc(f); + if (debugging & D_CLASSFILEIO) jdebug("rd1 %d", x); + return x; +} + +static unsigned32 rd2(FILE *f) +{ unsigned32 x = getc(f); + x = x<<8 | getc(f); + if (debugging & D_CLASSFILEIO) jdebug("rd2 0x%.4x", x); + return x; +} + +static unsigned32 rd4(FILE *f) +{ unsigned32 x = getc(f); + x = x<<8 | getc(f); + x = x<<8 | getc(f); + x = x<<8 | getc(f); + if (debugging & D_CLASSFILEIO) jdebug("rd4 0x%.8x", x); + return x; +} + +static char *rd1string(FILE *f, unsigned32 n) +{ int i; + unsigned8 *p = (unsigned8 *)jmalloc((n+1) * sizeof(*p)); + for (i=0; iconstant_pool_count) + { Cp_Info *cpitem = &cf->constant_pool[cpx]; + if (cpitem->tag == CONSTANT_Utf8) return cpitem->u.utf8; + return ""; + } + return ""; +} + +static Attribute_Sort lookup_attribute_sort(char *utf8, unsigned32 len) +{ /* Should use 'len' not rely on rd1string() zero padding. */ + if (strcmp(utf8,"SourceFile") == 0) return ATT_SourceFile; + if (strcmp(utf8,"ConstantValue") == 0) return ATT_ConstantValue; + if (strcmp(utf8,"Code") == 0) return ATT_Code; + if (strcmp(utf8,"Exceptions") == 0) return ATT_Exceptions; + if (strcmp(utf8,"LineNumberTable") == 0) return ATT_LineNumberTable; + if (strcmp(utf8,"LocalVariableTable") == 0) return ATT_LocalVariableTable; + return ATT_unknown; +} + +static int rdAttribute_Info(FILE *f, ClassFile *cf, unsigned32 n, Attribute_Info **res); + +static int rdSourceFile_Attribute(FILE *f, ClassFile *cf, + SourceFile_Attribute **res) +{ SourceFile_Attribute *p = (SourceFile_Attribute *)jmalloc(sizeof(*p)); + depth++; + p->sourcefile_index = rd2(f); + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute Sourcefile '%s'", + depth*2, "", cpname(p->sourcefile_index, cf)); + *res = p; + return (depth--, 0); +} + +static int rdConstantValue_Attribute(FILE *f, ClassFile *cf, + ConstantValue_Attribute **res) +{ ConstantValue_Attribute *p = (ConstantValue_Attribute *)jmalloc(sizeof(*p)); + depth++; + p->constantvalue_index = rd2(f); + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute ConstantValue [%d]", + depth*2, "", p->constantvalue_index); + *res = p; + return (depth--, 0); +} + +static int rdCode_Attribute(FILE *f, ClassFile *cf, Code_Attribute **res) +{ Code_Attribute *p = (Code_Attribute *)jmalloc(sizeof(*p)); + unsigned32 i,n; + depth++; + p->max_stack = rd2(f); + p->max_locals = rd2(f); + p->code_length = n = rd4(f); + p->code = (unsigned8 *)jmalloc(n * sizeof(*p->code)); + for (i=0; icode[i] = rd1(f); + p->exception_table_length = n = rd2(f); + p->exception_table = (Exception_Info *)jmalloc(n * sizeof(*p->exception_table)); + for (i=0; iexception_table[i]; + q->start_pc = rd2(f); + q->end_pc = rd2(f); + q->handler_pc = rd2(f); + q->catch_type = rd2(f); + } + p->attributes_count = n = rd2(f); + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute Code \ +(stack %d, locals %d, bytes %d, exceptions %d)", + depth*2, "", + p->max_stack, p->max_locals, + p->code_length, p->exception_table_length); + if (debugging & D_CLASSFILECODE) + javadecode(p->code, p->code_length, + cf->constant_pool, cf->constant_pool_count); + if (rdAttribute_Info(f, cf, n, &p[i].attributes)) return 5; + *res = p; + return (depth--, 0); +} + +static int rdExceptions_Attribute(FILE *f, ClassFile *cf, + Exceptions_Attribute **res) +{ Exceptions_Attribute *p = (Exceptions_Attribute *)jmalloc(sizeof(*p)); + unsigned32 i,n; + depth++; + p->number_of_exceptions = n = rd2(f); + p->exception_index_table = (unsigned16 *)jmalloc(n * sizeof(*p->exception_index_table)); + for (i=0; iexception_index_table[i] = rd2(f); + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute Exceptions (entries %d)", + depth*2, "", p->number_of_exceptions); + *res = p; + return (depth--, 0); +} + +static int rdLineNumberTable_Attribute(FILE *f, ClassFile *cf, + LineNumberTable_Attribute **res) +{ LineNumberTable_Attribute *p = (LineNumberTable_Attribute *)jmalloc(sizeof(*p)); + unsigned32 i,n; + depth++; + p->line_number_table_length = n = rd2(f); + p->line_number_table = (LineNumber_Info *)jmalloc(n * sizeof(*p->line_number_table)); + for (i=0; iline_number_table[i]; + q->start_pc = rd2(f); + q->line_number = rd2(f); + } + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute LineNumberTable (entries %d)", + depth*2, "", p->line_number_table_length); + *res = p; + return (depth--, 0); +} + +static int rdLocalVariableTable_Attribute(FILE *f, ClassFile *cf, + LocalVariableTable_Attribute **res) +{ LocalVariableTable_Attribute *p = (LocalVariableTable_Attribute *)jmalloc(sizeof(*p)); + unsigned32 i,n; + depth++; + p->local_variable_table_length = n = rd2(f); + p->local_variable_table = (LocalVariable_Info *)jmalloc(n * sizeof(*p->local_variable_table)); + for (i=0; ilocal_variable_table[i]; + q->start_pc = rd2(f); + q->length = rd2(f); + q->name_index = rd2(f); + q->signature_index = rd2(f); + q->slot = rd2(f); + } + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute LocalVariableTable (entries %d)", + depth*2, "", p->local_variable_table_length); + *res = p; + return (depth--, 0); +} + +/* 'Attributes' occur more than once in a Classfile, hence they are */ +/* stored in *res (OK/NOK is return value), but reading Attributes */ +/* also requires cf to access the previously read Cp_Info. */ +static int rdAttribute_Info(FILE *f, ClassFile *cf, unsigned32 n, Attribute_Info **res) +{ Attribute_Info *p; + unsigned32 i; + if (n > 0xffff) return 1; + p = (Attribute_Info *)jmalloc(n * sizeof(*p)); + if (debugging & D_CLASSFILE) + jdebug("%*sAttributes_Info %d", depth*2, "", n); + for (i=0; iconstant_pool[cpx]; + if (cpitem->tag != CONSTANT_Utf8) return 3; + switch (p[i].sort = lookup_attribute_sort(cpitem->u.utf8, cpitem->len)) + { +case ATT_Code: + if (rdCode_Attribute(f, cf, &p[i].uattr.code)) return 6; + break; +case ATT_SourceFile: + if (rdSourceFile_Attribute(f, cf, &p[i].uattr.sourcefile)) return 6; + break; +case ATT_ConstantValue: + if (rdConstantValue_Attribute(f, cf, &p[i].uattr.constantvalue)) + return 6; + break; +case ATT_Exceptions: + if (rdExceptions_Attribute(f, cf, &p[i].uattr.exceptions)) + return 6; + break; +case ATT_LineNumberTable: + if (rdLineNumberTable_Attribute(f, cf, &p[i].uattr.linenumbertable)) + return 6; + break; +case ATT_LocalVariableTable: + if (rdLocalVariableTable_Attribute(f, cf, &p[i].uattr.localvariabletable)) + return 6; + break; +default: /* currently ignore other attributes */ + if (debugging & D_CLASSFILE) + jdebug("%*sAttribute '%s' unknown", (depth+1)*2, "", + cpitem->u.utf8); + while (len) rd1(f), len--; + } + } + *res = p; + return 0; +} + +static int rdCp_Info(FILE *f, ClassFile *cf, unsigned32 n) +{ Cp_Info *p; + unsigned32 i, nn; + depth++; + if (n > 0xffff) return 1; + if (debugging & D_CLASSFILE) jdebug("Cp_Info %d", n); + p = (Cp_Info *)jmalloc(n * sizeof(*p)); + /* Yes, the next line really is '1'! */ + for (i=1; i 0xffff) nn = 0; /* EOF */ + p[i].len = nn; p[i].u.utf8 = rd1string(f, nn); + break; +case CONSTANT_Unicode: if ((nn = rd2(f)) > 0xffff) nn = 0; /* EOF */ + p[i].len = nn; p[i].u.utf8 = rd2string(f, nn); + break; +case CONSTANT_NameAndType: + /* stuff signature_index into len */ + p[i].u.val = rd2(f); p[i].len = rd2(f); break; + } + cf->constant_pool = p; + return (depth--, 0); +} + +static int rdInterface_Info(FILE *f, ClassFile *cf, unsigned32 n) +{ unsigned16 *p; + unsigned32 i; + depth++; + if (n > 0xffff) return 1; + if (debugging & D_CLASSFILE) jdebug("Interface_Info %d", n); + p = (unsigned16 *)jmalloc(n * sizeof(*p)); + for (i=0; iinterfaces = p; + return (depth--, 0); +} + +static int rdField_Info(FILE *f, ClassFile *cf, unsigned32 n) +{ Field_Info *p; + unsigned32 i; + depth++; + if (n > 0xffff) return 1; + if (debugging & D_CLASSFILE) jdebug("Field_Info %d", n); + p = (Field_Info *)jmalloc(n * sizeof(*p)); + for (i=0; ifields = p; + return (depth--, 0); +} + +static int rdMethod_Info(FILE *f, ClassFile *cf, unsigned32 n) +{ Method_Info *p; + unsigned32 i; + depth++; + if (n > 0xffff) return 1; + if (debugging & D_CLASSFILE) jdebug("Method_Info %d", n); + p = (Method_Info *)jmalloc(n * sizeof(*p)); + for (i=0; imethods = p; + return (depth--, 0); +} + +ClassFile *rdClassFile(char *name) +{ FILE *f = fopen(name, "rb"); + ClassFile *cf = rdClassFILE1(f, name); + fclose(f); + return cf; +} + +ClassFile *rdClassFILE1(FILE *f, char *name) +{ + ClassFile *cf; + unsigned32 n; + depth = 0; + if (f == 0) + { jsyserr("cannot read '%s'", name); return 0; } + if (rd4(f) != JAVA_MAGIC) + { jsyserr("not class file '%s'", name); return 0; } + if ((n = rd2(f)) > JAVA_THIS_MIN) + jdebug("ClassFile '%s' wrong minor vsn %d", name, n); + if ((n = rd2(f)) != JAVA_THIS_MAJ) + jdebug("ClassFile '%s' wrong major vsn %d", name, n); + cf = (ClassFile *)jmalloc(sizeof(ClassFile)); + cf->constant_pool_count = n = rd2(f); + if (rdCp_Info(f, cf, n)) goto corrupt; + cf->access_flags = rd2(f); + cf->this_class = rd2(f); + cf->super_class = rd2(f); + cf->interfaces_count = n = rd2(f); + if (rdInterface_Info(f, cf, n)) goto corrupt; + cf->fields_count = n = rd2(f); + if (rdField_Info(f, cf, n)) goto corrupt; + cf->methods_count = n = rd2(f); + if (rdMethod_Info(f, cf, n)) goto corrupt; + cf->attributes_count = n = rd2(f); + if (rdAttribute_Info(f, cf, n, &cf->attributes)) goto corrupt; + if (rd1(f) != EOF) jdebug("junk at end of ClassFile '%s'", name); + return cf; +corrupt: + jsyserr("ClassFile '%s' corrupted", name); + return 0; +}  Index: r36/java/JAVAGLB.H ================================================================== --- r36/java/JAVAGLB.H +++ r36/java/JAVAGLB.H @@ -1,17 +1,17 @@ -/* javaglb.h: Copyright (C) Codemist Ltd., 1996. */ - -extern int debugging; - -extern void jsyserr(char *fmt, ...); -extern void jdebug(char *fmt, ...); -extern void *jmalloc(unsigned32 n); -extern void *jfree(void *p); -extern ClassFile *rdClassFile(char *name); -extern ClassFile *rdClassFILE1(FILE *file, char *name); -extern void javaint(ClassFile *); -extern void javadecode(unsigned8 *code, unsigned32 len, Cp_Info *cp, unsigned32 cplen); -extern char *jdecodeopname(unsigned32 op); -extern ClassFile java_PrintStream; - -/* end of javaglb.h */ +/* javaglb.h: Copyright (C) Codemist Ltd., 1996. */ + +extern int debugging; + +extern void jsyserr(char *fmt, ...); +extern void jdebug(char *fmt, ...); +extern void *jmalloc(unsigned32 n); +extern void *jfree(void *p); +extern ClassFile *rdClassFile(char *name); +extern ClassFile *rdClassFILE1(FILE *file, char *name); +extern void javaint(ClassFile *); +extern void javadecode(unsigned8 *code, unsigned32 len, Cp_Info *cp, unsigned32 cplen); +extern char *jdecodeopname(unsigned32 op); +extern ClassFile java_PrintStream; + +/* end of javaglb.h */  Index: r36/java/JAVAHOST.H ================================================================== --- r36/java/JAVAHOST.H +++ r36/java/JAVAHOST.H @@ -1,164 +1,164 @@ -/* javahost.h: Copyright (C) Codemist Ltd., 1996. */ - - -#define JAVA_MAGIC 0xCAFEBABE -#define JAVA_THIS_MAJ 45 -#define JAVA_THIS_MIN 3 - -/* The following structures define the internal format of a class file: */ - -typedef int32 *(*JavaBuiltin)(int32 *); - -typedef enum Attribute_Sort -{ ATT_unknown, - ATT_SourceFile, - ATT_ConstantValue, - ATT_Code, - ATT_Exceptions, - ATT_LineNumberTable, - ATT_LocalVariableTable -} Attribute_Sort; - -typedef struct Attribute_Info Attribute_Info; - -typedef struct SourceFile_Attribute -{ unsigned16 sourcefile_index; -} SourceFile_Attribute; - -typedef struct ConstantValue_Attribute -{ unsigned16 constantvalue_index; -} ConstantValue_Attribute; - - /* logically local to Code_Attribute */ - typedef struct Exception_Info - { unsigned16 start_pc; - unsigned16 end_pc; - unsigned16 handler_pc; - unsigned16 catch_type; - } Exception_Info; - -typedef struct Code_Attribute -{ unsigned16 max_stack; - unsigned16 max_locals; - unsigned32 code_length; - unsigned16 exception_table_length; - unsigned16 attributes_count; - unsigned8 *code; - Exception_Info *exception_table; - Attribute_Info *attributes; -} Code_Attribute; - -typedef struct Exceptions_Attribute -{ unsigned16 number_of_exceptions; - unsigned16 *exception_index_table; -} Exceptions_Attribute; - - /* logically local to LineNumberTable_Attribute */ - typedef struct LineNumber_Info - { unsigned16 start_pc; - unsigned16 line_number; - } LineNumber_Info; - -typedef struct LineNumberTable_Attribute -{ unsigned16 line_number_table_length; - LineNumber_Info *line_number_table; -} LineNumberTable_Attribute; - - /* logically local to LocalVariableTable_Attribute */ - typedef struct LocalVariable_Info - { unsigned16 start_pc; - unsigned16 length; - unsigned16 name_index; - unsigned16 signature_index; - unsigned16 slot; - } LocalVariable_Info; - -typedef struct LocalVariableTable_Attribute -{ unsigned16 local_variable_table_length; - LocalVariable_Info *local_variable_table; -} LocalVariableTable_Attribute; - -/*typedef*/ struct Attribute_Info -{ enum Attribute_Sort sort; - union { SourceFile_Attribute *sourcefile; - ConstantValue_Attribute *constantvalue; - Code_Attribute *code; - Exceptions_Attribute *exceptions; - LineNumberTable_Attribute *linenumbertable; - LocalVariableTable_Attribute *localvariabletable; } uattr; -}; - -typedef struct Cp_Info -{ unsigned8 tag; - unsigned16 len; - union { unsigned32 val; char *utf8; void *ptr; } u; -} Cp_Info; - -/* Currently Field_Info and Method_Info are identical, but note they */ -/* allow different attributes. */ -typedef struct Field_Info -{ unsigned16 access_flags; - unsigned16 name_index; - unsigned16 signature_index; - unsigned16 attributes_count; - Attribute_Info *attributes; -} Field_Info; - -typedef struct Method_Info -{ unsigned16 access_flags; - unsigned16 name_index; - unsigned16 signature_index; - unsigned16 attributes_count; - Attribute_Info *attributes; -} Method_Info; - -typedef struct ClassFile { -/* Internal representation of class file: see rdClassFile(). */ - unsigned16 access_flags; - unsigned16 this_class; - unsigned16 super_class; - - unsigned16 constant_pool_count; - unsigned16 interfaces_count; - unsigned16 fields_count; - unsigned16 methods_count; - unsigned16 attributes_count; - - Cp_Info *constant_pool; - unsigned16 *interfaces; - Field_Info *fields; - Method_Info *methods; - Attribute_Info *attributes; -} ClassFile; - -/* Cp_Info tags: */ -#define CONSTANT_Class 7 -#define CONSTANT_FieldRef 9 -#define CONSTANT_MethodRef 10 -#define CONSTANT_InterfaceMethodRef 11 -#define CONSTANT_String 8 -#define CONSTANT_Integer 3 -#define CONSTANT_Float 4 -#define CONSTANT_Long 5 -#define CONSTANT_Double 6 -#define CONSTANT_NameAndType 12 -#define CONSTANT_Utf8 1 -#define CONSTANT_Unicode 2 -/* The next (illegal) tag represents the 2nd word of a long or double. */ -#define CONSTANT_Xhalf 42 - -/* access_flags: */ -#define ACC_PUBLIC 0x0001 -#define ACC_PRIVATE 0x0002 -#define ACC_PROTECTED 0x0004 -#define ACC_STATIC 0x0008 -#define ACC_FINAL 0x0010 -#define ACC_SYNCHRONIZED 0x0020 -#define ACC_VOLATILE 0x0040 -#define ACC_TRANSIENT 0x0080 -#define ACC_NATIVE 0x0100 -#define ACC_INTERFACE 0x0200 -#define ACC_ABSTRACT 0x0400 - -/* end of javahost.h */ +/* javahost.h: Copyright (C) Codemist Ltd., 1996. */ + + +#define JAVA_MAGIC 0xCAFEBABE +#define JAVA_THIS_MAJ 45 +#define JAVA_THIS_MIN 3 + +/* The following structures define the internal format of a class file: */ + +typedef int32 *(*JavaBuiltin)(int32 *); + +typedef enum Attribute_Sort +{ ATT_unknown, + ATT_SourceFile, + ATT_ConstantValue, + ATT_Code, + ATT_Exceptions, + ATT_LineNumberTable, + ATT_LocalVariableTable +} Attribute_Sort; + +typedef struct Attribute_Info Attribute_Info; + +typedef struct SourceFile_Attribute +{ unsigned16 sourcefile_index; +} SourceFile_Attribute; + +typedef struct ConstantValue_Attribute +{ unsigned16 constantvalue_index; +} ConstantValue_Attribute; + + /* logically local to Code_Attribute */ + typedef struct Exception_Info + { unsigned16 start_pc; + unsigned16 end_pc; + unsigned16 handler_pc; + unsigned16 catch_type; + } Exception_Info; + +typedef struct Code_Attribute +{ unsigned16 max_stack; + unsigned16 max_locals; + unsigned32 code_length; + unsigned16 exception_table_length; + unsigned16 attributes_count; + unsigned8 *code; + Exception_Info *exception_table; + Attribute_Info *attributes; +} Code_Attribute; + +typedef struct Exceptions_Attribute +{ unsigned16 number_of_exceptions; + unsigned16 *exception_index_table; +} Exceptions_Attribute; + + /* logically local to LineNumberTable_Attribute */ + typedef struct LineNumber_Info + { unsigned16 start_pc; + unsigned16 line_number; + } LineNumber_Info; + +typedef struct LineNumberTable_Attribute +{ unsigned16 line_number_table_length; + LineNumber_Info *line_number_table; +} LineNumberTable_Attribute; + + /* logically local to LocalVariableTable_Attribute */ + typedef struct LocalVariable_Info + { unsigned16 start_pc; + unsigned16 length; + unsigned16 name_index; + unsigned16 signature_index; + unsigned16 slot; + } LocalVariable_Info; + +typedef struct LocalVariableTable_Attribute +{ unsigned16 local_variable_table_length; + LocalVariable_Info *local_variable_table; +} LocalVariableTable_Attribute; + +/*typedef*/ struct Attribute_Info +{ enum Attribute_Sort sort; + union { SourceFile_Attribute *sourcefile; + ConstantValue_Attribute *constantvalue; + Code_Attribute *code; + Exceptions_Attribute *exceptions; + LineNumberTable_Attribute *linenumbertable; + LocalVariableTable_Attribute *localvariabletable; } uattr; +}; + +typedef struct Cp_Info +{ unsigned8 tag; + unsigned16 len; + union { unsigned32 val; char *utf8; void *ptr; } u; +} Cp_Info; + +/* Currently Field_Info and Method_Info are identical, but note they */ +/* allow different attributes. */ +typedef struct Field_Info +{ unsigned16 access_flags; + unsigned16 name_index; + unsigned16 signature_index; + unsigned16 attributes_count; + Attribute_Info *attributes; +} Field_Info; + +typedef struct Method_Info +{ unsigned16 access_flags; + unsigned16 name_index; + unsigned16 signature_index; + unsigned16 attributes_count; + Attribute_Info *attributes; +} Method_Info; + +typedef struct ClassFile { +/* Internal representation of class file: see rdClassFile(). */ + unsigned16 access_flags; + unsigned16 this_class; + unsigned16 super_class; + + unsigned16 constant_pool_count; + unsigned16 interfaces_count; + unsigned16 fields_count; + unsigned16 methods_count; + unsigned16 attributes_count; + + Cp_Info *constant_pool; + unsigned16 *interfaces; + Field_Info *fields; + Method_Info *methods; + Attribute_Info *attributes; +} ClassFile; + +/* Cp_Info tags: */ +#define CONSTANT_Class 7 +#define CONSTANT_FieldRef 9 +#define CONSTANT_MethodRef 10 +#define CONSTANT_InterfaceMethodRef 11 +#define CONSTANT_String 8 +#define CONSTANT_Integer 3 +#define CONSTANT_Float 4 +#define CONSTANT_Long 5 +#define CONSTANT_Double 6 +#define CONSTANT_NameAndType 12 +#define CONSTANT_Utf8 1 +#define CONSTANT_Unicode 2 +/* The next (illegal) tag represents the 2nd word of a long or double. */ +#define CONSTANT_Xhalf 42 + +/* access_flags: */ +#define ACC_PUBLIC 0x0001 +#define ACC_PRIVATE 0x0002 +#define ACC_PROTECTED 0x0004 +#define ACC_STATIC 0x0008 +#define ACC_FINAL 0x0010 +#define ACC_SYNCHRONIZED 0x0020 +#define ACC_VOLATILE 0x0040 +#define ACC_TRANSIENT 0x0080 +#define ACC_NATIVE 0x0100 +#define ACC_INTERFACE 0x0200 +#define ACC_ABSTRACT 0x0400 + +/* end of javahost.h */  Index: r36/java/JAVAINT.C ================================================================== --- r36/java/JAVAINT.C +++ r36/java/JAVAINT.C @@ -1,536 +1,536 @@ -/* javaint.c: Copyright (C) Codemist Ltd., 1996. */ - -#include -/* #include */ -#include -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "stream.h" -#include "arith.h" -#include "entries.h" -#include "javahost.h" -#include "javaops.h" -#include "javaglb.h" - -/* integers representing exceptions (map to Java exceptions in javaint(). */ -#define E_NegativeArraySizeException 1 -#define E_OutOfMemoryError 2 -#define E_NullPointerException 3 -#define E_ArrayIndexOutOfBoundsException 4 - -#define JSTK_MAX 10000 -#ifdef DOWNWARD_STACK /* need to fix up locals too! */ -#define push_(sp,v) (*--(sp)=(v)) -#define pop_(sp) (*(sp)++) -#define lose_(sp,k) ((sp)+=(k)) -#define stk_(sp,k) ((sp)[k]) -#define STLO 0 -#define STHI 1 -#define loc_(lv,k) (*((lv)-(k))) -#else -#define push_(sp,v) (*++(sp)=(v)) -#define pop_(sp) (*(sp)--) -#define lose_(sp,k) ((sp)-=(k)) -#define stk_(sp,k) (*((sp)-(k))) -#define STLO 1 -#define STHI 0 -#define loc_(lv,k) ((lv)[k]) -#endif - -static void jraise(int E_whatever) -{ jsyserr("Exceptions unimplemented"); -} - -static int java_sizeof(int32 t) -{ switch (t) - { default: jsyserr("bad type code to newarray()"); - case T_BOOLEAN: return 1; - case T_CHAR: return 1; - case T_FLOAT: return 4; - case T_DOUBLE: return 8; - case T_BYTE: return 1; - case T_SHORT: return 2; - case T_INT: return 4; - case T_LONG: return 8; - case -1: return 4; /* for anewarray */ - } -} - -typedef struct JavaArray -{ unsigned32 length; - /* access long/double by stream as maybe not aligned */ - union { int8 elts8[1]; unsigned8 eltu8[1]; - int16 elts16[1]; unsigned16 eltu16[1]; int32 elt32[1]; } u; -} JavaArray; - -static int32 java_newarray(int32 *sp, int32 flavour, int32 refclass, int32 k) -{ /* Note that 'k' is (number of dimensions)-1. */ - /* Caller loses junk when k>0 (j_multinewarray). */ - /* k>0 not supported yet. */ - JavaArray *res; - int32 nelts = stk_(sp,0), csize; - if (nelts < 0) return E_NegativeArraySizeException; - csize = java_sizeof(flavour)*nelts + sizeof(int32); - res = (JavaArray *)jmalloc(csize); - if (res == 0) return E_OutOfMemoryError; - memset(res, 0, csize); /* @@@ beware 0 = HR_NULL assumed! */ - res->length = nelts; - stk_(sp,k) = (int32)res; /*ALPHA*/ - return 0; -} - -/* beware host/java rep issues here */ -#define HR_NULL 0 /* Host Representation? */ -static const union { struct { double d[2]; float f[3]; } s; - int32 r[7]; - } hostflttab = { 0.0, 1.0, 0.0f, 1.0f, 2.0f }; -/* Remember many of the following are zero (optimise?) */ -#define HR_D0W1 hostflttab.r[0] -#define HR_D0W2 hostflttab.r[1] -#define HR_D1W1 hostflttab.r[2] -#define HR_D1W2 hostflttab.r[3] -#define HR_F0 hostflttab.r[4] -#define HR_F1 hostflttab.r[5] -#define HR_F2 hostflttab.r[6] - -typedef union DbleRep { int32 irep[2]; double d; } DbleRep; - -/* Some of the following optimise if we know double's only need to be */ -/* 32-bit aligned. */ -static int32 *sim_i2d(int32 *sp) -{ DbleRep u; - u.d = (double)stk_(sp,0); - stk_(sp,0) = u.irep[STHI]; - push_(sp, u.irep[STLO]); - return sp; -} -static int32 *sim_d2i(int32 *sp) -{ DbleRep u; - u.irep[STLO] = pop_(sp); - u.irep[STHI] = stk_(sp,0); - stk_(sp,0) = (int32)u.d; - return sp; -} -static int32 *sim_l2d(int32 *sp) { jsyserr("l2d"); return sp;} -static int32 *sim_d2l(int32 *sp) { jsyserr("d2l"); return sp;} -static int32 *sim_f2l(int32 *sp) { jsyserr("f2l"); lose_(sp,1); return sp;} -static int32 *sim_l2f(int32 *sp) { jsyserr("l2f"); push_(sp,0); return sp;} -static int32 *sim_f2d(int32 *sp) -{ DbleRep u; - u.d = (double)stk_((float *)sp,0); - stk_(sp,0) = u.irep[STHI]; - push_(sp, u.irep[STLO]); - return sp; -} -static int32 *sim_d2f(int32 *sp) -{ DbleRep u; - u.irep[STLO] = pop_(sp); - u.irep[STHI] = stk_(sp,0); - stk_((float *)sp,0) = (float)u.d; - return sp; -} - -static Code_Attribute *findcodeattr(Attribute_Info *v, unsigned32 n) -{ int i; - for (i = 0; iconstant_pool; - { int i; - for (i = 0; i < cf->methods_count; i++) - { unsigned32 n = cf->methods[i].name_index; - if (0 < n && n < cf->constant_pool_count && - cp[n].tag == CONSTANT_Utf8 && - memcmp(cp[n].u.utf8, "main", 4) == 0) - { Code_Attribute *p = findcodeattr(cf->methods[i].attributes, - cf->methods[i].attributes_count); - if (p == 0) jsyserr("no code for main"); - pc = (int8 *)p->code; goto foundmain; - } - } - jsyserr("no main()"); - return; - } -foundmain: - jdebug("Execution..."); -#define u8i_(pc) (*(pc)++ & 255) -#define s8i_(pc) (*(pc)++) -#define s16i_(pc) (t1 = s8i_(pc), t1<<8 | u8i_(pc)) -#define u16i_(pc) (t1 = u8i_(pc), t1<<8 | u8i_(pc)) -#define s32i_(pc) (t1 = s8i_(pc), t1 = t1<<8 | u8i_(pc), \ - t1 = t1<<8 | u8i_(pc), t1<<8 | u8i_(pc)) -#define cp_maybe_string_(d) \ - (cp[d].tag == CONSTANT_String ? cp[cp[d].u.val].u.val : cp[d].u.val) - -#define cp1_(d) (cp[d].u.val) -#define cp2_(d) (cp[(d)+1].u.val) - for (pb = 0;;) switch (jdebug("trace %d", op = u8i_(pc)), op) - { -default: jsyserr("Illegal java op %d/%s", op, jdecodeopname(op)); - break; -unimp: jsyserr("Unimplemented java op %d/%s", op, jdecodeopname(op)); - break; -case j_bipush: push_(sp, s8i_(pc)); break; -case j_sipush: push_(sp, s16i_(pc)); break; -case j_ldc1: t2 = u8i_(pc); push_(sp, cp_maybe_string_(t2)); break; -case j_ldc2: t2 = u16i_(pc); push_(sp, cp_maybe_string_(t2)); break; -case j_ldc2w: t2 = u16i_(pc); push_(sp, cp1_(t2)); push_(sp, cp2_(t2)); break; -case j_aconst_null: push_(sp, HR_NULL); break; -case j_iconst_m1: push_(sp, -1); break; -case j_iconst_0: push_(sp, 0); break; -case j_iconst_1: push_(sp, 1); break; -case j_iconst_2: push_(sp, 2); break; -case j_iconst_3: push_(sp, 3); break; -case j_iconst_4: push_(sp, 4); break; -case j_iconst_5: push_(sp, 5); break; -case j_lconst_0: push_(sp, 0); push_(sp, 0); break; -case j_lconst_1: push_(sp, 0); push_(sp, 0); break; -case j_fconst_0: push_(sp, HR_F0); break; -case j_fconst_1: push_(sp, HR_F1); break; -case j_fconst_2: push_(sp, HR_F2); break; -case j_dconst_0: push_(sp, HR_D0W1); push_(sp, HR_D0W2); break; -case j_dconst_1: push_(sp, HR_D1W1); push_(sp, HR_D1W2); break; - -case3(j_iload,j_fload,j_aload): - push_(sp, loc_(lv,pb+u8i_(pc))); pb = 0; break; -case3(j_iload_0,j_fload_0,j_aload_0): push_(sp, loc_(lv,0)); break; -case3(j_iload_1,j_fload_1,j_aload_1): push_(sp, loc_(lv,1)); break; -case3(j_iload_2,j_fload_2,j_aload_2): push_(sp, loc_(lv,2)); break; -case3(j_iload_3,j_fload_3,j_aload_3): push_(sp, loc_(lv,3)); break; -/* Could use sv1,sv2 if lots of registers on my target. */ -case2(j_lload,j_dload): pb += u8i_(pc); /* STHI, STLO */ - sv = loc_(lv, pb+0); push_(sp, sv); - sv = loc_(lv, pb+1); push_(sp, sv); pb = 0; break; -case2(j_lload_0,j_dload_0): push_(sp, loc_(lv,0)); push_(sp, loc_(lv,1)); break; -case2(j_lload_1,j_dload_1): push_(sp, loc_(lv,1)); push_(sp, loc_(lv,2)); break; -case2(j_lload_2,j_dload_2): push_(sp, loc_(lv,2)); push_(sp, loc_(lv,3)); break; -case2(j_lload_3,j_dload_3): push_(sp, loc_(lv,3)); push_(sp, loc_(lv,4)); break; - -case3(j_istore,j_fstore,j_astore): - loc_(lv, pb+u8i_(pc)) = pop_(sp); pb = 0; break; -case3(j_istore_0,j_fstore_0,j_astore_0): loc_(lv,0) = pop_(sp); break; -case3(j_istore_1,j_fstore_1,j_astore_1): loc_(lv,1) = pop_(sp); break; -case3(j_istore_2,j_fstore_2,j_astore_2): loc_(lv,2) = pop_(sp); break; -case3(j_istore_3,j_fstore_3,j_astore_3): loc_(lv,3) = pop_(sp); break; -/* Could use sv1,sv2 if lots of registers on my target. */ -case2(j_lstore,j_dstore): pb += u8i_(pc); /* STHI, STLO */ - sv = pop_(sp); loc_(lv, pb+1) = sv; - sv = pop_(sp); loc_(lv, pb+0) = sv; pb = 0; break; -case2(j_lstore_0,j_dstore_0): loc_(lv,1)=pop_(sp); loc_(lv,0)=pop_(sp); break; -case2(j_lstore_1,j_dstore_1): loc_(lv,2)=pop_(sp); loc_(lv,1)=pop_(sp); break; -case2(j_lstore_2,j_dstore_2): loc_(lv,3)=pop_(sp); loc_(lv,2)=pop_(sp); break; -case2(j_lstore_3,j_dstore_3): loc_(lv,4)=pop_(sp); loc_(lv,3)=pop_(sp); break; - -case j_iinc: pb += u8i_(pc); loc_(lv, pb) += s8i_(pc); pb = 0; break; - -case j_wide: pb = u8i_(pc) << 8; break; - -case j_newarray: if ((t1 = java_newarray(sp, u8i_(pc), 0, 0)) != 0) - { jraise(t1); - } - break; -case j_anewarray: t2 = u16i_(pc); - if ((t1 = java_newarray(sp, -1, cp1_(t2), 0)) != 0) - { jraise(t1); - } - break; -case j_multinewarray: t2 = u16i_(pc); t3 = u8i_(pc)-1; - t1 = java_newarray(sp, -1, cp1_(t2), t3); - sp += t3; - if (t1 != 0) - { jraise(t1); - } - break; - -case j_arraylength: - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - stk_(sp,0) = sv_qua_array->length; - break; - -case3(j_iaload,j_faload,j_aaload): - ao = pop_(sp); - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)ao >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - stk_(sp,0) = sv_qua_array->u.elt32[ao]; - break; -case2(j_laload,j_daload): - ao = pop_(sp); - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)ao >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - stk_(sp,0) = sv_qua_array->u.elt32[2*ao+STHI]; - push_(sp, sv_qua_array->u.elt32[2*ao+STLO]); - break; -case j_baload: ao = pop_(sp); - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)ao >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - stk_(sp,0) = sv_qua_array->u.elts8[ao]; - break; -case j_caload: ao = pop_(sp); - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)ao >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - stk_(sp,0) = sv_qua_array->u.eltu16[ao]; - break; -case j_saload: ao = pop_(sp); - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)ao >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - stk_(sp,0) = sv_qua_array->u.elts16[ao]; - break; - -case3(j_iastore,j_fastore,j_aastore): - if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - sv_qua_array->u.elt32[ao] = stk_(sp,0); - lose_(sp,3); - break; -case2(j_lastore,j_dastore): - if ((sv_qua_array = (JavaArray *)stk_(sp,3)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)(ao = stk_(sp,2)) >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - sv_qua_array->u.elt32[2*ao+STLO] = stk_(sp,0); - sv_qua_array->u.elt32[2*ao+STHI] = stk_(sp,1); - lose_(sp,4); - break; -case j_bastore: - if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - sv_qua_array->u.eltu8[ao] = stk_(sp,0); - lose_(sp,3); - break; -case2(j_sastore,j_castore): - if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } - if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) - { jraise(E_ArrayIndexOutOfBoundsException); - } - sv_qua_array->u.eltu16[ao] = stk_(sp,0); - lose_(sp,3); - break; - -case j_nop: break; -case j_pop: lose_(sp,1); break; -case j_pop2: lose_(sp,2); break; -case j_dup: sv = stk_(sp, 0); push_(sp, sv); break; -case j_dup2: sv = stk_(sp, 1); push_(sp, sv); - sv = stk_(sp, 1); push_(sp, sv); break; -case j_dup_x1: sv = stk_(sp, 0); stk_(sp, 0) = stk_(sp, 1); - stk_(sp, 1) = sv; push_(sp, sv); break; -case j_dup2_x1: r1 = stk_(sp, 0); r2 = stk_(sp, 1); stk_(sp,0) = stk_(sp,2); - stk_(sp,1) = r1; stk_(sp,2) = r2; push_(sp, r2); push_(sp,r1); - break; -case j_dup_x2: sv = stk_(sp, 0); push_(sp, sv); stk_(sp,1) = stk_(sp,2); - stk_(sp,2) = stk_(sp,3); stk_(sp,3) = sv; break; -case j_dup2_x2: sv = stk_(sp, 1); push_(sp, sv); stk_(sp,2) = stk_(sp,4); - stk_(sp,4) = sv; - sv = stk_(sp, 1); push_(sp, sv); stk_(sp,2) = stk_(sp,4); - stk_(sp,4) = sv; break; -case j_swap: sv = stk_(sp, 0); stk_(sp, 0) = stk_(sp, 1); - stk_(sp, 1) = sv; break; - -case j_iadd: r1 = pop_(sp); stk_(sp,0) += r1; break; -case j_ladd: goto unimp; -case j_fadd: goto unimp; -case j_dadd: goto unimp; -case j_isub: r1 = pop_(sp); stk_(sp,0) -= r1; break; -case j_lsub: goto unimp; -case j_fsub: goto unimp; -case j_dsub: goto unimp; -case j_imul: r1 = pop_(sp); stk_(sp,0) *= r1; break; -case j_lmul: goto unimp; -case j_fmul: goto unimp; -case j_dmul: goto unimp; -case j_idiv: r1 = pop_(sp); stk_(sp,0) /= r1; break; -case j_ldiv: goto unimp; -case j_fdiv: goto unimp; -case j_ddiv: goto unimp; -case j_irem: r1 = pop_(sp); stk_(sp,0) %= r1; break; -case j_lrem: goto unimp; -case j_frem: goto unimp; -case j_drem: goto unimp; -case j_ineg: stk_(sp,0) = -stk_(sp,0); break; -case j_lneg: goto unimp; -case j_fneg: goto unimp; -case j_dneg: goto unimp; - -case j_ishl: r1 = pop_(sp); stk_(sp,0) <<= r1&31; break; -#ifdef HOST_SHIFT_SIGNED -case j_ishr: r1 = pop_(sp); stk_(sp,0) >>= r1&31; break; -#else -case j_ishr: goto unimp; -#endif -case j_iushr: r1 = pop_(sp); stk_(sp,0) = (unsigned32)stk_(sp,0) >> r1&31; break; -case j_lshl: goto unimp; -case j_lshr: goto unimp; -case j_lushr: goto unimp; -case j_iand: r1 = pop_(sp); stk_(sp,0) &= r1; break; -case j_land: stk_(sp,2) &= stk_(sp,0); stk_(sp,3) &= stk_(sp,1); - lose_(sp,2); break; -case j_ior: r1 = pop_(sp); stk_(sp,0) |= r1; break; -case j_lor: stk_(sp,2) |= stk_(sp,0); stk_(sp,3) |= stk_(sp,1); - lose_(sp,2); break; -case j_ixor: r1 = pop_(sp); stk_(sp,0) ^= r1; break; -case j_lxor: stk_(sp,2) ^= stk_(sp,0); stk_(sp,3) ^= stk_(sp,1); - lose_(sp,2); break; - -case j_i2l: r1u = stk_(sp,0); push_(sp, -(r1u >> 31)); break; -case j_i2f: stk_((float *)sp,0) = (float)stk_(sp,0); break; -case j_i2d: sp = sim_i2d(sp); break; -case j_l2i: lose_(sp,1); break; -case j_l2f: sp = sim_l2f(sp); break; -case j_l2d: sp = sim_l2d(sp); break; -case j_f2i: stk_(sp,0) = (int32)stk_((float *)sp,0); break; -case j_f2l: sp = sim_f2l(sp); break; -case j_f2d: sp = sim_f2d(sp); break; -case j_d2i: sp = sim_d2i(sp); break; -case j_d2l: sp = sim_d2l(sp); break; -case j_d2f: sp = sim_d2f(sp); break; - -#define signext_(w,n) ((((w) & (1< 0); break; -case j_ifge: condbr(pop_(sp) >= 0); break; -case j_if_icmpeq: sv = pop_(sp); condbr(pop_(sp) == sv); break; -case j_if_icmpne: sv = pop_(sp); condbr(pop_(sp) != sv); break; -case j_if_icmplt: sv = pop_(sp); condbr(pop_(sp) < sv); break; -case j_if_icmpgt: sv = pop_(sp); condbr(pop_(sp) > sv); break; -case j_if_icmple: sv = pop_(sp); condbr(pop_(sp) <= sv); break; -case j_if_icmpge: sv = pop_(sp); condbr(pop_(sp) >= sv); break; -case j_lcmp: -case j_fcmpl: -case j_fcmpg: -case j_dcmpl: -case j_dcmpg: -case j_if_acmpeq: -case j_if_acmpne: -case j_goto: t2 = s16i_(pc); pc += t2-3; break; -case j_goto_w: t2 = s32i_(pc); pc += t2-5; break; -case j_jsr: t2 = s16i_(pc); push_(sp,(int32)pc); pc += t2-3; break; /*ALPHA*/ -case j_jsr_w: t2 = s32i_(pc); push_(sp,(int32)pc); pc += t2-5; break; /*ALPHA*/ -case j_ret: t2 = u8i_(pc); pc = (int8 *)stk_(sp, t2); break; /*ALPHA*/ -case j_ret_w: t2 = u16i_(pc); pc = (int8 *)stk_(sp, t2); break; /*ALPHA*/ - -case j_ireturn: -case j_lreturn: -case j_freturn: -case j_dreturn: -case j_areturn: -case j_return: -case j_breakpoint: - -case j_tableswitch: -case j_lookupswitch: - -case j_putfield: goto unimp; -case j_getfield: - if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ - { jraise(E_NullPointerException); - } -case j_putstatic: goto unimp; -case j_getstatic: t2 = u16i_(pc); - push_(sp, (int32)&java_PrintStream); /* @@@ */ - break; /* @@@ */ - -case j_invokevirtual: t2 = u16i_(pc); - cf = (ClassFile *)*spbase; - if (cf != &java_PrintStream) - jsyserr("invokevirtual"); - if (cf->methods_count == 1 && /* @@@ */ - cf->methods[0].access_flags & ACC_NATIVE) - { sp = ((JavaBuiltin)(cf->methods[0].attributes))(spbase); - } - else - { lv = spbase; - spbase = sp+1; - goto unimp; - } - break; - -case j_invokenonvirtual: goto unimp; -case j_invokestatic: goto unimp; -case j_invokeinterface: goto unimp; - -case j_athrow: goto unimp; - -case j_new: t2 = u16i_(pc); - term_printf("NEW %d %d %.8x\n", - t2, cp[t2].tag, cp_maybe_string_(t2)); - goto unimp; -case j_checkcast: goto unimp; -case j_instanceof: goto unimp; -case j_monitorenter: goto unimp; -case j_monitorexit: goto unimp; - - } -} +/* javaint.c: Copyright (C) Codemist Ltd., 1996. */ + +#include +/* #include */ +#include +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "stream.h" +#include "arith.h" +#include "entries.h" +#include "javahost.h" +#include "javaops.h" +#include "javaglb.h" + +/* integers representing exceptions (map to Java exceptions in javaint(). */ +#define E_NegativeArraySizeException 1 +#define E_OutOfMemoryError 2 +#define E_NullPointerException 3 +#define E_ArrayIndexOutOfBoundsException 4 + +#define JSTK_MAX 10000 +#ifdef DOWNWARD_STACK /* need to fix up locals too! */ +#define push_(sp,v) (*--(sp)=(v)) +#define pop_(sp) (*(sp)++) +#define lose_(sp,k) ((sp)+=(k)) +#define stk_(sp,k) ((sp)[k]) +#define STLO 0 +#define STHI 1 +#define loc_(lv,k) (*((lv)-(k))) +#else +#define push_(sp,v) (*++(sp)=(v)) +#define pop_(sp) (*(sp)--) +#define lose_(sp,k) ((sp)-=(k)) +#define stk_(sp,k) (*((sp)-(k))) +#define STLO 1 +#define STHI 0 +#define loc_(lv,k) ((lv)[k]) +#endif + +static void jraise(int E_whatever) +{ jsyserr("Exceptions unimplemented"); +} + +static int java_sizeof(int32 t) +{ switch (t) + { default: jsyserr("bad type code to newarray()"); + case T_BOOLEAN: return 1; + case T_CHAR: return 1; + case T_FLOAT: return 4; + case T_DOUBLE: return 8; + case T_BYTE: return 1; + case T_SHORT: return 2; + case T_INT: return 4; + case T_LONG: return 8; + case -1: return 4; /* for anewarray */ + } +} + +typedef struct JavaArray +{ unsigned32 length; + /* access long/double by stream as maybe not aligned */ + union { int8 elts8[1]; unsigned8 eltu8[1]; + int16 elts16[1]; unsigned16 eltu16[1]; int32 elt32[1]; } u; +} JavaArray; + +static int32 java_newarray(int32 *sp, int32 flavour, int32 refclass, int32 k) +{ /* Note that 'k' is (number of dimensions)-1. */ + /* Caller loses junk when k>0 (j_multinewarray). */ + /* k>0 not supported yet. */ + JavaArray *res; + int32 nelts = stk_(sp,0), csize; + if (nelts < 0) return E_NegativeArraySizeException; + csize = java_sizeof(flavour)*nelts + sizeof(int32); + res = (JavaArray *)jmalloc(csize); + if (res == 0) return E_OutOfMemoryError; + memset(res, 0, csize); /* @@@ beware 0 = HR_NULL assumed! */ + res->length = nelts; + stk_(sp,k) = (int32)res; /*ALPHA*/ + return 0; +} + +/* beware host/java rep issues here */ +#define HR_NULL 0 /* Host Representation? */ +static const union { struct { double d[2]; float f[3]; } s; + int32 r[7]; + } hostflttab = { 0.0, 1.0, 0.0f, 1.0f, 2.0f }; +/* Remember many of the following are zero (optimise?) */ +#define HR_D0W1 hostflttab.r[0] +#define HR_D0W2 hostflttab.r[1] +#define HR_D1W1 hostflttab.r[2] +#define HR_D1W2 hostflttab.r[3] +#define HR_F0 hostflttab.r[4] +#define HR_F1 hostflttab.r[5] +#define HR_F2 hostflttab.r[6] + +typedef union DbleRep { int32 irep[2]; double d; } DbleRep; + +/* Some of the following optimise if we know double's only need to be */ +/* 32-bit aligned. */ +static int32 *sim_i2d(int32 *sp) +{ DbleRep u; + u.d = (double)stk_(sp,0); + stk_(sp,0) = u.irep[STHI]; + push_(sp, u.irep[STLO]); + return sp; +} +static int32 *sim_d2i(int32 *sp) +{ DbleRep u; + u.irep[STLO] = pop_(sp); + u.irep[STHI] = stk_(sp,0); + stk_(sp,0) = (int32)u.d; + return sp; +} +static int32 *sim_l2d(int32 *sp) { jsyserr("l2d"); return sp;} +static int32 *sim_d2l(int32 *sp) { jsyserr("d2l"); return sp;} +static int32 *sim_f2l(int32 *sp) { jsyserr("f2l"); lose_(sp,1); return sp;} +static int32 *sim_l2f(int32 *sp) { jsyserr("l2f"); push_(sp,0); return sp;} +static int32 *sim_f2d(int32 *sp) +{ DbleRep u; + u.d = (double)stk_((float *)sp,0); + stk_(sp,0) = u.irep[STHI]; + push_(sp, u.irep[STLO]); + return sp; +} +static int32 *sim_d2f(int32 *sp) +{ DbleRep u; + u.irep[STLO] = pop_(sp); + u.irep[STHI] = stk_(sp,0); + stk_((float *)sp,0) = (float)u.d; + return sp; +} + +static Code_Attribute *findcodeattr(Attribute_Info *v, unsigned32 n) +{ int i; + for (i = 0; iconstant_pool; + { int i; + for (i = 0; i < cf->methods_count; i++) + { unsigned32 n = cf->methods[i].name_index; + if (0 < n && n < cf->constant_pool_count && + cp[n].tag == CONSTANT_Utf8 && + memcmp(cp[n].u.utf8, "main", 4) == 0) + { Code_Attribute *p = findcodeattr(cf->methods[i].attributes, + cf->methods[i].attributes_count); + if (p == 0) jsyserr("no code for main"); + pc = (int8 *)p->code; goto foundmain; + } + } + jsyserr("no main()"); + return; + } +foundmain: + jdebug("Execution..."); +#define u8i_(pc) (*(pc)++ & 255) +#define s8i_(pc) (*(pc)++) +#define s16i_(pc) (t1 = s8i_(pc), t1<<8 | u8i_(pc)) +#define u16i_(pc) (t1 = u8i_(pc), t1<<8 | u8i_(pc)) +#define s32i_(pc) (t1 = s8i_(pc), t1 = t1<<8 | u8i_(pc), \ + t1 = t1<<8 | u8i_(pc), t1<<8 | u8i_(pc)) +#define cp_maybe_string_(d) \ + (cp[d].tag == CONSTANT_String ? cp[cp[d].u.val].u.val : cp[d].u.val) + +#define cp1_(d) (cp[d].u.val) +#define cp2_(d) (cp[(d)+1].u.val) + for (pb = 0;;) switch (jdebug("trace %d", op = u8i_(pc)), op) + { +default: jsyserr("Illegal java op %d/%s", op, jdecodeopname(op)); + break; +unimp: jsyserr("Unimplemented java op %d/%s", op, jdecodeopname(op)); + break; +case j_bipush: push_(sp, s8i_(pc)); break; +case j_sipush: push_(sp, s16i_(pc)); break; +case j_ldc1: t2 = u8i_(pc); push_(sp, cp_maybe_string_(t2)); break; +case j_ldc2: t2 = u16i_(pc); push_(sp, cp_maybe_string_(t2)); break; +case j_ldc2w: t2 = u16i_(pc); push_(sp, cp1_(t2)); push_(sp, cp2_(t2)); break; +case j_aconst_null: push_(sp, HR_NULL); break; +case j_iconst_m1: push_(sp, -1); break; +case j_iconst_0: push_(sp, 0); break; +case j_iconst_1: push_(sp, 1); break; +case j_iconst_2: push_(sp, 2); break; +case j_iconst_3: push_(sp, 3); break; +case j_iconst_4: push_(sp, 4); break; +case j_iconst_5: push_(sp, 5); break; +case j_lconst_0: push_(sp, 0); push_(sp, 0); break; +case j_lconst_1: push_(sp, 0); push_(sp, 0); break; +case j_fconst_0: push_(sp, HR_F0); break; +case j_fconst_1: push_(sp, HR_F1); break; +case j_fconst_2: push_(sp, HR_F2); break; +case j_dconst_0: push_(sp, HR_D0W1); push_(sp, HR_D0W2); break; +case j_dconst_1: push_(sp, HR_D1W1); push_(sp, HR_D1W2); break; + +case3(j_iload,j_fload,j_aload): + push_(sp, loc_(lv,pb+u8i_(pc))); pb = 0; break; +case3(j_iload_0,j_fload_0,j_aload_0): push_(sp, loc_(lv,0)); break; +case3(j_iload_1,j_fload_1,j_aload_1): push_(sp, loc_(lv,1)); break; +case3(j_iload_2,j_fload_2,j_aload_2): push_(sp, loc_(lv,2)); break; +case3(j_iload_3,j_fload_3,j_aload_3): push_(sp, loc_(lv,3)); break; +/* Could use sv1,sv2 if lots of registers on my target. */ +case2(j_lload,j_dload): pb += u8i_(pc); /* STHI, STLO */ + sv = loc_(lv, pb+0); push_(sp, sv); + sv = loc_(lv, pb+1); push_(sp, sv); pb = 0; break; +case2(j_lload_0,j_dload_0): push_(sp, loc_(lv,0)); push_(sp, loc_(lv,1)); break; +case2(j_lload_1,j_dload_1): push_(sp, loc_(lv,1)); push_(sp, loc_(lv,2)); break; +case2(j_lload_2,j_dload_2): push_(sp, loc_(lv,2)); push_(sp, loc_(lv,3)); break; +case2(j_lload_3,j_dload_3): push_(sp, loc_(lv,3)); push_(sp, loc_(lv,4)); break; + +case3(j_istore,j_fstore,j_astore): + loc_(lv, pb+u8i_(pc)) = pop_(sp); pb = 0; break; +case3(j_istore_0,j_fstore_0,j_astore_0): loc_(lv,0) = pop_(sp); break; +case3(j_istore_1,j_fstore_1,j_astore_1): loc_(lv,1) = pop_(sp); break; +case3(j_istore_2,j_fstore_2,j_astore_2): loc_(lv,2) = pop_(sp); break; +case3(j_istore_3,j_fstore_3,j_astore_3): loc_(lv,3) = pop_(sp); break; +/* Could use sv1,sv2 if lots of registers on my target. */ +case2(j_lstore,j_dstore): pb += u8i_(pc); /* STHI, STLO */ + sv = pop_(sp); loc_(lv, pb+1) = sv; + sv = pop_(sp); loc_(lv, pb+0) = sv; pb = 0; break; +case2(j_lstore_0,j_dstore_0): loc_(lv,1)=pop_(sp); loc_(lv,0)=pop_(sp); break; +case2(j_lstore_1,j_dstore_1): loc_(lv,2)=pop_(sp); loc_(lv,1)=pop_(sp); break; +case2(j_lstore_2,j_dstore_2): loc_(lv,3)=pop_(sp); loc_(lv,2)=pop_(sp); break; +case2(j_lstore_3,j_dstore_3): loc_(lv,4)=pop_(sp); loc_(lv,3)=pop_(sp); break; + +case j_iinc: pb += u8i_(pc); loc_(lv, pb) += s8i_(pc); pb = 0; break; + +case j_wide: pb = u8i_(pc) << 8; break; + +case j_newarray: if ((t1 = java_newarray(sp, u8i_(pc), 0, 0)) != 0) + { jraise(t1); + } + break; +case j_anewarray: t2 = u16i_(pc); + if ((t1 = java_newarray(sp, -1, cp1_(t2), 0)) != 0) + { jraise(t1); + } + break; +case j_multinewarray: t2 = u16i_(pc); t3 = u8i_(pc)-1; + t1 = java_newarray(sp, -1, cp1_(t2), t3); + sp += t3; + if (t1 != 0) + { jraise(t1); + } + break; + +case j_arraylength: + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + stk_(sp,0) = sv_qua_array->length; + break; + +case3(j_iaload,j_faload,j_aaload): + ao = pop_(sp); + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)ao >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + stk_(sp,0) = sv_qua_array->u.elt32[ao]; + break; +case2(j_laload,j_daload): + ao = pop_(sp); + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)ao >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + stk_(sp,0) = sv_qua_array->u.elt32[2*ao+STHI]; + push_(sp, sv_qua_array->u.elt32[2*ao+STLO]); + break; +case j_baload: ao = pop_(sp); + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)ao >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + stk_(sp,0) = sv_qua_array->u.elts8[ao]; + break; +case j_caload: ao = pop_(sp); + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)ao >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + stk_(sp,0) = sv_qua_array->u.eltu16[ao]; + break; +case j_saload: ao = pop_(sp); + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)ao >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + stk_(sp,0) = sv_qua_array->u.elts16[ao]; + break; + +case3(j_iastore,j_fastore,j_aastore): + if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + sv_qua_array->u.elt32[ao] = stk_(sp,0); + lose_(sp,3); + break; +case2(j_lastore,j_dastore): + if ((sv_qua_array = (JavaArray *)stk_(sp,3)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)(ao = stk_(sp,2)) >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + sv_qua_array->u.elt32[2*ao+STLO] = stk_(sp,0); + sv_qua_array->u.elt32[2*ao+STHI] = stk_(sp,1); + lose_(sp,4); + break; +case j_bastore: + if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + sv_qua_array->u.eltu8[ao] = stk_(sp,0); + lose_(sp,3); + break; +case2(j_sastore,j_castore): + if ((sv_qua_array = (JavaArray *)stk_(sp,2)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } + if ((unsigned32)(ao = stk_(sp,1)) >= sv_qua_array->length) + { jraise(E_ArrayIndexOutOfBoundsException); + } + sv_qua_array->u.eltu16[ao] = stk_(sp,0); + lose_(sp,3); + break; + +case j_nop: break; +case j_pop: lose_(sp,1); break; +case j_pop2: lose_(sp,2); break; +case j_dup: sv = stk_(sp, 0); push_(sp, sv); break; +case j_dup2: sv = stk_(sp, 1); push_(sp, sv); + sv = stk_(sp, 1); push_(sp, sv); break; +case j_dup_x1: sv = stk_(sp, 0); stk_(sp, 0) = stk_(sp, 1); + stk_(sp, 1) = sv; push_(sp, sv); break; +case j_dup2_x1: r1 = stk_(sp, 0); r2 = stk_(sp, 1); stk_(sp,0) = stk_(sp,2); + stk_(sp,1) = r1; stk_(sp,2) = r2; push_(sp, r2); push_(sp,r1); + break; +case j_dup_x2: sv = stk_(sp, 0); push_(sp, sv); stk_(sp,1) = stk_(sp,2); + stk_(sp,2) = stk_(sp,3); stk_(sp,3) = sv; break; +case j_dup2_x2: sv = stk_(sp, 1); push_(sp, sv); stk_(sp,2) = stk_(sp,4); + stk_(sp,4) = sv; + sv = stk_(sp, 1); push_(sp, sv); stk_(sp,2) = stk_(sp,4); + stk_(sp,4) = sv; break; +case j_swap: sv = stk_(sp, 0); stk_(sp, 0) = stk_(sp, 1); + stk_(sp, 1) = sv; break; + +case j_iadd: r1 = pop_(sp); stk_(sp,0) += r1; break; +case j_ladd: goto unimp; +case j_fadd: goto unimp; +case j_dadd: goto unimp; +case j_isub: r1 = pop_(sp); stk_(sp,0) -= r1; break; +case j_lsub: goto unimp; +case j_fsub: goto unimp; +case j_dsub: goto unimp; +case j_imul: r1 = pop_(sp); stk_(sp,0) *= r1; break; +case j_lmul: goto unimp; +case j_fmul: goto unimp; +case j_dmul: goto unimp; +case j_idiv: r1 = pop_(sp); stk_(sp,0) /= r1; break; +case j_ldiv: goto unimp; +case j_fdiv: goto unimp; +case j_ddiv: goto unimp; +case j_irem: r1 = pop_(sp); stk_(sp,0) %= r1; break; +case j_lrem: goto unimp; +case j_frem: goto unimp; +case j_drem: goto unimp; +case j_ineg: stk_(sp,0) = -stk_(sp,0); break; +case j_lneg: goto unimp; +case j_fneg: goto unimp; +case j_dneg: goto unimp; + +case j_ishl: r1 = pop_(sp); stk_(sp,0) <<= r1&31; break; +#ifdef HOST_SHIFT_SIGNED +case j_ishr: r1 = pop_(sp); stk_(sp,0) >>= r1&31; break; +#else +case j_ishr: goto unimp; +#endif +case j_iushr: r1 = pop_(sp); stk_(sp,0) = (unsigned32)stk_(sp,0) >> r1&31; break; +case j_lshl: goto unimp; +case j_lshr: goto unimp; +case j_lushr: goto unimp; +case j_iand: r1 = pop_(sp); stk_(sp,0) &= r1; break; +case j_land: stk_(sp,2) &= stk_(sp,0); stk_(sp,3) &= stk_(sp,1); + lose_(sp,2); break; +case j_ior: r1 = pop_(sp); stk_(sp,0) |= r1; break; +case j_lor: stk_(sp,2) |= stk_(sp,0); stk_(sp,3) |= stk_(sp,1); + lose_(sp,2); break; +case j_ixor: r1 = pop_(sp); stk_(sp,0) ^= r1; break; +case j_lxor: stk_(sp,2) ^= stk_(sp,0); stk_(sp,3) ^= stk_(sp,1); + lose_(sp,2); break; + +case j_i2l: r1u = stk_(sp,0); push_(sp, -(r1u >> 31)); break; +case j_i2f: stk_((float *)sp,0) = (float)stk_(sp,0); break; +case j_i2d: sp = sim_i2d(sp); break; +case j_l2i: lose_(sp,1); break; +case j_l2f: sp = sim_l2f(sp); break; +case j_l2d: sp = sim_l2d(sp); break; +case j_f2i: stk_(sp,0) = (int32)stk_((float *)sp,0); break; +case j_f2l: sp = sim_f2l(sp); break; +case j_f2d: sp = sim_f2d(sp); break; +case j_d2i: sp = sim_d2i(sp); break; +case j_d2l: sp = sim_d2l(sp); break; +case j_d2f: sp = sim_d2f(sp); break; + +#define signext_(w,n) ((((w) & (1< 0); break; +case j_ifge: condbr(pop_(sp) >= 0); break; +case j_if_icmpeq: sv = pop_(sp); condbr(pop_(sp) == sv); break; +case j_if_icmpne: sv = pop_(sp); condbr(pop_(sp) != sv); break; +case j_if_icmplt: sv = pop_(sp); condbr(pop_(sp) < sv); break; +case j_if_icmpgt: sv = pop_(sp); condbr(pop_(sp) > sv); break; +case j_if_icmple: sv = pop_(sp); condbr(pop_(sp) <= sv); break; +case j_if_icmpge: sv = pop_(sp); condbr(pop_(sp) >= sv); break; +case j_lcmp: +case j_fcmpl: +case j_fcmpg: +case j_dcmpl: +case j_dcmpg: +case j_if_acmpeq: +case j_if_acmpne: +case j_goto: t2 = s16i_(pc); pc += t2-3; break; +case j_goto_w: t2 = s32i_(pc); pc += t2-5; break; +case j_jsr: t2 = s16i_(pc); push_(sp,(int32)pc); pc += t2-3; break; /*ALPHA*/ +case j_jsr_w: t2 = s32i_(pc); push_(sp,(int32)pc); pc += t2-5; break; /*ALPHA*/ +case j_ret: t2 = u8i_(pc); pc = (int8 *)stk_(sp, t2); break; /*ALPHA*/ +case j_ret_w: t2 = u16i_(pc); pc = (int8 *)stk_(sp, t2); break; /*ALPHA*/ + +case j_ireturn: +case j_lreturn: +case j_freturn: +case j_dreturn: +case j_areturn: +case j_return: +case j_breakpoint: + +case j_tableswitch: +case j_lookupswitch: + +case j_putfield: goto unimp; +case j_getfield: + if ((sv_qua_array = (JavaArray *)stk_(sp,0)) == HR_NULL) /*ALPHA*/ + { jraise(E_NullPointerException); + } +case j_putstatic: goto unimp; +case j_getstatic: t2 = u16i_(pc); + push_(sp, (int32)&java_PrintStream); /* @@@ */ + break; /* @@@ */ + +case j_invokevirtual: t2 = u16i_(pc); + cf = (ClassFile *)*spbase; + if (cf != &java_PrintStream) + jsyserr("invokevirtual"); + if (cf->methods_count == 1 && /* @@@ */ + cf->methods[0].access_flags & ACC_NATIVE) + { sp = ((JavaBuiltin)(cf->methods[0].attributes))(spbase); + } + else + { lv = spbase; + spbase = sp+1; + goto unimp; + } + break; + +case j_invokenonvirtual: goto unimp; +case j_invokestatic: goto unimp; +case j_invokeinterface: goto unimp; + +case j_athrow: goto unimp; + +case j_new: t2 = u16i_(pc); + term_printf("NEW %d %d %.8x\n", + t2, cp[t2].tag, cp_maybe_string_(t2)); + goto unimp; +case j_checkcast: goto unimp; +case j_instanceof: goto unimp; +case j_monitorenter: goto unimp; +case j_monitorexit: goto unimp; + + } +}  Index: r36/java/JAVAMAIN.C ================================================================== --- r36/java/JAVAMAIN.C +++ r36/java/JAVAMAIN.C @@ -1,127 +1,127 @@ -/* javamain.c: Copyright (C) Codemist Ltd., 1996. */ - -#include -#include -#include -#include -#include -#include "machine.h" -#include "tags.h" -#undef IGNORE -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "stream.h" -#include "arith.h" -#include "entries.h" -#include "javahost.h" -#include "javaglb.h" -/* #include "javatype.h" */ - -#include - -int debugging; - -void jdebug(char *fmt, ...) -{ va_list ap; - char buffer[256]; - va_start(ap, fmt); - vsprintf(buffer, fmt, ap); - va_end(ap); - err_printf("CJ-debug: %s\n", buffer); -} - -jmp_buf java_exit; - -void jsyserr(char *fmt, ...) -{ va_list ap; - char buffer[256]; - va_start(ap, fmt); - vsprintf(buffer, fmt, ap); - va_end(ap); - err_printf("\nFatal Codemist-Java error: %s\n", buffer); - longjmp(java_exit, 1); -} - -void *jmalloc(unsigned32 n) -{ void *p; - if (n == 0) return 0; - p = malloc(n); - if (p == 0) jsyserr("out of memory"); - return p; -} - -static void dbg_set(char *p) -{ for (;;) switch (*p++) - { -case 0: return; -case 'c': if (isdigit(*p)) debugging |= 1 << (*p-'0'); - break; - } -} - -int JAVAmain(int argc, char *argv[]) -{ ClassFile *p = 0; - int seen = 0; - int i; - debugging = 0; - for (i = 1; i] file.java\n", argv[0]); - else if (p) javaint(p); - } - return 0; -} - -void process_java_file(FILE *f) -{ - ClassFile *p; - p = rdClassFILE1(f, ""); - if (p && !setjmp(java_exit)) javaint(p); - err_printf("exiting from Java sub-system\n"); -} - -Lisp_Object MS_CDECL java0(Lisp_Object env, int nargs, ...) -{ - Lisp_Object nil = C_nil; - return onevalue(nil); -} - -Lisp_Object MS_CDECL java1(Lisp_Object env, Lisp_Object a) -{ - Lisp_Object nil = C_nil; - return onevalue(nil); -} - -Lisp_Object MS_CDECL java2(Lisp_Object env, Lisp_Object a, Lisp_Object b) -{ - Lisp_Object nil = C_nil; - return onevalue(nil); -} - -Lisp_Object MS_CDECL java3(Lisp_Object env, int nargs, ...) -{ - Lisp_Object nil = C_nil; - return onevalue(nil); -} - -Lisp_Object MS_CDECL javan(Lisp_Object env, int nargs, ...) -{ - Lisp_Object nil = C_nil; - return onevalue(nil); -} - - - -/* end of javamain.c */ +/* javamain.c: Copyright (C) Codemist Ltd., 1996. */ + +#include +#include +#include +#include +#include +#include "machine.h" +#include "tags.h" +#undef IGNORE +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "stream.h" +#include "arith.h" +#include "entries.h" +#include "javahost.h" +#include "javaglb.h" +/* #include "javatype.h" */ + +#include + +int debugging; + +void jdebug(char *fmt, ...) +{ va_list ap; + char buffer[256]; + va_start(ap, fmt); + vsprintf(buffer, fmt, ap); + va_end(ap); + err_printf("CJ-debug: %s\n", buffer); +} + +jmp_buf java_exit; + +void jsyserr(char *fmt, ...) +{ va_list ap; + char buffer[256]; + va_start(ap, fmt); + vsprintf(buffer, fmt, ap); + va_end(ap); + err_printf("\nFatal Codemist-Java error: %s\n", buffer); + longjmp(java_exit, 1); +} + +void *jmalloc(unsigned32 n) +{ void *p; + if (n == 0) return 0; + p = malloc(n); + if (p == 0) jsyserr("out of memory"); + return p; +} + +static void dbg_set(char *p) +{ for (;;) switch (*p++) + { +case 0: return; +case 'c': if (isdigit(*p)) debugging |= 1 << (*p-'0'); + break; + } +} + +int JAVAmain(int argc, char *argv[]) +{ ClassFile *p = 0; + int seen = 0; + int i; + debugging = 0; + for (i = 1; i] file.java\n", argv[0]); + else if (p) javaint(p); + } + return 0; +} + +void process_java_file(FILE *f) +{ + ClassFile *p; + p = rdClassFILE1(f, ""); + if (p && !setjmp(java_exit)) javaint(p); + err_printf("exiting from Java sub-system\n"); +} + +Lisp_Object MS_CDECL java0(Lisp_Object env, int nargs, ...) +{ + Lisp_Object nil = C_nil; + return onevalue(nil); +} + +Lisp_Object MS_CDECL java1(Lisp_Object env, Lisp_Object a) +{ + Lisp_Object nil = C_nil; + return onevalue(nil); +} + +Lisp_Object MS_CDECL java2(Lisp_Object env, Lisp_Object a, Lisp_Object b) +{ + Lisp_Object nil = C_nil; + return onevalue(nil); +} + +Lisp_Object MS_CDECL java3(Lisp_Object env, int nargs, ...) +{ + Lisp_Object nil = C_nil; + return onevalue(nil); +} + +Lisp_Object MS_CDECL javan(Lisp_Object env, int nargs, ...) +{ + Lisp_Object nil = C_nil; + return onevalue(nil); +} + + + +/* end of javamain.c */  Index: r36/java/JAVAOPS.H ================================================================== --- r36/java/JAVAOPS.H +++ r36/java/JAVAOPS.H @@ -1,241 +1,241 @@ -/* javaops.h: Copyright (C) Codemist Ltd., 1996. */ - -/* Java operators. */ -/* The operators below are taken from */ -/* "The Java Virtual Machine Specification" (dated Aug 21, 1995). */ -/* They are listed in section order, rather than numerical order, but */ -/* I note there are 203 of them: 0..202 and 209 with 186 unused. */ - -/* section 3.2: pushing constants onto the stack */ -#define j_bipush 16 -#define j_sipush 17 -#define j_ldc1 18 -#define j_ldc2 19 -#define j_ldc2w 20 -#define j_aconst_null 1 -#define j_iconst_m1 2 -#define j_iconst_0 3 -#define j_iconst_1 4 -#define j_iconst_2 5 -#define j_iconst_3 6 -#define j_iconst_4 7 -#define j_iconst_5 8 -#define j_lconst_0 9 -#define j_lconst_1 10 -#define j_fconst_0 11 -#define j_fconst_1 12 -#define j_fconst_2 13 -#define j_dconst_0 14 -#define j_dconst_1 15 -/* section 3.3: loading locals onto the stack */ -#define j_iload 21 -#define j_iload_0 26 -#define j_iload_1 27 -#define j_iload_2 28 -#define j_iload_3 29 -#define j_lload 22 -#define j_lload_0 30 -#define j_lload_1 31 -#define j_lload_2 32 -#define j_lload_3 33 -#define j_fload 23 -#define j_fload_0 34 -#define j_fload_1 35 -#define j_fload_2 36 -#define j_fload_3 37 -#define j_dload 24 -#define j_dload_0 38 -#define j_dload_1 39 -#define j_dload_2 40 -#define j_dload_3 41 -#define j_aload 25 -#define j_aload_0 42 -#define j_aload_1 43 -#define j_aload_2 44 -#define j_aload_3 45 -/* section 3.4 storing stack values into locals */ -#define j_istore 54 -#define j_istore_0 59 -#define j_istore_1 60 -#define j_istore_2 61 -#define j_istore_3 62 -#define j_lstore 55 -#define j_lstore_0 63 -#define j_lstore_1 64 -#define j_lstore_2 65 -#define j_lstore_3 66 -#define j_fstore 56 -#define j_fstore_0 67 -#define j_fstore_1 68 -#define j_fstore_2 69 -#define j_fstore_3 70 -#define j_dstore 57 -#define j_dstore_0 71 -#define j_dstore_1 72 -#define j_dstore_2 73 -#define j_dstore_3 74 -#define j_astore 58 -#define j_astore_0 75 -#define j_astore_1 76 -#define j_astore_2 77 -#define j_astore_3 78 -#define j_iinc 132 -/* section 3.5: wider index for loading etc. */ -#define j_wide 196 -/* section 3.6: managing arrays */ -#define j_newarray 188 -#define j_anewarray 189 -#define j_multinewarray 197 -#define j_arraylength 190 -#define j_iaload 46 -#define j_laload 47 -#define j_faload 48 -#define j_daload 49 -#define j_aaload 50 -#define j_baload 51 -#define j_caload 52 -#define j_saload 53 -#define j_iastore 79 -#define j_lastore 80 -#define j_fastore 81 -#define j_dastore 82 -#define j_aastore 83 -#define j_bastore 84 -#define j_castore 85 -#define j_sastore 86 -/* 3.7 stack instructions */ -#define j_nop 0 -#define j_pop 87 -#define j_pop2 88 -#define j_dup 89 -#define j_dup2 92 -#define j_dup_x1 90 -#define j_dup2_x1 93 -#define j_dup_x2 91 -#define j_dup2_x2 94 -#define j_swap 95 -/* 3.8 arithmetic instructions */ -#define j_iadd 96 -#define j_ladd 97 -#define j_fadd 98 -#define j_dadd 99 -#define j_isub 100 -#define j_lsub 101 -#define j_fsub 102 -#define j_dsub 103 -#define j_imul 104 -#define j_lmul 105 -#define j_fmul 106 -#define j_dmul 107 -#define j_idiv 108 -#define j_ldiv 109 -#define j_fdiv 110 -#define j_ddiv 111 -#define j_irem 112 -#define j_lrem 113 -#define j_frem 114 -#define j_drem 115 -#define j_ineg 116 -#define j_lneg 117 -#define j_fneg 118 -#define j_dneg 119 -/* 3.9 logical instructions */ -#define j_ishl 120 -#define j_ishr 121 -#define j_iushr 122 -#define j_lshl 123 -#define j_lshr 124 -#define j_lushr 125 -#define j_iand 126 -#define j_land 127 -#define j_ior 128 -#define j_lor 129 -#define j_ixor 130 -#define j_lxor 131 -/* 3.10 conversion instructions */ -#define j_i2l 133 -#define j_i2f 134 -#define j_i2d 135 -#define j_l2i 136 -#define j_l2f 137 -#define j_l2d 138 -#define j_f2i 139 -#define j_f2l 140 -#define j_f2d 141 -#define j_d2i 142 -#define j_d2l 143 -#define j_d2f 144 -#define j_int2byte 145 -#define j_int2char 146 -#define j_int2short 147 -/* 3.11 control transfer instructions */ -#define j_ifeq 153 -#define j_ifnull 198 -#define j_iflt 155 -#define j_ifle 158 -#define j_ifne 154 -#define j_ifnonnull 199 -#define j_ifgt 157 -#define j_ifge 156 -#define j_if_icmpeq 159 -#define j_if_icmpne 160 -#define j_if_icmplt 161 -#define j_if_icmpgt 163 -#define j_if_icmple 164 -#define j_if_icmpge 162 -#define j_lcmp 148 -#define j_fcmpl 149 -#define j_fcmpg 150 -#define j_dcmpl 151 -#define j_dcmpg 152 -#define j_if_acmpeq 165 -#define j_if_acmpne 166 -#define j_goto 167 -#define j_goto_w 200 -#define j_jsr 168 -#define j_jsr_w 201 -#define j_ret 169 -#define j_ret_w 209 -/* 3.12 function return */ -#define j_ireturn 172 -#define j_lreturn 173 -#define j_freturn 174 -#define j_dreturn 175 -#define j_areturn 176 -#define j_return 177 -#define j_breakpoint 202 -/* 3.13 table jumping */ -#define j_tableswitch 170 -#define j_lookupswitch 171 -/* 3.14 manipulating object fields */ -#define j_putfield 181 -#define j_getfield 180 -#define j_putstatic 179 -#define j_getstatic 178 -/* 3.15 method invokation */ -#define j_invokevirtual 182 -#define j_invokenonvirtual 183 -#define j_invokestatic 184 -#define j_invokeinterface 185 -/* 3.16 exception handling */ -#define j_athrow 191 -/* 3.17 miscellaneous object operation */ -#define j_new 187 -#define j_checkcast 192 -#define j_instanceof 193 -#define j_monitorenter 194 -#define j_monitorexit 195 -/* Quick variants of opcodes are not currently supported. */ - -/* Java type codes. */ -#define T_BOOLEAN 4 -#define T_CHAR 5 -#define T_FLOAT 6 -#define T_DOUBLE 7 -#define T_BYTE 8 -#define T_SHORT 9 -#define T_INT 10 -#define T_LONG 11 - -/* end of javaops.h */ +/* javaops.h: Copyright (C) Codemist Ltd., 1996. */ + +/* Java operators. */ +/* The operators below are taken from */ +/* "The Java Virtual Machine Specification" (dated Aug 21, 1995). */ +/* They are listed in section order, rather than numerical order, but */ +/* I note there are 203 of them: 0..202 and 209 with 186 unused. */ + +/* section 3.2: pushing constants onto the stack */ +#define j_bipush 16 +#define j_sipush 17 +#define j_ldc1 18 +#define j_ldc2 19 +#define j_ldc2w 20 +#define j_aconst_null 1 +#define j_iconst_m1 2 +#define j_iconst_0 3 +#define j_iconst_1 4 +#define j_iconst_2 5 +#define j_iconst_3 6 +#define j_iconst_4 7 +#define j_iconst_5 8 +#define j_lconst_0 9 +#define j_lconst_1 10 +#define j_fconst_0 11 +#define j_fconst_1 12 +#define j_fconst_2 13 +#define j_dconst_0 14 +#define j_dconst_1 15 +/* section 3.3: loading locals onto the stack */ +#define j_iload 21 +#define j_iload_0 26 +#define j_iload_1 27 +#define j_iload_2 28 +#define j_iload_3 29 +#define j_lload 22 +#define j_lload_0 30 +#define j_lload_1 31 +#define j_lload_2 32 +#define j_lload_3 33 +#define j_fload 23 +#define j_fload_0 34 +#define j_fload_1 35 +#define j_fload_2 36 +#define j_fload_3 37 +#define j_dload 24 +#define j_dload_0 38 +#define j_dload_1 39 +#define j_dload_2 40 +#define j_dload_3 41 +#define j_aload 25 +#define j_aload_0 42 +#define j_aload_1 43 +#define j_aload_2 44 +#define j_aload_3 45 +/* section 3.4 storing stack values into locals */ +#define j_istore 54 +#define j_istore_0 59 +#define j_istore_1 60 +#define j_istore_2 61 +#define j_istore_3 62 +#define j_lstore 55 +#define j_lstore_0 63 +#define j_lstore_1 64 +#define j_lstore_2 65 +#define j_lstore_3 66 +#define j_fstore 56 +#define j_fstore_0 67 +#define j_fstore_1 68 +#define j_fstore_2 69 +#define j_fstore_3 70 +#define j_dstore 57 +#define j_dstore_0 71 +#define j_dstore_1 72 +#define j_dstore_2 73 +#define j_dstore_3 74 +#define j_astore 58 +#define j_astore_0 75 +#define j_astore_1 76 +#define j_astore_2 77 +#define j_astore_3 78 +#define j_iinc 132 +/* section 3.5: wider index for loading etc. */ +#define j_wide 196 +/* section 3.6: managing arrays */ +#define j_newarray 188 +#define j_anewarray 189 +#define j_multinewarray 197 +#define j_arraylength 190 +#define j_iaload 46 +#define j_laload 47 +#define j_faload 48 +#define j_daload 49 +#define j_aaload 50 +#define j_baload 51 +#define j_caload 52 +#define j_saload 53 +#define j_iastore 79 +#define j_lastore 80 +#define j_fastore 81 +#define j_dastore 82 +#define j_aastore 83 +#define j_bastore 84 +#define j_castore 85 +#define j_sastore 86 +/* 3.7 stack instructions */ +#define j_nop 0 +#define j_pop 87 +#define j_pop2 88 +#define j_dup 89 +#define j_dup2 92 +#define j_dup_x1 90 +#define j_dup2_x1 93 +#define j_dup_x2 91 +#define j_dup2_x2 94 +#define j_swap 95 +/* 3.8 arithmetic instructions */ +#define j_iadd 96 +#define j_ladd 97 +#define j_fadd 98 +#define j_dadd 99 +#define j_isub 100 +#define j_lsub 101 +#define j_fsub 102 +#define j_dsub 103 +#define j_imul 104 +#define j_lmul 105 +#define j_fmul 106 +#define j_dmul 107 +#define j_idiv 108 +#define j_ldiv 109 +#define j_fdiv 110 +#define j_ddiv 111 +#define j_irem 112 +#define j_lrem 113 +#define j_frem 114 +#define j_drem 115 +#define j_ineg 116 +#define j_lneg 117 +#define j_fneg 118 +#define j_dneg 119 +/* 3.9 logical instructions */ +#define j_ishl 120 +#define j_ishr 121 +#define j_iushr 122 +#define j_lshl 123 +#define j_lshr 124 +#define j_lushr 125 +#define j_iand 126 +#define j_land 127 +#define j_ior 128 +#define j_lor 129 +#define j_ixor 130 +#define j_lxor 131 +/* 3.10 conversion instructions */ +#define j_i2l 133 +#define j_i2f 134 +#define j_i2d 135 +#define j_l2i 136 +#define j_l2f 137 +#define j_l2d 138 +#define j_f2i 139 +#define j_f2l 140 +#define j_f2d 141 +#define j_d2i 142 +#define j_d2l 143 +#define j_d2f 144 +#define j_int2byte 145 +#define j_int2char 146 +#define j_int2short 147 +/* 3.11 control transfer instructions */ +#define j_ifeq 153 +#define j_ifnull 198 +#define j_iflt 155 +#define j_ifle 158 +#define j_ifne 154 +#define j_ifnonnull 199 +#define j_ifgt 157 +#define j_ifge 156 +#define j_if_icmpeq 159 +#define j_if_icmpne 160 +#define j_if_icmplt 161 +#define j_if_icmpgt 163 +#define j_if_icmple 164 +#define j_if_icmpge 162 +#define j_lcmp 148 +#define j_fcmpl 149 +#define j_fcmpg 150 +#define j_dcmpl 151 +#define j_dcmpg 152 +#define j_if_acmpeq 165 +#define j_if_acmpne 166 +#define j_goto 167 +#define j_goto_w 200 +#define j_jsr 168 +#define j_jsr_w 201 +#define j_ret 169 +#define j_ret_w 209 +/* 3.12 function return */ +#define j_ireturn 172 +#define j_lreturn 173 +#define j_freturn 174 +#define j_dreturn 175 +#define j_areturn 176 +#define j_return 177 +#define j_breakpoint 202 +/* 3.13 table jumping */ +#define j_tableswitch 170 +#define j_lookupswitch 171 +/* 3.14 manipulating object fields */ +#define j_putfield 181 +#define j_getfield 180 +#define j_putstatic 179 +#define j_getstatic 178 +/* 3.15 method invokation */ +#define j_invokevirtual 182 +#define j_invokenonvirtual 183 +#define j_invokestatic 184 +#define j_invokeinterface 185 +/* 3.16 exception handling */ +#define j_athrow 191 +/* 3.17 miscellaneous object operation */ +#define j_new 187 +#define j_checkcast 192 +#define j_instanceof 193 +#define j_monitorenter 194 +#define j_monitorexit 195 +/* Quick variants of opcodes are not currently supported. */ + +/* Java type codes. */ +#define T_BOOLEAN 4 +#define T_CHAR 5 +#define T_FLOAT 6 +#define T_DOUBLE 7 +#define T_BYTE 8 +#define T_SHORT 9 +#define T_INT 10 +#define T_LONG 11 + +/* end of javaops.h */  Index: r36/java/JAVARTS.C ================================================================== --- r36/java/JAVARTS.C +++ r36/java/JAVARTS.C @@ -1,18 +1,18 @@ /* javarts.c: Copyright (C) Codemist Ltd., 1996. */ #include #include #include -#include "machine.h" -#include "tags.h" -#include "cslerror.h" -#include "externs.h" -#include "read.h" -#include "stream.h" -#include "arith.h" -#include "entries.h" +#include "machine.h" +#include "tags.h" +#include "cslerror.h" +#include "externs.h" +#include "read.h" +#include "stream.h" +#include "arith.h" +#include "entries.h" #include "javahost.h" #include "javaops.h" #include "javaglb.h" static int32 *println(int32 *spbase) Index: r36/lalr.red ================================================================== --- r36/lalr.red +++ r36/lalr.red @@ -1,1569 +1,1569 @@ - -symbolic; -spool "lalr.log"; -on comp, backtrace; -unglobal '(!*raise); -fluid '(!*raise); - -%============================================================================= -% The file provides parser support for Lisp. The file contains three -% major sections. The first is a lexical analyser, which has been -% coded to support RLISP and Standard Lisp. Its interface is modelled after -% the one used with the lex/yacc combination commonly used with Unix. -% -% The second section is the generic part of an LR parser. It requires -% tables to tell it what actions to take, and calls the lexical analyser to -% obtain tokens. -% -% The final part is an LALR(1) parser generator, which can take the -% specification of a grammar and construct tables that direct the -% generic parser skeleton. -% -%============================================================================= - -% -% This is a lexical anaylser for use with RLISP. Its interface is -% styles after the one needed by yacc, in that it exports a function -% called yylex() that returns as a value a numeric category code, but -% sets a variable yylval to hold further information about the token -% just parsed. Single character objects are coded as their (ASCII?) code -% [leaving this code non-portable to machines with other encodings?]. -% Other things must have been given 'lex_code properties indicate the -% associated category code. This lexer handles ' and ` as special prefix -% characters that introduce Lisp-stype s-expressions. and it knows about -% RLISP-style comments and a few diphthongs. It also supports some -% simple preprocessor directives. -% -% Arthur Norman. April 1995 - - -fluid '(!*raise !*lower !*echo); -global '(lex_char yylval last64 last64p which_line); - -% I keep a circular buffer with the last 64 characters that have been -% read. Initially the buffer contains NILs rather than characters, so I can -% tell when it is only partially filled. - -smacro procedure yyreadch(); - << last64p := last64p + 1; - if last64p = 64 then last64p := 0; - lex_char := readch(); - if lex_char = !$eol!$ then which_line := which_line + 1; - putv(last64, last64p, lex_char); - lex_char >>; - -symbolic procedure yyerror msg; - begin - scalar c; - terpri(); - princ "+++++ Parse error at line "; prin which_line; princ ":"; - if atom msg then msg := list msg; - for each s in msg do << princ " "; princ s >>; - terpri(); - for i := 1:64 do << - last64p := last64p + 1; - if last64p = 64 then last64p := 0; - c := getv(last64, last64p); - if c = !$eof!$ then princ "" - else if not (c = nil) then princ c >>; - if not (c = !$eol!$) then terpri() - end; - -% Before a succession of calls to yylex() it is necessary to -% ensure that lex_char is set suitably and that the circular buffer -% used to store characters for error messages is ready for use. - -symbolic procedure start_parser(); - << last64 := mkvect 64; - last64p := 0; - which_line := 1; - yyreadch() >>; - -% -% The following version of YYLEX provides RLISP with a facility for -% conditional compilation. The protocol is that text is included or -% excluded at the level of tokens. Control by use of new reserved -% tokens !#if, !#else and !#endif. These are used in the form: -% !#if (some Lisp expression for use as a condition) -% ... RLISP input ... -% !#else -% ... alternative RLISP input ... -% !#endif -% -% The form -% !#if C1 ... !#elif C2 ... !#elif C3 ... !#else ... !#endif -% is also supported. -% -% Conditional compilation can be nested. If the Lisp expression used to -% guard a condition causes an error it is taken to be a FALSE condition. -% It is not necessary to have an !#else before !#endif if no alternative -% text is needed. Although the examples here put !#if etc at the start of -% lines this is not necessary (though it may count as good style?). Since -% the condtion will be read using RLISPs own list-reader there could be -% condtional compilation guarding parts of it - the exploitation of that -% possibility is to be discouraged! -% -% Making the condition a raw Lisp expression makes sure that parsing it -% is easy. It makes it possible to express arbitrary conditions, but it is -% hoped that most conditions will not be very elaborate - things like -% !#if (not (member 'csl lispsystem!*)) -% error(); -% !#else -% magic(); -% !#endif -% or -% !#if debugging_mode % NB if variable is unset that counts as nil -% print "message"; % so care should be taken to select the most -% !#endif % useful default sense for such tests -% should be about as complicated as reasonable people need. -% -% Two further facilities are provided: -% !#eval (any lisp expression) -% causes that expression to be evaluated at parse time. Apart from any -% side-effects in the evaluation the text involved is all ignored. It is -% expected that this will only be needed in rather curious cases, for instance -% to set system-specific options for a compiler. -% -% !#define symbol value -% where the value should be another symbol, a string or a number, causes -% the first symbol to be mapped onto the second value wherever it occurs in -% subsequent input. No special facility for undoing the effect of a -% !#define is provided, but the general-purpose !#eval could be used to -% remove the '!#define property that is involved. -% -% NOTE: The special symbols !#if etc are NOT recognised within Lisp -% quoted expressions, so test like the following will be -% ineffective: -% a := '( -% P -% !#if q_is_wanted -% Q -% !#endif -% Q); -% but on the other hand code like -% if sym = '!#if then ... -% behaves the way that had probably been wanted. Unlike the C -% preprocessor, this system recognizes directives within rather than -% just at the start of lines. - - -symbolic procedure yylex(); - begin - scalar w, done; -% I take a rather robust view here - words that are intended to be used as -% keywords may not be written with included escape characters. Thus for -% instance this lexer will view "be!gin" or "!begin" as being a simple -% symbol and NOT being the keyword "begin". - w := lex_basic_token(); -% The "while not done" loop is so that I can restart the scan after seeing -% a pre-processor directive such as !#if. - while not done do << -% The word "COMMENT" introduces a comment that terminates at the next ";" -% or "$". - while yylval = 'comment and - w = '!:symbol_or_keyword do << - while not (lex_char = '!; or lex_char = '!$) do - yyreadch(); - yyreadch(); - w := lex_basic_token() >>; -% If a word was spelt out directly (without any escape characters in it) it -% may be a keyword - if it is, then convert it here. - if w = '!:symbol_or_keyword then << - if w := get(yylval, '!#define) then << - yylval := cdr w; - w := car w >> - else << - if done := get(yylval, 'lex_code) then w := done - else if flagp(yylval, 'rlis) then - w := get('rlistat, 'lex_code) - else if flagp(yylval, 'endstat) then - w := get('endstat, 'lex_code) - else w := get('!:symbol, 'lex_code); - done := t >> >> -% A word with escapes in might be a pre-processor directive. - else if w = '!:symbol then << - if yylval eq '!#if then << - read_s_expression(); - w := lex_conditional yylval >> - else if yylval eq '!#else or - yylval eq '!#elif then << - yylval := nil; - w := lex_skipping(w, nil) >> - else if yylval eq '!#endif then w := lex_basic_token() - else if yylval eq '!#eval then << - read_s_expression(); - errorset(yylval, nil, nil); - w := lex_basic_token() >> - else if yylval eq '!#define then << - read_s_expression(); - w := yylval; % Ought to be a symbol - done := read_s_expression(); - if idp w then put(w, '!#define, done . yylval); - w := lex_basic_token(); - done := nil >> - else << - w := get('!:symbol, 'lex_code); - done := t >> >> - else if numberp w then << -% Now gobble up extra characters for multi-character operators (eg ">="). -% Note that I only look one character ahead here. - while done := atsoc(lex_char, get(yylval, 'lex_dipthong)) do << - w := cdr done; - yylval := cdr w; - w := get(car w, 'lex_code); - yyreadch() >>; - if done := get(yylval, '!#define) then << - yylval := cdr done; - w := car done; - done := nil >> - else done := t >> - else << - done := t; - w := get(w, 'lex_code) >> >>; - return w - end; - - - -% If, when reading ordinary text, I come across the token !#if I read -% the expression following. If that evaluates to TRUE I just keep on -% on reading. So the sequence "!#if t" is in effect ignored. Then -% if later on I just ignore an "!#endif" all will be well. If on the other -% hand the expression evaluates to NIL (or if evaluation fails), I will -% call lex_skipping() to discard more tokens (up to and including -% the next "!#else", "!#elif t" or "!endif"). - -symbolic procedure lex_conditional x; - begin - scalar w; - w := lex_basic_token(); - x := errorset(x, nil, nil); - if errorp x or null car x then return lex_skipping(w, nil) - else return w - end; - -% I call lex_skipping when I find "!#if nil" or "!#else" or "!#elif" -% that is processed. When a top-level "!#else" or "!#elif" is found it -% is discarded before calling lex_skipping, since it must follow a -% successful "!#if" and hence introduce material to be thrown away. - -symbolic procedure lex_skipping(w, x); - begin - scalar done; -% In this code x keep track of the depth of testing of "!#if" constructions - while not done do << - if w = 0 then done := t % End of file - else << - if w = '!:symbol then << - if yylval = '!#endif then << - if null x then done := t - else x := cdr x >> - else if yylval = '!#if then x := nil . x - else if yylval = '!#else and null x then done := t - else if yylval = '!#elif and null x then << - read_s_expression(); - done := errorset(yylval, nil, nil); - if errorp done or null car done then done := nil >> >>; - w := lex_basic_token() >> >>; - return w - end; - - - -% In some cases RLISP operators are made up out of two (or more) characters. -% I map '**' onto '^', and >=, <= onto GEQ and LEQ. -% ":=" becomes SETQ. I turn << and >> onto symbols that can not be -% read directly (!:lsect and !:rsect). -% This means that the system that sets up lex_code properties had really -% better make sure that it gives setq, geq, leq, !:rsect and !:lsect values. - -put('!*, 'lex_dipthong, '((!* !^ . !^))); -put('!:, 'lex_dipthong, '((!= setq . setq))); -put('!>, 'lex_dipthong, '((!= geq . geq), - (!> !:rsect . !:rsect))); -put('!<, 'lex_dipthong, '((!= leq . leq), - (!< !:lsect . !:lsect))); - -put('!^, 'lex_code, char!-code '!^); - - -% lex_basic_token() will read the next token from the current input stream and -% leave a value in yylval to show what was found. It does not handle the -% word "comment", nor does it consolidate things like ':' followed by '=' into -% ':='. Those steps are left to yylex(). But lex_basic_token() does recognize -% the quote prefix, as in '(lisp expression). The return value is numeric -% for single-character tokens, but otherwise a descriptive symbol. - -% Some people would consider the Lisp dialect that I am using here to be -% significantly flawed, in that I need to build symbols, numbers and -% strings up as lists, and then use COMPRESS to make the real objects. The -% CONS operations involved can be seen as an overhead, and going back to -% something like the VERY old-fashioned clearbuff/pack/boffo world might -% avoid that. - -symbolic procedure lex_basic_token(); - begin - scalar r, w; -% First skip over whitespace. Note that at some stage in the future RLISP -% may want to make newlines significant and partially equivalent to -% semicolons, but that is not supported at present. - while lex_char = '! or lex_char = !$eol!$ or - (lex_char = '!% and << - while not (lex_char = !$eol!$ or lex_char = !$eof!$) do - yyreadch(); - t >>) do yyreadch(); -% Symbols start with a letter or an escaped character and continue with -% letters, digits, underscores and escapes. - if liter lex_char or - (lex_char = '!! and begin - scalar !*raise, !*lower; % Rebind !*raise & !*lower to avoid.. - r := lex_char . r; % case folding when the next character.. - yyreadch(); % is read. - return (w := t) end) then << - r := lex_char. r; - while liter(yyreadch()) or - digit lex_char or - lex_char = '!_ or - (lex_char = '!! and begin - scalar !*raise, !*lower; - r := lex_char . r; - yyreadch(); - return (w := t) end) do - r := lex_char . r; -% If there was a '!' in the word I will never treat it as a keyword. - yylval := compress reversip r; - return if w then '!:symbol else '!:symbol_or_keyword >> -% Numbers are either integers or floats. A floating point number is -% indicated by either a point "." or an exponent marker "e". In the code -% here I keep a flag (in w) to indicate if I had a floating or integer -% value, but in the end I ignore this and hand back the lexical category -% :number in both cases. - else if digit lex_char then << - r := list lex_char; - while digit (yyreadch()) do r := lex_char . r; - if lex_char = '!. then << - w := t; % Flag to indicate floating point - r := lex_char . r; - while digit (yyreadch()) do r := lex_char . r >>; -% I permit the user to write the exponent marker in either case. - if lex_char = '!e or lex_char = '!E then << -% If the input as 1234E56 I expand it as 1234.0E56 - if not w then r := '!0 . '!. . r; - w := t; - r := '!e . r; - yyreadch(); - if lex_char = '!+ or lex_char = '!- then << - r := lex_char . r; - yyreadch() >>; -% If there is no digit written after "E" I insert a zero. Thus overall the -% input 17E gets treated as 17.0E0 - if not digit lex_char then r := '!0 . r - else << - r := lex_char . r; - while digit (yyreadch()) do r := lex_char . r >> >>; - yylval := compress reversip r; - return '!:number >> -% Strings are enclosed in double-quotes, and "abc""def" is a string with -% a double-quote mark within it. Note no case folding on characters in a -% string. - else if lex_char = '!" then << - begin - scalar !*raise, !*lower; - repeat << - r := lex_char . r; - while not ((yyreadch()) = '!") do r := lex_char . r; - r := lex_char . r; - yyreadch() >> until not (lex_char = '!"); - end; - yylval := compress reversip r; - return '!:string >> -% "'" and "`" introduce Lisp syntax S-expressions - else if lex_char = '!' then << - yyreadch(); - read_s_expression(); - yylval := list('quote, yylval); - return '!:list >> - else if lex_char = '!` then << - yyreadch(); - read_s_expression(); - yylval := list('backquote, yylval); - return '!:list >> - else << - yylval := lex_char; -% I take special notice of end of file, since it is fairly drastic. -% In particular I do not attempt to advance lex_char beyond it. So I do -% TWO things here: I avoid advancing the input, and I return the code 0 -% as an end-of-file indication. - if yylval = !$eof!$ then return 0 - else << - yyreadch(); - return char!-code yylval >> >> - end; - -% -% I use a hand-written recursive descent parser for Lisp S-expressions -% mainly because the syntax involved is so VERY simple. A rough sketch of -% the syntax required is given here, but in reality (in part because I do -% not want to have to report syntax errors) I implement a more liberal -% syntax, especially as it relates to dotted-pair notation. This of course -% is one of the natural dangers in using recursive descent... the syntax -% actually parsed is only properly defined by direct reference to the code. -% - -% s_tail = ")" | -% "." s_expr ")" | -% s_expr s_tail; -% -% s_vectail = "]" | -% s_expr s_vectail; -% -% s_expr = symbol | -% number | -% string | -% "(" s_tail | -% "[" s_vectail | -% "'" s_expr | -% "`" s_expr | -% "," s_expr | -% ",@" s_expr; - -global '(dot_char rpar_char rsquare_char); - -dot_char := char!-code '!.; -rpar_char := char!-code '!); -rsquare_char := char!-code '!]; - -symbolic procedure read_s_expression(); - << -% At the start of an S-expression I want to check for the characters -% "(", "[" and ",". Thus I need to skip whitespace. - while lex_char = '! or lex_char = '!$eol!$ do yyreadch(); - if lex_char = '!( then begin - scalar r, w, w1; - yyreadch(); - w := read_s_expression(); - while not (w = rpar_char or w = dot_char or w = 0) do << - r := yylval . r; -% Note that at the end of the list read_s_expression() will read the ")" -% as a token. - w := read_s_expression() >>; - if not w = dot_char then yylval := reversip r - else << - read_s_expression(); % Thing after the "." - w := yylval; -% Reverse the list putting a dotted item on the end. - while r do << - w1 := cdr r; - rplacd(r, w); - w := r; - r := w1 >>; - yylval := w; -% I will be somewhat liberal about syntactic problems with dotted pair -% notation, since it is unclear how I can usefully report or repair errors. - while lex_char = '! or lex_char = '!$eol!$ do - yyreadch(); -% When I find a ")" I do not read beyond it immediately, but reset lex_char -% to whitespace. This may help prevent unwanted hangups in interactive use. - if lex_char = '!) then lex_char := '! >>; - return '!:list end -% "[" introduces a simple vector. - else if lex_char = '![ then begin - scalar r, w, w1; - yyreadch(); - w := read_s_expression(); - w1 := -1; - while not (w = rsquare_char or w = 0) do << - r := yylval . r; - w1 := w1 + 1; - w := read_s_expression() >>; -% Create a vector of the correct size and copy information into it. - w := mkvect w1; - r := reversip r; - w1 := 0; - while r do << - putv(w, w1, car r); - w1 := w1 + 1; - r := cdr r >>; - yylval := w; - return '!:list end -% I spot "," and ",@" here, and should wonder if I should (a) police that -% they are only expected to make sense within the scope of a "`" and (b) -% whether I ought to expand them in terms of LIST, CONS, APPEND etc here. -% For now I just hand back markers that show where they occured. - else if lex_char = '!, then << - yyreadch(); - if lex_char = '!@ then << - yyreadch(); - read_s_expression(); - yylval := list('!,!@, yylval) >> - else << - read_s_expresssion(); - yylval := list('!,, yylval) >>; - 'list >> -% Care with ")" and "]" not to read ahead further than is essential. - else if lex_char = '!) or lex_char = '!] or lex_char = '!. then << - yylval := lex_char; - lex_char := '! ; - char!-code yylval >> -% In most cases (including "'" and "`") I just hand down to read a token. -% This covers the cases of symbols, numbers and strings. - else lex_basic_token() >>; - - - -%============================================================================= - -% Here I have a general-purpose LR(1) parser skeleton. This needs to -% have a source of tokens, and some tables that will direct its actions. - -% The format of the tables required by this code will be a little curious, -% mainly because they represent some attempt to compact the information that -% is needed. Note that the CSL functions mkvect16, putv16, getv16 are -% somewhat similar to the regular mkvect, putv and getv, but may be used -% if the vector contents will always be 16-bit fixnums. - -global '(!*verbose); - -!*verbose := t; % How much will the parset-generator print? - -global '(goto_index goto_old_state goto_new_state); - -% For each terminal I have a pointer (stored in goto_index) into -% a pair of vectors, goto_old_state and goto_new_state. The first of these -% holds states that I might be in, and the second holds the ones I must -% move into after a reduction has been performed. In the goto_old_state -% table the value "-1" is taken to match any state that I am attempting -% to look up. Thus it can be used to terminate a segment of the table. I am -% entitled to let undefined locations in the goto table respond with -% any value that just happens. - -smacro procedure get_goto(state, non_terminal); - << w1 := getv16(goto_index, non_terminal); - while not (((w2 := getv16(goto_old_state, w1)) = -1) or - w2 = state) do w1 := w1 + 1; - getv16(goto_new_state, w1) >>; - -global '(action_index, action_terminal action_result); - -% In a rather similar way, actions are found via an association-list -% like look-up in a table. In this table a strictly positive number n stands -% for (SHIFT n) [observe that if I reserve zero as the number of the -% initial state of my augmented grammar I can never need to shift into -% state 0]. The value 0 in the table represents ACCEPT. This leaves -% nagative values to cover reductions and error cases. - -smacro procedure get_action(state, terminal); - << w1 := getv16(action_index, state); - while not (((w2 := getv16(action_terminal, w1)) = -1) or - w2 = terminal) do w1 := w1 + 1; - getv(action_result, w1) >>; - -global '(action_first_error action_error_messages); - -global '(action_fn action_A action_n); - -symbolic procedure yyparse(); - begin - scalar sym_stack, state_stack, next_input, w, w1, w2; - state_stack := list 0; % Note that state 0 must be the initial one. - start_parser(); - next_input := yylex(); - while not (w := get_action(car state_stack, next_input)) = 0 do - if w > 0 then << - sym_stack := next_input . sym_stack; - state_stack := cadr w . state_stack; - next_input := yylex() >> - else begin - scalar A, n, action; - w := - (w + 1); - if w < action_first_error then << - action := getv(action_fn, w); - n := getv8(action_n, w); - A := getv16(action_A, w); -% I am now reducing by "A -> beta { action() }" where beta has n items - w := nil; - for i := 1:n do << - w := car sym_stack . w; - sym_stack := cdr sym_stack; - state_stack := cdr state_stack >>; - w := reversip w; - if action then w := apply1(action, w) - else w := A . w; - sym_stack := w . sym_stack; - state_stack := get_goto(car state_stack, A) >> - else << - w := w - action_first_error; - yyerror getv(action_error_messages, w); -% The next activity must result in the loop ending... - state_stack := list 0; - sym_stack := '(error); - next_input := 0 >> - end; - return car sym_stack - end; - -%============================================================================= -% -% A grammar is represented as a list of rules. A rule -% sym : x y z { p q r } -% | x y z { p q r } -% ; -% maps onto the list -% (sym ((x y z) p q r) -% ((x y z) p q r)) -% and items on the right hand side can be symbols or strings. Strings -% stand for terminals. Symbols that are mentioned on a left hand side of -% a production are non-terminals, others are considered to be terminals -% supported by the lexer. -% -% ***** I am still working out what to do with the "semantic actions". - -global '(terminals non_terminals symbols goto_cache action_map); - -smacro procedure lalr_productions x; - get(x, 'produces); - -smacro procedure lalr_set_productions(x, y); - put(x, 'produces, y); - -symbolic procedure lalr_prin_symbol x; - if x = 0 then princ "$" - else if x = nil then princ "" - else if x = '!. then princ "." - else if numberp x and rassoc(x, terminals) then - prin car rassoc(x, terminals) - else if stringp x then prin x - else for each c in explode2uc x do princ c; - -symbolic procedure lalr_display_symbols(); - begin - princ "Terminal symbols are:"; terpri(); - for each x in terminals do << - princ " "; prin car x; - princ ":"; prin cdr x >>; - terpri(); - princ "Non-terminal symbols are:"; terpri(); - for each x in non_terminals do begin - scalar w; - princ "["; prin get(x, 'non_terminal_code); princ "]"; - lalr_prin_symbol x; - w := ":"; - for each y in lalr_productions x do << - ttab 20; princ w; w := "|"; - for each z in car y do << princ " "; lalr_prin_symbol z >>; - if posn() > 48 then terpri(); - ttab 48; - princ "{"; - for each z in cdr y do << princ " "; prin z >>; - princ " }"; - terpri() >>; - ttab 20; - princ ";"; - terpri() end; - terpri(); - end; - -symbolic procedure lalr_print_action_map(); - begin - princ "Action map:"; terpri(); - for each x in action_map do << - prin cdr x; princ ":"; ttab 12; prin car x; terpri() >> - end; - -symbolic procedure lalr_set_grammar g; - begin - scalar name, vals, tnum, w; - terminals := non_terminals := symbols := nil; - tnum := 0; -% I will start by augmenting the grammar with an initial production... - g := list('s!', list list caar g) . g; - for each x in g do << - name := car x; vals := cdr x; - if name member non_terminals then - vals := append(vals, lalr_productions name) - else non_terminals := name . non_terminals; - for each vv in cdr x do - for each v in car vv do << - if stringp v or numberp v then << - if not assoc(v, terminals) then - terminals := (v . (tnum := tnum+1)) . terminals >> - else if not (v member symbols) then symbols := v . symbols >>; - lalr_set_productions(name, vals) >>; - for each name in non_terminals do symbols := delete(name, symbols); - for each v in symbols do terminals := (v . (tnum := tnum+1)) . terminals; -% I reverse the list of non-terminals here so that the starting symbol -% remains as the first item. - non_terminals := reversip non_terminals; - tnum := -1; - for each v in non_terminals do - put(v, 'non_terminal_code, tnum := tnum+1); - symbols := append(non_terminals, for each x in terminals collect cdr x); - goto_cache := mkhash(length non_terminals, 1, 1.5); - if !*verbose then lalr_display_symbols(); -% Map all terminals onto numeric codes. - for each x in non_terminals do - lalr_set_productions(x, - for each y in lalr_productions x collect - sublis(terminals, car y) . cdr y); -% Map all actions onto numeric codes, such that identical actions all have the -% same code - action_map := nil; - tnum := -1; - for each x in non_terminals do - for each a in lalr_productions x do << - w := assoc(cdr a, action_map); - if null w then << - w := cdr a . (tnum := tnum + 1); - action_map := w . action_map >>; - rplacd(a, list cdr w) >>; - action_map := reversip action_map; - if !*verbose then lalr_print_action_map(); - lalr_calculate_first non_terminals; - end; - -symbolic procedure lalr_clean_up(); - begin - for each x in terminals do << - remprop(x, 'produces); - remprop(x, 'lalr_first); - remprop(x, 'non_terminal_code) >>; - terminals := non_terminals := symbols := nil; - goto_cache := action_map := nil - end; - -symbolic procedure lalr_action(lhs, rhs); - cdr assoc(rhs, lalr_productions lhs); - -symbolic procedure lalr_print_firsts g; - begin - princ "FIRST sets for each non-terminal:"; terpri(); - for each x in g do << - lalr_prin_symbol x; - princ ": "; - ttab 15; - for each y in get(x, 'lalr_first) do << - princ " "; lalr_prin_symbol y >>; - terpri() >> - end; - -symbolic procedure lalr_calculate_first g; - begin - scalar w, y, z, done; - for each x in g do - if assoc(nil, lalr_productions x) then put(x, 'lalr_first, '(nil)); - repeat << - done := nil; - for each x in g do << - z := get(x, 'lalr_first); - for each y1 in lalr_productions x do << - y := car y1; - while y and - not numberp y - and (nil member (w := get(car y, 'lalr_first))) do << - z := union(w, z); - y := cdr y >>; - if null y then nil - else if numberp car y then z := union(list car y, z) - else z := union(get(car y, 'lalr_first), z) >>; - if not (z = get(x, 'lalr_first)) then done := t; - put(x, 'lalr_first, z) >> - >> until not done; - if !*verbose then lalr_print_firsts g; - return nil - end; - -symbolic procedure lalr_first l; - begin - scalar r, w; - while l and - not numberp car l and - (nil member (w := get(car l, 'lalr_first))) do << - r := union(delete(nil, w), r); - l := cdr l >>; - if null l then r := nil . r - else if numberp car l then r := union(list car l, r) - else r := union(w, r); - return r - end; - - -% The next few procedures are as documented in Figure 4.38 of Red Dragon - -symbolic procedure lalr_print_items(heading, cc); - begin - princ heading; - terpri(); - for each y in cc do << - princ "Item number "; prin cdr y; terpri(); - for each x in sort(car y, function orderp) do << - lalr_prin_symbol caar x; princ " ->"; - for each y in cdar x do << princ " "; lalr_prin_symbol y >>; - princ " : "; - lalr_prin_symbol cadr x; - terpri() >>; - for each x in hashcontents goto_cache do - for each xx in cdr x do - if car xx = cdr y then << - ttab 10; lalr_prin_symbol car x; - princ " GOTO state "; prin cdr xx; terpri() >> >> - end; - -symbolic procedure lalr_items g; - begin - scalar c, val, done, w, w1, w2, n; - val := lalr_productions 's!'; - if cdr val then error(0, "Starting state must only reduce to one thing") - else val := caar val; - n := 0; - c := list (lalr_closure list list(('s!' . '!. . val), 0) . n); - repeat << - done := nil; - for each i in c do - for each x in symbols do - if w := lalr_goto(car i, x) then << - w1 := assoc(w, c); - if w1 then << - w2 := gethash(x, goto_cache); - if not assoc(cdr i, w2) then - puthash(x, goto_cache, (cdr i . cdr w1) . w2) >> - else << - c := (w . (n := n + 1)) . c; - puthash(x, goto_cache, - (cdr i . n) . gethash(x, goto_cache)); - done := t >> >> - >> until not done; - c := reversip c; % So that item numbers come out in nicer order. - if !*verbose then lalr_print_items("LR(1) Items:", c); - return c - end; - -symbolic procedure lalr_closure i; - begin - scalar pending, a, rule, tail, done, ff, w; - pending := i; - while pending do << - ff := car pending; % [(A -> alpha . B beta), a] - pending := cdr pending; - rule := car ff; a := cadr ff; tail := cdr ('!. member rule); - if tail and not numberp car tail then << - ff := lalr_first append(cdr tail, list a); - for each p in lalr_productions car tail do - for each b in ff do << - w := list(car tail . '!. . car p, b); -% It might be better to store items as hash tables, since then the -% member-check here would be much faster. - if not (w member i) then << - i := w . i; - pending := w . pending >> >> >> >>; - return i - end; - -symbolic procedure lalr_move_dot(z, x); - begin - scalar r; - while not (car z = '!.) do << - r := car z . r; - z := cdr z >>; - z := cdr z; - if not (z and car z = x) then return nil; - z := car z . '!. . cdr z; - while r do << - z := car r . z; - r := cdr r >>; - return z - end; - -symbolic procedure lalr_goto(i, x); - begin - scalar j, w; - for each z in i do << - w := lalr_move_dot(car z, x); - if w then j := list(w, cadr z) . j >>; - return lalr_closure j - end; - -symbolic procedure lalr_cached_goto(i, x); - cdr assoc(i, gethash(x, goto_cache)); - -% Next part of Algorithm 4.11 from the Red Dragon - -symbolic procedure lalr_remove_duplicates x; - begin - scalar r; - if null x then return nil; - x := sort(x, function orderp); - r := list car x; - x := cdr x; - while x do << - if not (car x = car r) then r := car x . r; - x := cdr x >>; - return r - end; - -symbolic procedure lalr_core i; - lalr_remove_duplicates for each x in car i collect car x; - -symbolic procedure lalr_same_core(i1, i2); - lalr_core i1 = lalr_core i2; - -% cc is a list of items, while i is a single item. If cc already contains -% an item with the same core as I then merge i into that, and adjust any -% goto records either out of or into i to refer now to the thing merged -% with. - -fluid '(renamings); - -symbolic procedure lalr_insert_core(i, cc); - if null cc then list i - else if lalr_same_core(i, car cc) then << - renamings := (i . cdar cc) . renamings; - (union(car i, caar cc) . cdar cc) . cdr cc >> - else car cc . lalr_insert_core(i, cdr cc); - -symbolic procedure lalr_rename_gotos(); - begin - scalar w; - for each x in non_terminals do << - w := sublis(renamings, gethash(x, goto_cache)); - puthash(x, goto_cache, lalr_remove_duplicates w) >> - end; - -% Part of Algorithm 4.10 of the Red Dragon - -symbolic procedure lalr_print_actions action_table; - begin - scalar w; - princ "Actions:"; terpri(); - for each x in action_table do - for each xx in cdr x do << - prin car x; ttab 20; - lalr_prin_symbol car xx; ttab 40; - w := cadr xx; - if eqcar(w, 'reduce) then << - princ "reduce "; - lalr_prin_symbol caadr w; - princ " ->"; - for each v in cdadr w do << princ " "; lalr_prin_symbol v >>; - princ " {"; - for each v in caddr w do << princ " "; prin v >>; - princ " }"; - terpri() >> - else << prin w; terpri() >> >> - end; - -symbolic procedure lalr_make_actions c; - begin - scalar action_table, aa, j, w; - for each i in c do << - aa := nil; - for each r in car i do << - w := cdr ('!. member cdar r); - if w and numberp car w then << - j := lalr_cached_goto(cdr i, car w); - aa := list(car w, list('shift, j)) . aa >> - else if null w and not (caar r = 's!') then << - w := reverse cdr reverse car r; - aa := - list(cadr r, list('reduce, w, lalr_action(car w, cdr w))) . - aa >> - else if null w and caar r = 's!' then - aa := list(0, 'accept) . aa >>; - action_table := (cdr i . lalr_remove_duplicates aa) . action_table >>; - action_index := mkvect16 caar action_table; - action_table := reversip action_table; - if !*verbose then lalr_print_actions action_table; - j := 0; w := nil; - for each x in action_table do << - putv16(action_index, car x, j); - aa := lalr_lay_out_actions cdr x; - while aa do << - w := (0 . 0) . w; - j := j + 1 >> >>; - action_terminal := mkvect16 j; - action_result := mkvect16 j; - while j > 0 do << - j := j - 1; - putv16(action_terminal, j, caar w); - putv16(action_result, j, cdar w); - w := cdr w >> - end; - -symbolic procedure lalr_most_common_dest p; - begin - scalar r, w; - for each x in p do - if (w := assoc(cdr x, r)) then rplacd(w, cdr w + 1) - else r := (cdr x . 1) . r; - w := car r; - for each x in cdr r do if cdr x > cdr w then w := x; - return car w - end; - -symbolic procedure lalr_make_gotos(); - begin - scalar p, r1, w, r; - p := 0; - for each x in hashcontents goto_cache do - if not numberp car x then << - if !*verbose then - for each xx in cdr x do << - prin car xx; ttab 10; lalr_prin_symbol car x; - princ " GOTO state "; prin cdr xx; terpri() >>; - r1 := (get(car x, 'non_terminal_code) . p) . r1; - if cdr x then << - w := lalr_most_common_dest cdr x; - for each xx in cdr x do if not (cdr xx = w) then << - r := xx . r; - p := p + 1 >>; - r := ((-1) . w) . r; - p := p + 1 >> >>; - goto_index := mkvect16 length non_terminals; - goto_old_state := mkvect16 p; - goto_new_state := mkvect16 p; - for each x in r1 do putv16(goto_index, car x, cdr x); - while p > 0 do << - p := p - 1; - putv16(goto_old_state, p, caar r); - putv16(goto_new_state, p, cdar r); - r := cdr r >>; - princ "goto_index: "; print goto_index; - princ "goto_old_state: "; print goto_old_state; - princ "goto_new_state: "; print goto_new_state - end; - -% A main driver function that performs all the steps involved -% in building parse tables for a given grammar. - -symbolic procedure lalr_construct_parser g; - begin - scalar c, cc, renamings; - lalr_set_grammar g; - c := lalr_items non_terminals; - renamings := nil; - for each i in c do cc := lalr_insert_core(i, cc); - lalr_rename_gotos(); - if !*verbose then lalr_print_items("Merged Items:", cc); - lalr_make_actions cc; - lalr_make_gotos(); - lalr_clean_up() - end; - -%============================================================================= - -% Now some test cases - -on time; - -% Here I set up a sample grammar -% S' -> S -% S -> CC { A1 } -% C -> cC { A2 } -% | d { A3 } -% (example 4.42 from Aho, Sethi and Ullman's Red Dragon book, with -% some dummy semantic actions added. Note that I do not need to insert -% the production S' -> S for myself since the analysis code will -% augment my grammar with it for me anyway. - -grammar := '((S ((C C) A1)) - (C (("c" C) A2) - (("d") A3)) - ); - -lalr_construct_parser grammar; - -% Example 4.46 from the Red Dragon - -g4_46 := '((S ((L "=" R) a1) - ((R) a2)) - (L (("*" R) a3) - ((id) a4)) - (R ((L) a5))); - -lalr_construct_parser g4_46; - - -% Now a much more complicated grammar - one that recognizes the syntax of -% RLISP. - -rlisp_grammar := '( - -(command (( cmnd sep ) action) - (( end sep ) action) - (( command cmnd sep ) action) - (( command end sep ) action) -) - - -(sep (( ";" ) action) - (( "$" ) action) -) - - -(proc_type (( symbolic ) action) - (( algebraic ) action) -) - - -(proc_qual (( expr ) action) - (( macro ) action) - (( smacro ) action) -) - - -(sym_list (( ")" ) action) - (( "," symbol sym_list ) action) -) - - -(infix (( setq ) action) - (( or ) action) - (( and ) action) - (( member ) action) - (( memq ) action) - (( "=" ) action) - (( neq ) action) - (( eq ) action) - (( geq ) action) - (( ">" ) action) - (( leq ) action) - (( "<" ) action) - (( freeof ) action) - (( "+" ) action) - (( "-" ) action) - (( "*" ) action) - (( "/" ) action) - (( "^" ) action) - (( "." ) action) -) - -(prefix (( not ) action) - (( "+" ) action) - (( "-" ) action) -) - - -(proc_head (( symbol ) action) - (( symbol symbol ) action) - (( symbol "(" ")" ) action) - (( symbol "(" symbol sym_list ) action) - (( prefix symbol ) action) - (( symbol infix symbol ) action) -) - - -(proc_def (( procedure proc_head sep cmnd ) action) - (( proc_type procedure proc_head sep cmnd ) action) - (( proc_qual procedure proc_head sep cmnd ) action) - (( proc_type proc_qual procedure proc_head sep cmnd ) action) -) - - -(rlistat (( rlistat ) action) - (( in ) action) - (( on ) action) -) - - -(rltail (( expr ) action) - (( expr "," rltail ) action) -) - - -(cmnd (( expr ) action) - (( rlistat rltail ) action) -) - - -(if_stmt (( if expr then cmnd else cmnd ) action) - (( if expr then cmnd ) action) -) - - -(for_update (( ":" expr ) action) - (( step expr until expr ) action) -) - - -(for_action (( do ) action) - (( sum ) action) - (( collect ) action) -) - - -(for_inon (( in ) action) - (( on ) action) -) - - -(for_stmt (( for symbol setq expr for_update for_action cmnd ) action) - (( for each symbol for_inon expr for_action cmnd ) action) - (( foreach symbol for_inon expr for_action cmnd ) action) -) - - -(while_stmt (( while expr do cmnd ) action) -) - - -(repeat_stmt (( repeat cmnd until expr ) action) -) - - -(return_stmt (( return ) action) - (( return expr ) action) -) - - -(goto_stmt (( goto symbol ) action) - (( go symbol ) action) - (( go to symbol ) action) -) - - -(group_tail (( rsect ) action) - (( sep rsect ) action) - (( sep cmnd group_tail ) action) -) - - -(group_expr (( lsect cmnd group_tail ) action) -) - - -(scalar_tail (( sep ) action) - (( "," symbol scalar_tail ) action) - (( "," integer scalar_tail ) action) -) - - -(scalar_def (( scalar symbol scalar_tail ) action) - (( integer symbol scalar_tail ) action) -) - - -(scalar_defs (( scalar_def ) action) - (( scalar_defs scalar_def ) action) -) - - -(block_tail (( end ) action) - (( cmnd end ) action) - (( symbol ":" block_tail ) action) - (( cmnd sep block_tail ) action) - (( sep block_tail ) action) -) - -(block_expr (( begin scalar_defs block_tail ) action) - (( begin block_tail ) action) -) - - -(lambda_vars (( sep ) action) - (( "," symbol lambda_vars ) action) -) - - -(lambda_expr (( lambda symbol lambda_vars cmnd ) action) - (( lambda "(" ")" sep cmnd ) action) - (( lambda "(" symbol sym_list sep cmnd ) action) -) - - -(expr (( rx0 ) action) - (( lx0 ) action) -) - - -(rx0 (( lx0 where symbol "=" rx1 ) action) - (( rx1 ) action) -) - - -(lx0 (( lx0 where symbol "=" lx1 ) action) - (( lx1 ) action) -) - - -(rx1 (( lx2 setq rx1 ) action) - (( rx2 ) action) -) - - -(lx1 (( lx2 setq lx1 ) action) - (( lx2 ) action) -) - - -(rx2tail (( rx3 ) action) - (( lx3 or rx2tail ) action) -) - -(rx2 (( lx3 or rx2tail ) action) - (( rx3 ) action) -) - - -(lx2tail (( lx3 ) action) - (( lx3 or lx2tail ) action) -) - -(lx2 (( lx3 or lx2tail ) action) - (( lx3 ) action) -) - - -(rx3tail (( rx4 ) action) - (( lx4 and rx3tail ) action) -) - -(rx3 (( lx4 and rx3tail ) action) - (( rx4 ) action) -) - - -(lx3tail (( lx4 ) action) - (( lx4 and lx3tail ) action) -) - -(lx3 (( lx4 and lx3tail ) action) - (( lx4 ) action) -) - - -(rx4 (( not rx4 ) action) - (( rx5 ) action) -) - - -(lx4 (( not lx4 ) action) - (( lx5 ) action) -) - - -(rx5 (( lx6 member ry6 ) action) - (( lx6 memq ry6 ) action) - (( lx6 "=" ry6 ) action) - (( lx6 neq ry6 ) action) - (( lx6 eq ry6 ) action) - (( lx6 geq ry6 ) action) - (( lx6 ">" ry6 ) action) - (( lx6 leq ry6 ) action) - (( lx6 "<" ry6 ) action) - (( lx6 freeof ry6 ) action) - (( rx6 ) action) -) - - -(lx5 (( lx6 member ly6 ) action) - (( lx6 memq ly6 ) action) - (( lx6 "=" ly6 ) action) - (( lx6 neq ly6 ) action) - (( lx6 eq ly6 ) action) - (( lx6 geq ly6 ) action) - (( lx6 ">" ly6 ) action) - (( lx6 leq ly6 ) action) - (( lx6 "<" ly6 ) action) - (( lx6 freeof ly6 ) action) - (( lx6 ) action) -) - - -(ry6 (( not ry6 ) action) - (( rx6 ) action) -) - - -(ly6 (( not ly6 ) action) - (( lx6 ) action) -) - - -(rx6tail (( ry6a ) action) - (( ly6a "+" rx6tail ) action) -) - -(rx6 (( lx6a "+" rx6tail ) action) - (( rx6a ) action) -) - - -(lx6tail (( ly6a ) action) - (( ly6a "+" lx6tail ) action) -) - -(lx6 (( lx6a "+" lx6tail ) action) - (( lx6a ) action) -) - - -(ry6a (( not ry6a ) action) - (( rx6a ) action) -) - - -(rx6a (( lx6a "-" ry7 ) action) - (( rx7 ) action) -) - - -(ly6a (( not ly6a ) action) - (( lx6a ) action) -) - - -(lx6a (( lx6a "-" ly7 ) action) - (( lx7 ) action) -) - - -(ry7 (( not ry7 ) action) - (( rx7 ) action) -) - - -(rx7 (( "+" ry7 ) action) - (( "-" ry7 ) action) - (( rx8 ) action) -) - - -(ly7 (( not ly7 ) action) - (( lx7 ) action) -) - - -(lx7 (( "+" ly7 ) action) - (( "-" ly7 ) action) - (( lx8 ) action) -) - - -(rx8tail (( ry9 ) action) - (( ly9 "*" rx8tail ) action) -) - -(rx8 (( lx9 "*" rx8tail ) action) - (( rx9 ) action) -) - - -(lx8tail (( ly9 ) action) - (( ly9 "*" lx8tail ) action) -) - -(lx8 (( lx9 "*" lx8tail ) action) - (( lx9 ) action) -) - - -(ry9 (( not ry9 ) action) - (( "+" ry9 ) action) - (( "-" ry9 ) action) - (( rx9 ) action) -) - - -(rx9 (( lx9 "/" ry10 ) action) - (( rx10 ) action) -) - - -(ly9 (( not ly9 ) action) - (( "+" ly9 ) action) - (( "-" ly9 ) action) - (( lx9 ) action) -) - - -(lx9 (( lx9 "/" ly10 ) action) - (( lx10 ) action) -) - - -(ly10 (( not ly10 ) action) - (( "+" ly10 ) action) - (( "-" ly10 ) action) - (( lx10 ) action) -) - - -(lx10 (( lx11 "^" ly10 ) action) - (( lx11 ) action) -) - - -(ry10 (( not ry10 ) action) - (( "+" ry10 ) action) - (( "-" ry10 ) action) - (( rx10 ) action) -) - - -(rx10 (( lx11 "^" ry10 ) action) - (( rx11 ) action) -) - - -(ry11 (( not ry11 ) action) - (( "+" ry11 ) action) - (( "-" ry11 ) action) - (( rx11 ) action) -) - - -(rx11 (( x12 "." ry11 ) action) - (( if_stmt ) action) - (( for_stmt ) action) - (( while_stmt ) action) - (( repeat_stmt ) action) - (( return_stmt ) action) - (( goto_stmt ) action) - (( lambda_expr ) action) - (( proc_type ) action) - (( proc_def ) action) - (( endstat ) action) -) - - -(ly11 (( not ly11 ) action) - (( "+" ly11 ) action) - (( "-" ly11 ) action) - (( lx11 ) action) -) - - -(lx11 (( x12 "." ly11 ) action) - (( x12 ) action) -) - - -(arg_list (( expr ")" ) action) - (( expr "," arg_list ) action) -) - - -(x12 (( x13 "[" expr "]" ) action) - (( x13 "(" ")" ) action) - (( x13 "(" expr "," arg_list ) action) - (( x13 x12 ) action) - (( x13 ) action) -) - - -(x13 (( symbol ) action) - (( number ) action) - (( string ) action) - (( quoted ) action) - (( backquoted ) action) - (( group_expr ) action) - (( block_expr ) action) - (( "(" expr ")" ) action) -) -)$ - - -% lalr_construct_parser rlisp_grammar; - - -end; - + +symbolic; +spool "lalr.log"; +on comp, backtrace; +unglobal '(!*raise); +fluid '(!*raise); + +%============================================================================= +% The file provides parser support for Lisp. The file contains three +% major sections. The first is a lexical analyser, which has been +% coded to support RLISP and Standard Lisp. Its interface is modelled after +% the one used with the lex/yacc combination commonly used with Unix. +% +% The second section is the generic part of an LR parser. It requires +% tables to tell it what actions to take, and calls the lexical analyser to +% obtain tokens. +% +% The final part is an LALR(1) parser generator, which can take the +% specification of a grammar and construct tables that direct the +% generic parser skeleton. +% +%============================================================================= + +% +% This is a lexical anaylser for use with RLISP. Its interface is +% styles after the one needed by yacc, in that it exports a function +% called yylex() that returns as a value a numeric category code, but +% sets a variable yylval to hold further information about the token +% just parsed. Single character objects are coded as their (ASCII?) code +% [leaving this code non-portable to machines with other encodings?]. +% Other things must have been given 'lex_code properties indicate the +% associated category code. This lexer handles ' and ` as special prefix +% characters that introduce Lisp-stype s-expressions. and it knows about +% RLISP-style comments and a few diphthongs. It also supports some +% simple preprocessor directives. +% +% Arthur Norman. April 1995 + + +fluid '(!*raise !*lower !*echo); +global '(lex_char yylval last64 last64p which_line); + +% I keep a circular buffer with the last 64 characters that have been +% read. Initially the buffer contains NILs rather than characters, so I can +% tell when it is only partially filled. + +smacro procedure yyreadch(); + << last64p := last64p + 1; + if last64p = 64 then last64p := 0; + lex_char := readch(); + if lex_char = !$eol!$ then which_line := which_line + 1; + putv(last64, last64p, lex_char); + lex_char >>; + +symbolic procedure yyerror msg; + begin + scalar c; + terpri(); + princ "+++++ Parse error at line "; prin which_line; princ ":"; + if atom msg then msg := list msg; + for each s in msg do << princ " "; princ s >>; + terpri(); + for i := 1:64 do << + last64p := last64p + 1; + if last64p = 64 then last64p := 0; + c := getv(last64, last64p); + if c = !$eof!$ then princ "" + else if not (c = nil) then princ c >>; + if not (c = !$eol!$) then terpri() + end; + +% Before a succession of calls to yylex() it is necessary to +% ensure that lex_char is set suitably and that the circular buffer +% used to store characters for error messages is ready for use. + +symbolic procedure start_parser(); + << last64 := mkvect 64; + last64p := 0; + which_line := 1; + yyreadch() >>; + +% +% The following version of YYLEX provides RLISP with a facility for +% conditional compilation. The protocol is that text is included or +% excluded at the level of tokens. Control by use of new reserved +% tokens !#if, !#else and !#endif. These are used in the form: +% !#if (some Lisp expression for use as a condition) +% ... RLISP input ... +% !#else +% ... alternative RLISP input ... +% !#endif +% +% The form +% !#if C1 ... !#elif C2 ... !#elif C3 ... !#else ... !#endif +% is also supported. +% +% Conditional compilation can be nested. If the Lisp expression used to +% guard a condition causes an error it is taken to be a FALSE condition. +% It is not necessary to have an !#else before !#endif if no alternative +% text is needed. Although the examples here put !#if etc at the start of +% lines this is not necessary (though it may count as good style?). Since +% the condtion will be read using RLISPs own list-reader there could be +% condtional compilation guarding parts of it - the exploitation of that +% possibility is to be discouraged! +% +% Making the condition a raw Lisp expression makes sure that parsing it +% is easy. It makes it possible to express arbitrary conditions, but it is +% hoped that most conditions will not be very elaborate - things like +% !#if (not (member 'csl lispsystem!*)) +% error(); +% !#else +% magic(); +% !#endif +% or +% !#if debugging_mode % NB if variable is unset that counts as nil +% print "message"; % so care should be taken to select the most +% !#endif % useful default sense for such tests +% should be about as complicated as reasonable people need. +% +% Two further facilities are provided: +% !#eval (any lisp expression) +% causes that expression to be evaluated at parse time. Apart from any +% side-effects in the evaluation the text involved is all ignored. It is +% expected that this will only be needed in rather curious cases, for instance +% to set system-specific options for a compiler. +% +% !#define symbol value +% where the value should be another symbol, a string or a number, causes +% the first symbol to be mapped onto the second value wherever it occurs in +% subsequent input. No special facility for undoing the effect of a +% !#define is provided, but the general-purpose !#eval could be used to +% remove the '!#define property that is involved. +% +% NOTE: The special symbols !#if etc are NOT recognised within Lisp +% quoted expressions, so test like the following will be +% ineffective: +% a := '( +% P +% !#if q_is_wanted +% Q +% !#endif +% Q); +% but on the other hand code like +% if sym = '!#if then ... +% behaves the way that had probably been wanted. Unlike the C +% preprocessor, this system recognizes directives within rather than +% just at the start of lines. + + +symbolic procedure yylex(); + begin + scalar w, done; +% I take a rather robust view here - words that are intended to be used as +% keywords may not be written with included escape characters. Thus for +% instance this lexer will view "be!gin" or "!begin" as being a simple +% symbol and NOT being the keyword "begin". + w := lex_basic_token(); +% The "while not done" loop is so that I can restart the scan after seeing +% a pre-processor directive such as !#if. + while not done do << +% The word "COMMENT" introduces a comment that terminates at the next ";" +% or "$". + while yylval = 'comment and + w = '!:symbol_or_keyword do << + while not (lex_char = '!; or lex_char = '!$) do + yyreadch(); + yyreadch(); + w := lex_basic_token() >>; +% If a word was spelt out directly (without any escape characters in it) it +% may be a keyword - if it is, then convert it here. + if w = '!:symbol_or_keyword then << + if w := get(yylval, '!#define) then << + yylval := cdr w; + w := car w >> + else << + if done := get(yylval, 'lex_code) then w := done + else if flagp(yylval, 'rlis) then + w := get('rlistat, 'lex_code) + else if flagp(yylval, 'endstat) then + w := get('endstat, 'lex_code) + else w := get('!:symbol, 'lex_code); + done := t >> >> +% A word with escapes in might be a pre-processor directive. + else if w = '!:symbol then << + if yylval eq '!#if then << + read_s_expression(); + w := lex_conditional yylval >> + else if yylval eq '!#else or + yylval eq '!#elif then << + yylval := nil; + w := lex_skipping(w, nil) >> + else if yylval eq '!#endif then w := lex_basic_token() + else if yylval eq '!#eval then << + read_s_expression(); + errorset(yylval, nil, nil); + w := lex_basic_token() >> + else if yylval eq '!#define then << + read_s_expression(); + w := yylval; % Ought to be a symbol + done := read_s_expression(); + if idp w then put(w, '!#define, done . yylval); + w := lex_basic_token(); + done := nil >> + else << + w := get('!:symbol, 'lex_code); + done := t >> >> + else if numberp w then << +% Now gobble up extra characters for multi-character operators (eg ">="). +% Note that I only look one character ahead here. + while done := atsoc(lex_char, get(yylval, 'lex_dipthong)) do << + w := cdr done; + yylval := cdr w; + w := get(car w, 'lex_code); + yyreadch() >>; + if done := get(yylval, '!#define) then << + yylval := cdr done; + w := car done; + done := nil >> + else done := t >> + else << + done := t; + w := get(w, 'lex_code) >> >>; + return w + end; + + + +% If, when reading ordinary text, I come across the token !#if I read +% the expression following. If that evaluates to TRUE I just keep on +% on reading. So the sequence "!#if t" is in effect ignored. Then +% if later on I just ignore an "!#endif" all will be well. If on the other +% hand the expression evaluates to NIL (or if evaluation fails), I will +% call lex_skipping() to discard more tokens (up to and including +% the next "!#else", "!#elif t" or "!endif"). + +symbolic procedure lex_conditional x; + begin + scalar w; + w := lex_basic_token(); + x := errorset(x, nil, nil); + if errorp x or null car x then return lex_skipping(w, nil) + else return w + end; + +% I call lex_skipping when I find "!#if nil" or "!#else" or "!#elif" +% that is processed. When a top-level "!#else" or "!#elif" is found it +% is discarded before calling lex_skipping, since it must follow a +% successful "!#if" and hence introduce material to be thrown away. + +symbolic procedure lex_skipping(w, x); + begin + scalar done; +% In this code x keep track of the depth of testing of "!#if" constructions + while not done do << + if w = 0 then done := t % End of file + else << + if w = '!:symbol then << + if yylval = '!#endif then << + if null x then done := t + else x := cdr x >> + else if yylval = '!#if then x := nil . x + else if yylval = '!#else and null x then done := t + else if yylval = '!#elif and null x then << + read_s_expression(); + done := errorset(yylval, nil, nil); + if errorp done or null car done then done := nil >> >>; + w := lex_basic_token() >> >>; + return w + end; + + + +% In some cases RLISP operators are made up out of two (or more) characters. +% I map '**' onto '^', and >=, <= onto GEQ and LEQ. +% ":=" becomes SETQ. I turn << and >> onto symbols that can not be +% read directly (!:lsect and !:rsect). +% This means that the system that sets up lex_code properties had really +% better make sure that it gives setq, geq, leq, !:rsect and !:lsect values. + +put('!*, 'lex_dipthong, '((!* !^ . !^))); +put('!:, 'lex_dipthong, '((!= setq . setq))); +put('!>, 'lex_dipthong, '((!= geq . geq), + (!> !:rsect . !:rsect))); +put('!<, 'lex_dipthong, '((!= leq . leq), + (!< !:lsect . !:lsect))); + +put('!^, 'lex_code, char!-code '!^); + + +% lex_basic_token() will read the next token from the current input stream and +% leave a value in yylval to show what was found. It does not handle the +% word "comment", nor does it consolidate things like ':' followed by '=' into +% ':='. Those steps are left to yylex(). But lex_basic_token() does recognize +% the quote prefix, as in '(lisp expression). The return value is numeric +% for single-character tokens, but otherwise a descriptive symbol. + +% Some people would consider the Lisp dialect that I am using here to be +% significantly flawed, in that I need to build symbols, numbers and +% strings up as lists, and then use COMPRESS to make the real objects. The +% CONS operations involved can be seen as an overhead, and going back to +% something like the VERY old-fashioned clearbuff/pack/boffo world might +% avoid that. + +symbolic procedure lex_basic_token(); + begin + scalar r, w; +% First skip over whitespace. Note that at some stage in the future RLISP +% may want to make newlines significant and partially equivalent to +% semicolons, but that is not supported at present. + while lex_char = '! or lex_char = !$eol!$ or + (lex_char = '!% and << + while not (lex_char = !$eol!$ or lex_char = !$eof!$) do + yyreadch(); + t >>) do yyreadch(); +% Symbols start with a letter or an escaped character and continue with +% letters, digits, underscores and escapes. + if liter lex_char or + (lex_char = '!! and begin + scalar !*raise, !*lower; % Rebind !*raise & !*lower to avoid.. + r := lex_char . r; % case folding when the next character.. + yyreadch(); % is read. + return (w := t) end) then << + r := lex_char. r; + while liter(yyreadch()) or + digit lex_char or + lex_char = '!_ or + (lex_char = '!! and begin + scalar !*raise, !*lower; + r := lex_char . r; + yyreadch(); + return (w := t) end) do + r := lex_char . r; +% If there was a '!' in the word I will never treat it as a keyword. + yylval := compress reversip r; + return if w then '!:symbol else '!:symbol_or_keyword >> +% Numbers are either integers or floats. A floating point number is +% indicated by either a point "." or an exponent marker "e". In the code +% here I keep a flag (in w) to indicate if I had a floating or integer +% value, but in the end I ignore this and hand back the lexical category +% :number in both cases. + else if digit lex_char then << + r := list lex_char; + while digit (yyreadch()) do r := lex_char . r; + if lex_char = '!. then << + w := t; % Flag to indicate floating point + r := lex_char . r; + while digit (yyreadch()) do r := lex_char . r >>; +% I permit the user to write the exponent marker in either case. + if lex_char = '!e or lex_char = '!E then << +% If the input as 1234E56 I expand it as 1234.0E56 + if not w then r := '!0 . '!. . r; + w := t; + r := '!e . r; + yyreadch(); + if lex_char = '!+ or lex_char = '!- then << + r := lex_char . r; + yyreadch() >>; +% If there is no digit written after "E" I insert a zero. Thus overall the +% input 17E gets treated as 17.0E0 + if not digit lex_char then r := '!0 . r + else << + r := lex_char . r; + while digit (yyreadch()) do r := lex_char . r >> >>; + yylval := compress reversip r; + return '!:number >> +% Strings are enclosed in double-quotes, and "abc""def" is a string with +% a double-quote mark within it. Note no case folding on characters in a +% string. + else if lex_char = '!" then << + begin + scalar !*raise, !*lower; + repeat << + r := lex_char . r; + while not ((yyreadch()) = '!") do r := lex_char . r; + r := lex_char . r; + yyreadch() >> until not (lex_char = '!"); + end; + yylval := compress reversip r; + return '!:string >> +% "'" and "`" introduce Lisp syntax S-expressions + else if lex_char = '!' then << + yyreadch(); + read_s_expression(); + yylval := list('quote, yylval); + return '!:list >> + else if lex_char = '!` then << + yyreadch(); + read_s_expression(); + yylval := list('backquote, yylval); + return '!:list >> + else << + yylval := lex_char; +% I take special notice of end of file, since it is fairly drastic. +% In particular I do not attempt to advance lex_char beyond it. So I do +% TWO things here: I avoid advancing the input, and I return the code 0 +% as an end-of-file indication. + if yylval = !$eof!$ then return 0 + else << + yyreadch(); + return char!-code yylval >> >> + end; + +% +% I use a hand-written recursive descent parser for Lisp S-expressions +% mainly because the syntax involved is so VERY simple. A rough sketch of +% the syntax required is given here, but in reality (in part because I do +% not want to have to report syntax errors) I implement a more liberal +% syntax, especially as it relates to dotted-pair notation. This of course +% is one of the natural dangers in using recursive descent... the syntax +% actually parsed is only properly defined by direct reference to the code. +% + +% s_tail = ")" | +% "." s_expr ")" | +% s_expr s_tail; +% +% s_vectail = "]" | +% s_expr s_vectail; +% +% s_expr = symbol | +% number | +% string | +% "(" s_tail | +% "[" s_vectail | +% "'" s_expr | +% "`" s_expr | +% "," s_expr | +% ",@" s_expr; + +global '(dot_char rpar_char rsquare_char); + +dot_char := char!-code '!.; +rpar_char := char!-code '!); +rsquare_char := char!-code '!]; + +symbolic procedure read_s_expression(); + << +% At the start of an S-expression I want to check for the characters +% "(", "[" and ",". Thus I need to skip whitespace. + while lex_char = '! or lex_char = '!$eol!$ do yyreadch(); + if lex_char = '!( then begin + scalar r, w, w1; + yyreadch(); + w := read_s_expression(); + while not (w = rpar_char or w = dot_char or w = 0) do << + r := yylval . r; +% Note that at the end of the list read_s_expression() will read the ")" +% as a token. + w := read_s_expression() >>; + if not w = dot_char then yylval := reversip r + else << + read_s_expression(); % Thing after the "." + w := yylval; +% Reverse the list putting a dotted item on the end. + while r do << + w1 := cdr r; + rplacd(r, w); + w := r; + r := w1 >>; + yylval := w; +% I will be somewhat liberal about syntactic problems with dotted pair +% notation, since it is unclear how I can usefully report or repair errors. + while lex_char = '! or lex_char = '!$eol!$ do + yyreadch(); +% When I find a ")" I do not read beyond it immediately, but reset lex_char +% to whitespace. This may help prevent unwanted hangups in interactive use. + if lex_char = '!) then lex_char := '! >>; + return '!:list end +% "[" introduces a simple vector. + else if lex_char = '![ then begin + scalar r, w, w1; + yyreadch(); + w := read_s_expression(); + w1 := -1; + while not (w = rsquare_char or w = 0) do << + r := yylval . r; + w1 := w1 + 1; + w := read_s_expression() >>; +% Create a vector of the correct size and copy information into it. + w := mkvect w1; + r := reversip r; + w1 := 0; + while r do << + putv(w, w1, car r); + w1 := w1 + 1; + r := cdr r >>; + yylval := w; + return '!:list end +% I spot "," and ",@" here, and should wonder if I should (a) police that +% they are only expected to make sense within the scope of a "`" and (b) +% whether I ought to expand them in terms of LIST, CONS, APPEND etc here. +% For now I just hand back markers that show where they occured. + else if lex_char = '!, then << + yyreadch(); + if lex_char = '!@ then << + yyreadch(); + read_s_expression(); + yylval := list('!,!@, yylval) >> + else << + read_s_expresssion(); + yylval := list('!,, yylval) >>; + 'list >> +% Care with ")" and "]" not to read ahead further than is essential. + else if lex_char = '!) or lex_char = '!] or lex_char = '!. then << + yylval := lex_char; + lex_char := '! ; + char!-code yylval >> +% In most cases (including "'" and "`") I just hand down to read a token. +% This covers the cases of symbols, numbers and strings. + else lex_basic_token() >>; + + + +%============================================================================= + +% Here I have a general-purpose LR(1) parser skeleton. This needs to +% have a source of tokens, and some tables that will direct its actions. + +% The format of the tables required by this code will be a little curious, +% mainly because they represent some attempt to compact the information that +% is needed. Note that the CSL functions mkvect16, putv16, getv16 are +% somewhat similar to the regular mkvect, putv and getv, but may be used +% if the vector contents will always be 16-bit fixnums. + +global '(!*verbose); + +!*verbose := t; % How much will the parset-generator print? + +global '(goto_index goto_old_state goto_new_state); + +% For each terminal I have a pointer (stored in goto_index) into +% a pair of vectors, goto_old_state and goto_new_state. The first of these +% holds states that I might be in, and the second holds the ones I must +% move into after a reduction has been performed. In the goto_old_state +% table the value "-1" is taken to match any state that I am attempting +% to look up. Thus it can be used to terminate a segment of the table. I am +% entitled to let undefined locations in the goto table respond with +% any value that just happens. + +smacro procedure get_goto(state, non_terminal); + << w1 := getv16(goto_index, non_terminal); + while not (((w2 := getv16(goto_old_state, w1)) = -1) or + w2 = state) do w1 := w1 + 1; + getv16(goto_new_state, w1) >>; + +global '(action_index, action_terminal action_result); + +% In a rather similar way, actions are found via an association-list +% like look-up in a table. In this table a strictly positive number n stands +% for (SHIFT n) [observe that if I reserve zero as the number of the +% initial state of my augmented grammar I can never need to shift into +% state 0]. The value 0 in the table represents ACCEPT. This leaves +% nagative values to cover reductions and error cases. + +smacro procedure get_action(state, terminal); + << w1 := getv16(action_index, state); + while not (((w2 := getv16(action_terminal, w1)) = -1) or + w2 = terminal) do w1 := w1 + 1; + getv(action_result, w1) >>; + +global '(action_first_error action_error_messages); + +global '(action_fn action_A action_n); + +symbolic procedure yyparse(); + begin + scalar sym_stack, state_stack, next_input, w, w1, w2; + state_stack := list 0; % Note that state 0 must be the initial one. + start_parser(); + next_input := yylex(); + while not (w := get_action(car state_stack, next_input)) = 0 do + if w > 0 then << + sym_stack := next_input . sym_stack; + state_stack := cadr w . state_stack; + next_input := yylex() >> + else begin + scalar A, n, action; + w := - (w + 1); + if w < action_first_error then << + action := getv(action_fn, w); + n := getv8(action_n, w); + A := getv16(action_A, w); +% I am now reducing by "A -> beta { action() }" where beta has n items + w := nil; + for i := 1:n do << + w := car sym_stack . w; + sym_stack := cdr sym_stack; + state_stack := cdr state_stack >>; + w := reversip w; + if action then w := apply1(action, w) + else w := A . w; + sym_stack := w . sym_stack; + state_stack := get_goto(car state_stack, A) >> + else << + w := w - action_first_error; + yyerror getv(action_error_messages, w); +% The next activity must result in the loop ending... + state_stack := list 0; + sym_stack := '(error); + next_input := 0 >> + end; + return car sym_stack + end; + +%============================================================================= +% +% A grammar is represented as a list of rules. A rule +% sym : x y z { p q r } +% | x y z { p q r } +% ; +% maps onto the list +% (sym ((x y z) p q r) +% ((x y z) p q r)) +% and items on the right hand side can be symbols or strings. Strings +% stand for terminals. Symbols that are mentioned on a left hand side of +% a production are non-terminals, others are considered to be terminals +% supported by the lexer. +% +% ***** I am still working out what to do with the "semantic actions". + +global '(terminals non_terminals symbols goto_cache action_map); + +smacro procedure lalr_productions x; + get(x, 'produces); + +smacro procedure lalr_set_productions(x, y); + put(x, 'produces, y); + +symbolic procedure lalr_prin_symbol x; + if x = 0 then princ "$" + else if x = nil then princ "" + else if x = '!. then princ "." + else if numberp x and rassoc(x, terminals) then + prin car rassoc(x, terminals) + else if stringp x then prin x + else for each c in explode2uc x do princ c; + +symbolic procedure lalr_display_symbols(); + begin + princ "Terminal symbols are:"; terpri(); + for each x in terminals do << + princ " "; prin car x; + princ ":"; prin cdr x >>; + terpri(); + princ "Non-terminal symbols are:"; terpri(); + for each x in non_terminals do begin + scalar w; + princ "["; prin get(x, 'non_terminal_code); princ "]"; + lalr_prin_symbol x; + w := ":"; + for each y in lalr_productions x do << + ttab 20; princ w; w := "|"; + for each z in car y do << princ " "; lalr_prin_symbol z >>; + if posn() > 48 then terpri(); + ttab 48; + princ "{"; + for each z in cdr y do << princ " "; prin z >>; + princ " }"; + terpri() >>; + ttab 20; + princ ";"; + terpri() end; + terpri(); + end; + +symbolic procedure lalr_print_action_map(); + begin + princ "Action map:"; terpri(); + for each x in action_map do << + prin cdr x; princ ":"; ttab 12; prin car x; terpri() >> + end; + +symbolic procedure lalr_set_grammar g; + begin + scalar name, vals, tnum, w; + terminals := non_terminals := symbols := nil; + tnum := 0; +% I will start by augmenting the grammar with an initial production... + g := list('s!', list list caar g) . g; + for each x in g do << + name := car x; vals := cdr x; + if name member non_terminals then + vals := append(vals, lalr_productions name) + else non_terminals := name . non_terminals; + for each vv in cdr x do + for each v in car vv do << + if stringp v or numberp v then << + if not assoc(v, terminals) then + terminals := (v . (tnum := tnum+1)) . terminals >> + else if not (v member symbols) then symbols := v . symbols >>; + lalr_set_productions(name, vals) >>; + for each name in non_terminals do symbols := delete(name, symbols); + for each v in symbols do terminals := (v . (tnum := tnum+1)) . terminals; +% I reverse the list of non-terminals here so that the starting symbol +% remains as the first item. + non_terminals := reversip non_terminals; + tnum := -1; + for each v in non_terminals do + put(v, 'non_terminal_code, tnum := tnum+1); + symbols := append(non_terminals, for each x in terminals collect cdr x); + goto_cache := mkhash(length non_terminals, 1, 1.5); + if !*verbose then lalr_display_symbols(); +% Map all terminals onto numeric codes. + for each x in non_terminals do + lalr_set_productions(x, + for each y in lalr_productions x collect + sublis(terminals, car y) . cdr y); +% Map all actions onto numeric codes, such that identical actions all have the +% same code + action_map := nil; + tnum := -1; + for each x in non_terminals do + for each a in lalr_productions x do << + w := assoc(cdr a, action_map); + if null w then << + w := cdr a . (tnum := tnum + 1); + action_map := w . action_map >>; + rplacd(a, list cdr w) >>; + action_map := reversip action_map; + if !*verbose then lalr_print_action_map(); + lalr_calculate_first non_terminals; + end; + +symbolic procedure lalr_clean_up(); + begin + for each x in terminals do << + remprop(x, 'produces); + remprop(x, 'lalr_first); + remprop(x, 'non_terminal_code) >>; + terminals := non_terminals := symbols := nil; + goto_cache := action_map := nil + end; + +symbolic procedure lalr_action(lhs, rhs); + cdr assoc(rhs, lalr_productions lhs); + +symbolic procedure lalr_print_firsts g; + begin + princ "FIRST sets for each non-terminal:"; terpri(); + for each x in g do << + lalr_prin_symbol x; + princ ": "; + ttab 15; + for each y in get(x, 'lalr_first) do << + princ " "; lalr_prin_symbol y >>; + terpri() >> + end; + +symbolic procedure lalr_calculate_first g; + begin + scalar w, y, z, done; + for each x in g do + if assoc(nil, lalr_productions x) then put(x, 'lalr_first, '(nil)); + repeat << + done := nil; + for each x in g do << + z := get(x, 'lalr_first); + for each y1 in lalr_productions x do << + y := car y1; + while y and + not numberp y + and (nil member (w := get(car y, 'lalr_first))) do << + z := union(w, z); + y := cdr y >>; + if null y then nil + else if numberp car y then z := union(list car y, z) + else z := union(get(car y, 'lalr_first), z) >>; + if not (z = get(x, 'lalr_first)) then done := t; + put(x, 'lalr_first, z) >> + >> until not done; + if !*verbose then lalr_print_firsts g; + return nil + end; + +symbolic procedure lalr_first l; + begin + scalar r, w; + while l and + not numberp car l and + (nil member (w := get(car l, 'lalr_first))) do << + r := union(delete(nil, w), r); + l := cdr l >>; + if null l then r := nil . r + else if numberp car l then r := union(list car l, r) + else r := union(w, r); + return r + end; + + +% The next few procedures are as documented in Figure 4.38 of Red Dragon + +symbolic procedure lalr_print_items(heading, cc); + begin + princ heading; + terpri(); + for each y in cc do << + princ "Item number "; prin cdr y; terpri(); + for each x in sort(car y, function orderp) do << + lalr_prin_symbol caar x; princ " ->"; + for each y in cdar x do << princ " "; lalr_prin_symbol y >>; + princ " : "; + lalr_prin_symbol cadr x; + terpri() >>; + for each x in hashcontents goto_cache do + for each xx in cdr x do + if car xx = cdr y then << + ttab 10; lalr_prin_symbol car x; + princ " GOTO state "; prin cdr xx; terpri() >> >> + end; + +symbolic procedure lalr_items g; + begin + scalar c, val, done, w, w1, w2, n; + val := lalr_productions 's!'; + if cdr val then error(0, "Starting state must only reduce to one thing") + else val := caar val; + n := 0; + c := list (lalr_closure list list(('s!' . '!. . val), 0) . n); + repeat << + done := nil; + for each i in c do + for each x in symbols do + if w := lalr_goto(car i, x) then << + w1 := assoc(w, c); + if w1 then << + w2 := gethash(x, goto_cache); + if not assoc(cdr i, w2) then + puthash(x, goto_cache, (cdr i . cdr w1) . w2) >> + else << + c := (w . (n := n + 1)) . c; + puthash(x, goto_cache, + (cdr i . n) . gethash(x, goto_cache)); + done := t >> >> + >> until not done; + c := reversip c; % So that item numbers come out in nicer order. + if !*verbose then lalr_print_items("LR(1) Items:", c); + return c + end; + +symbolic procedure lalr_closure i; + begin + scalar pending, a, rule, tail, done, ff, w; + pending := i; + while pending do << + ff := car pending; % [(A -> alpha . B beta), a] + pending := cdr pending; + rule := car ff; a := cadr ff; tail := cdr ('!. member rule); + if tail and not numberp car tail then << + ff := lalr_first append(cdr tail, list a); + for each p in lalr_productions car tail do + for each b in ff do << + w := list(car tail . '!. . car p, b); +% It might be better to store items as hash tables, since then the +% member-check here would be much faster. + if not (w member i) then << + i := w . i; + pending := w . pending >> >> >> >>; + return i + end; + +symbolic procedure lalr_move_dot(z, x); + begin + scalar r; + while not (car z = '!.) do << + r := car z . r; + z := cdr z >>; + z := cdr z; + if not (z and car z = x) then return nil; + z := car z . '!. . cdr z; + while r do << + z := car r . z; + r := cdr r >>; + return z + end; + +symbolic procedure lalr_goto(i, x); + begin + scalar j, w; + for each z in i do << + w := lalr_move_dot(car z, x); + if w then j := list(w, cadr z) . j >>; + return lalr_closure j + end; + +symbolic procedure lalr_cached_goto(i, x); + cdr assoc(i, gethash(x, goto_cache)); + +% Next part of Algorithm 4.11 from the Red Dragon + +symbolic procedure lalr_remove_duplicates x; + begin + scalar r; + if null x then return nil; + x := sort(x, function orderp); + r := list car x; + x := cdr x; + while x do << + if not (car x = car r) then r := car x . r; + x := cdr x >>; + return r + end; + +symbolic procedure lalr_core i; + lalr_remove_duplicates for each x in car i collect car x; + +symbolic procedure lalr_same_core(i1, i2); + lalr_core i1 = lalr_core i2; + +% cc is a list of items, while i is a single item. If cc already contains +% an item with the same core as I then merge i into that, and adjust any +% goto records either out of or into i to refer now to the thing merged +% with. + +fluid '(renamings); + +symbolic procedure lalr_insert_core(i, cc); + if null cc then list i + else if lalr_same_core(i, car cc) then << + renamings := (i . cdar cc) . renamings; + (union(car i, caar cc) . cdar cc) . cdr cc >> + else car cc . lalr_insert_core(i, cdr cc); + +symbolic procedure lalr_rename_gotos(); + begin + scalar w; + for each x in non_terminals do << + w := sublis(renamings, gethash(x, goto_cache)); + puthash(x, goto_cache, lalr_remove_duplicates w) >> + end; + +% Part of Algorithm 4.10 of the Red Dragon + +symbolic procedure lalr_print_actions action_table; + begin + scalar w; + princ "Actions:"; terpri(); + for each x in action_table do + for each xx in cdr x do << + prin car x; ttab 20; + lalr_prin_symbol car xx; ttab 40; + w := cadr xx; + if eqcar(w, 'reduce) then << + princ "reduce "; + lalr_prin_symbol caadr w; + princ " ->"; + for each v in cdadr w do << princ " "; lalr_prin_symbol v >>; + princ " {"; + for each v in caddr w do << princ " "; prin v >>; + princ " }"; + terpri() >> + else << prin w; terpri() >> >> + end; + +symbolic procedure lalr_make_actions c; + begin + scalar action_table, aa, j, w; + for each i in c do << + aa := nil; + for each r in car i do << + w := cdr ('!. member cdar r); + if w and numberp car w then << + j := lalr_cached_goto(cdr i, car w); + aa := list(car w, list('shift, j)) . aa >> + else if null w and not (caar r = 's!') then << + w := reverse cdr reverse car r; + aa := + list(cadr r, list('reduce, w, lalr_action(car w, cdr w))) . + aa >> + else if null w and caar r = 's!' then + aa := list(0, 'accept) . aa >>; + action_table := (cdr i . lalr_remove_duplicates aa) . action_table >>; + action_index := mkvect16 caar action_table; + action_table := reversip action_table; + if !*verbose then lalr_print_actions action_table; + j := 0; w := nil; + for each x in action_table do << + putv16(action_index, car x, j); + aa := lalr_lay_out_actions cdr x; + while aa do << + w := (0 . 0) . w; + j := j + 1 >> >>; + action_terminal := mkvect16 j; + action_result := mkvect16 j; + while j > 0 do << + j := j - 1; + putv16(action_terminal, j, caar w); + putv16(action_result, j, cdar w); + w := cdr w >> + end; + +symbolic procedure lalr_most_common_dest p; + begin + scalar r, w; + for each x in p do + if (w := assoc(cdr x, r)) then rplacd(w, cdr w + 1) + else r := (cdr x . 1) . r; + w := car r; + for each x in cdr r do if cdr x > cdr w then w := x; + return car w + end; + +symbolic procedure lalr_make_gotos(); + begin + scalar p, r1, w, r; + p := 0; + for each x in hashcontents goto_cache do + if not numberp car x then << + if !*verbose then + for each xx in cdr x do << + prin car xx; ttab 10; lalr_prin_symbol car x; + princ " GOTO state "; prin cdr xx; terpri() >>; + r1 := (get(car x, 'non_terminal_code) . p) . r1; + if cdr x then << + w := lalr_most_common_dest cdr x; + for each xx in cdr x do if not (cdr xx = w) then << + r := xx . r; + p := p + 1 >>; + r := ((-1) . w) . r; + p := p + 1 >> >>; + goto_index := mkvect16 length non_terminals; + goto_old_state := mkvect16 p; + goto_new_state := mkvect16 p; + for each x in r1 do putv16(goto_index, car x, cdr x); + while p > 0 do << + p := p - 1; + putv16(goto_old_state, p, caar r); + putv16(goto_new_state, p, cdar r); + r := cdr r >>; + princ "goto_index: "; print goto_index; + princ "goto_old_state: "; print goto_old_state; + princ "goto_new_state: "; print goto_new_state + end; + +% A main driver function that performs all the steps involved +% in building parse tables for a given grammar. + +symbolic procedure lalr_construct_parser g; + begin + scalar c, cc, renamings; + lalr_set_grammar g; + c := lalr_items non_terminals; + renamings := nil; + for each i in c do cc := lalr_insert_core(i, cc); + lalr_rename_gotos(); + if !*verbose then lalr_print_items("Merged Items:", cc); + lalr_make_actions cc; + lalr_make_gotos(); + lalr_clean_up() + end; + +%============================================================================= + +% Now some test cases + +on time; + +% Here I set up a sample grammar +% S' -> S +% S -> CC { A1 } +% C -> cC { A2 } +% | d { A3 } +% (example 4.42 from Aho, Sethi and Ullman's Red Dragon book, with +% some dummy semantic actions added. Note that I do not need to insert +% the production S' -> S for myself since the analysis code will +% augment my grammar with it for me anyway. + +grammar := '((S ((C C) A1)) + (C (("c" C) A2) + (("d") A3)) + ); + +lalr_construct_parser grammar; + +% Example 4.46 from the Red Dragon + +g4_46 := '((S ((L "=" R) a1) + ((R) a2)) + (L (("*" R) a3) + ((id) a4)) + (R ((L) a5))); + +lalr_construct_parser g4_46; + + +% Now a much more complicated grammar - one that recognizes the syntax of +% RLISP. + +rlisp_grammar := '( + +(command (( cmnd sep ) action) + (( end sep ) action) + (( command cmnd sep ) action) + (( command end sep ) action) +) + + +(sep (( ";" ) action) + (( "$" ) action) +) + + +(proc_type (( symbolic ) action) + (( algebraic ) action) +) + + +(proc_qual (( expr ) action) + (( macro ) action) + (( smacro ) action) +) + + +(sym_list (( ")" ) action) + (( "," symbol sym_list ) action) +) + + +(infix (( setq ) action) + (( or ) action) + (( and ) action) + (( member ) action) + (( memq ) action) + (( "=" ) action) + (( neq ) action) + (( eq ) action) + (( geq ) action) + (( ">" ) action) + (( leq ) action) + (( "<" ) action) + (( freeof ) action) + (( "+" ) action) + (( "-" ) action) + (( "*" ) action) + (( "/" ) action) + (( "^" ) action) + (( "." ) action) +) + +(prefix (( not ) action) + (( "+" ) action) + (( "-" ) action) +) + + +(proc_head (( symbol ) action) + (( symbol symbol ) action) + (( symbol "(" ")" ) action) + (( symbol "(" symbol sym_list ) action) + (( prefix symbol ) action) + (( symbol infix symbol ) action) +) + + +(proc_def (( procedure proc_head sep cmnd ) action) + (( proc_type procedure proc_head sep cmnd ) action) + (( proc_qual procedure proc_head sep cmnd ) action) + (( proc_type proc_qual procedure proc_head sep cmnd ) action) +) + + +(rlistat (( rlistat ) action) + (( in ) action) + (( on ) action) +) + + +(rltail (( expr ) action) + (( expr "," rltail ) action) +) + + +(cmnd (( expr ) action) + (( rlistat rltail ) action) +) + + +(if_stmt (( if expr then cmnd else cmnd ) action) + (( if expr then cmnd ) action) +) + + +(for_update (( ":" expr ) action) + (( step expr until expr ) action) +) + + +(for_action (( do ) action) + (( sum ) action) + (( collect ) action) +) + + +(for_inon (( in ) action) + (( on ) action) +) + + +(for_stmt (( for symbol setq expr for_update for_action cmnd ) action) + (( for each symbol for_inon expr for_action cmnd ) action) + (( foreach symbol for_inon expr for_action cmnd ) action) +) + + +(while_stmt (( while expr do cmnd ) action) +) + + +(repeat_stmt (( repeat cmnd until expr ) action) +) + + +(return_stmt (( return ) action) + (( return expr ) action) +) + + +(goto_stmt (( goto symbol ) action) + (( go symbol ) action) + (( go to symbol ) action) +) + + +(group_tail (( rsect ) action) + (( sep rsect ) action) + (( sep cmnd group_tail ) action) +) + + +(group_expr (( lsect cmnd group_tail ) action) +) + + +(scalar_tail (( sep ) action) + (( "," symbol scalar_tail ) action) + (( "," integer scalar_tail ) action) +) + + +(scalar_def (( scalar symbol scalar_tail ) action) + (( integer symbol scalar_tail ) action) +) + + +(scalar_defs (( scalar_def ) action) + (( scalar_defs scalar_def ) action) +) + + +(block_tail (( end ) action) + (( cmnd end ) action) + (( symbol ":" block_tail ) action) + (( cmnd sep block_tail ) action) + (( sep block_tail ) action) +) + +(block_expr (( begin scalar_defs block_tail ) action) + (( begin block_tail ) action) +) + + +(lambda_vars (( sep ) action) + (( "," symbol lambda_vars ) action) +) + + +(lambda_expr (( lambda symbol lambda_vars cmnd ) action) + (( lambda "(" ")" sep cmnd ) action) + (( lambda "(" symbol sym_list sep cmnd ) action) +) + + +(expr (( rx0 ) action) + (( lx0 ) action) +) + + +(rx0 (( lx0 where symbol "=" rx1 ) action) + (( rx1 ) action) +) + + +(lx0 (( lx0 where symbol "=" lx1 ) action) + (( lx1 ) action) +) + + +(rx1 (( lx2 setq rx1 ) action) + (( rx2 ) action) +) + + +(lx1 (( lx2 setq lx1 ) action) + (( lx2 ) action) +) + + +(rx2tail (( rx3 ) action) + (( lx3 or rx2tail ) action) +) + +(rx2 (( lx3 or rx2tail ) action) + (( rx3 ) action) +) + + +(lx2tail (( lx3 ) action) + (( lx3 or lx2tail ) action) +) + +(lx2 (( lx3 or lx2tail ) action) + (( lx3 ) action) +) + + +(rx3tail (( rx4 ) action) + (( lx4 and rx3tail ) action) +) + +(rx3 (( lx4 and rx3tail ) action) + (( rx4 ) action) +) + + +(lx3tail (( lx4 ) action) + (( lx4 and lx3tail ) action) +) + +(lx3 (( lx4 and lx3tail ) action) + (( lx4 ) action) +) + + +(rx4 (( not rx4 ) action) + (( rx5 ) action) +) + + +(lx4 (( not lx4 ) action) + (( lx5 ) action) +) + + +(rx5 (( lx6 member ry6 ) action) + (( lx6 memq ry6 ) action) + (( lx6 "=" ry6 ) action) + (( lx6 neq ry6 ) action) + (( lx6 eq ry6 ) action) + (( lx6 geq ry6 ) action) + (( lx6 ">" ry6 ) action) + (( lx6 leq ry6 ) action) + (( lx6 "<" ry6 ) action) + (( lx6 freeof ry6 ) action) + (( rx6 ) action) +) + + +(lx5 (( lx6 member ly6 ) action) + (( lx6 memq ly6 ) action) + (( lx6 "=" ly6 ) action) + (( lx6 neq ly6 ) action) + (( lx6 eq ly6 ) action) + (( lx6 geq ly6 ) action) + (( lx6 ">" ly6 ) action) + (( lx6 leq ly6 ) action) + (( lx6 "<" ly6 ) action) + (( lx6 freeof ly6 ) action) + (( lx6 ) action) +) + + +(ry6 (( not ry6 ) action) + (( rx6 ) action) +) + + +(ly6 (( not ly6 ) action) + (( lx6 ) action) +) + + +(rx6tail (( ry6a ) action) + (( ly6a "+" rx6tail ) action) +) + +(rx6 (( lx6a "+" rx6tail ) action) + (( rx6a ) action) +) + + +(lx6tail (( ly6a ) action) + (( ly6a "+" lx6tail ) action) +) + +(lx6 (( lx6a "+" lx6tail ) action) + (( lx6a ) action) +) + + +(ry6a (( not ry6a ) action) + (( rx6a ) action) +) + + +(rx6a (( lx6a "-" ry7 ) action) + (( rx7 ) action) +) + + +(ly6a (( not ly6a ) action) + (( lx6a ) action) +) + + +(lx6a (( lx6a "-" ly7 ) action) + (( lx7 ) action) +) + + +(ry7 (( not ry7 ) action) + (( rx7 ) action) +) + + +(rx7 (( "+" ry7 ) action) + (( "-" ry7 ) action) + (( rx8 ) action) +) + + +(ly7 (( not ly7 ) action) + (( lx7 ) action) +) + + +(lx7 (( "+" ly7 ) action) + (( "-" ly7 ) action) + (( lx8 ) action) +) + + +(rx8tail (( ry9 ) action) + (( ly9 "*" rx8tail ) action) +) + +(rx8 (( lx9 "*" rx8tail ) action) + (( rx9 ) action) +) + + +(lx8tail (( ly9 ) action) + (( ly9 "*" lx8tail ) action) +) + +(lx8 (( lx9 "*" lx8tail ) action) + (( lx9 ) action) +) + + +(ry9 (( not ry9 ) action) + (( "+" ry9 ) action) + (( "-" ry9 ) action) + (( rx9 ) action) +) + + +(rx9 (( lx9 "/" ry10 ) action) + (( rx10 ) action) +) + + +(ly9 (( not ly9 ) action) + (( "+" ly9 ) action) + (( "-" ly9 ) action) + (( lx9 ) action) +) + + +(lx9 (( lx9 "/" ly10 ) action) + (( lx10 ) action) +) + + +(ly10 (( not ly10 ) action) + (( "+" ly10 ) action) + (( "-" ly10 ) action) + (( lx10 ) action) +) + + +(lx10 (( lx11 "^" ly10 ) action) + (( lx11 ) action) +) + + +(ry10 (( not ry10 ) action) + (( "+" ry10 ) action) + (( "-" ry10 ) action) + (( rx10 ) action) +) + + +(rx10 (( lx11 "^" ry10 ) action) + (( rx11 ) action) +) + + +(ry11 (( not ry11 ) action) + (( "+" ry11 ) action) + (( "-" ry11 ) action) + (( rx11 ) action) +) + + +(rx11 (( x12 "." ry11 ) action) + (( if_stmt ) action) + (( for_stmt ) action) + (( while_stmt ) action) + (( repeat_stmt ) action) + (( return_stmt ) action) + (( goto_stmt ) action) + (( lambda_expr ) action) + (( proc_type ) action) + (( proc_def ) action) + (( endstat ) action) +) + + +(ly11 (( not ly11 ) action) + (( "+" ly11 ) action) + (( "-" ly11 ) action) + (( lx11 ) action) +) + + +(lx11 (( x12 "." ly11 ) action) + (( x12 ) action) +) + + +(arg_list (( expr ")" ) action) + (( expr "," arg_list ) action) +) + + +(x12 (( x13 "[" expr "]" ) action) + (( x13 "(" ")" ) action) + (( x13 "(" expr "," arg_list ) action) + (( x13 x12 ) action) + (( x13 ) action) +) + + +(x13 (( symbol ) action) + (( number ) action) + (( string ) action) + (( quoted ) action) + (( backquoted ) action) + (( group_expr ) action) + (( block_expr ) action) + (( "(" expr ")" ) action) +) +)$ + + +% lalr_construct_parser rlisp_grammar; + + +end; + Index: r36/mkhelp/EXPORT.CHK ================================================================== --- r36/mkhelp/EXPORT.CHK +++ r36/mkhelp/EXPORT.CHK @@ -1,710 +1,710 @@ -EXPORT: Signatures 13-Dec-1995.10:03:00 <@@@@DGG@@JGD> -334f5664 668dead6 0 0 comphelp.red -334f5cb8 11111111 0 0 export.chk -334f5cb0 7379df02 0 0 export.pat -33516222 73e22f17 0 0 helphtml.red -334f7514 36f40873 0 0 helpunx.red -3350cba6 081c3bd0 0 0 helpwin.red -33513144 00000000 1 0 html -3351ff0e 71e410f7 0 0 html/r36.html -3351fed6 2a361437 0 0 html/r36_0001.html -3351fed6 3f8c974b 0 0 html/r36_0002.html -3351fed6 0f70f2a9 0 0 html/r36_0003.html -3351fed6 634241c9 0 0 html/r36_0004.html -3351fed6 3429fba4 0 0 html/r36_0005.html -3351fed6 2ea15831 0 0 html/r36_0006.html -3351fed6 58483e30 0 0 html/r36_0007.html -3351fed6 5fc1f2d8 0 0 html/r36_0008.html -3351fed6 1b93d3bf 0 0 html/r36_0009.html -3351fed6 4a5fe382 0 0 html/r36_0010.html -3351fed6 731f1c9b 0 0 html/r36_0011.html -3351fed6 27338ccc 0 0 html/r36_0012.html -3351fed6 3d9c9356 0 0 html/r36_0013.html -3351fed6 55d2fc9c 0 0 html/r36_0014.html -3351fed6 1bc7e511 0 0 html/r36_0015.html -3351fed6 4b27bbc5 0 0 html/r36_0016.html -3351fed8 78ce9a10 0 0 html/r36_0017.html -3351fed8 32c32073 0 0 html/r36_0018.html -3351fed8 79ff8d3b 0 0 html/r36_0019.html -3351fed8 00410671 0 0 html/r36_0020.html -3351fed8 4aa16a66 0 0 html/r36_0021.html -3351fed8 37723174 0 0 html/r36_0022.html -3351fed8 486713d3 0 0 html/r36_0023.html -3351fed8 138acc22 0 0 html/r36_0024.html -3351fed8 4f4fc836 0 0 html/r36_0025.html -3351fed8 5e603dc9 0 0 html/r36_0026.html -3351fed8 16145976 0 0 html/r36_0027.html -3351fed8 636aa7ca 0 0 html/r36_0028.html -3351fed8 6700a6f6 0 0 html/r36_0029.html -3351fed8 1e0a1718 0 0 html/r36_0030.html -3351fed8 3e5723ac 0 0 html/r36_0031.html -3351fed8 196a3168 0 0 html/r36_0032.html -3351fed8 0d43897e 0 0 html/r36_0033.html -3351fed8 4e36e3bd 0 0 html/r36_0034.html -3351fed8 43e4b024 0 0 html/r36_0035.html -3351fed8 48c79df7 0 0 html/r36_0036.html -3351fed8 55ad050c 0 0 html/r36_0037.html -3351fed8 53643130 0 0 html/r36_0038.html -3351feda 1f21bbce 0 0 html/r36_0039.html -3351feda 5e3c2912 0 0 html/r36_0040.html -3351feda 135a27d1 0 0 html/r36_0041.html -3351feda 54ea4370 0 0 html/r36_0042.html -3351feda 0c0e1ff7 0 0 html/r36_0043.html -3351feda 23c89fdd 0 0 html/r36_0044.html -3351feda 7fbaba46 0 0 html/r36_0045.html -3351feda 5dafc08f 0 0 html/r36_0046.html -3351feda 639fa8cc 0 0 html/r36_0047.html -3351feda 0c8f7a8b 0 0 html/r36_0048.html -3351feda 3e1e4113 0 0 html/r36_0049.html -3351feda 46811fec 0 0 html/r36_0050.html -3351feda 24e8cab5 0 0 html/r36_0051.html -3351feda 65aa1dc6 0 0 html/r36_0052.html -3351feda 493642f7 0 0 html/r36_0053.html -3351feda 0d5ebc10 0 0 html/r36_0054.html -3351fedc 7d338010 0 0 html/r36_0055.html -3351fedc 31e75c0d 0 0 html/r36_0056.html -3351fedc 782183aa 0 0 html/r36_0057.html -3351fedc 49d050e9 0 0 html/r36_0058.html -3351fedc 6c9981f6 0 0 html/r36_0059.html -3351fedc 369fb96b 0 0 html/r36_0060.html -3351fedc 1ded9cbc 0 0 html/r36_0061.html -3351fedc 21912cdf 0 0 html/r36_0062.html -3351fedc 5e883609 0 0 html/r36_0063.html -3351fedc 4bf914f6 0 0 html/r36_0064.html -3351fedc 66a20a14 0 0 html/r36_0065.html -3351fedc 514e7342 0 0 html/r36_0066.html -3351fedc 5ab28831 0 0 html/r36_0067.html -3351fedc 64ee5bf3 0 0 html/r36_0068.html -3351fedc 2e1b4ab7 0 0 html/r36_0069.html -3351fedc 38d7ca15 0 0 html/r36_0070.html -3351fedc 29a01022 0 0 html/r36_0071.html -3351fedc 1596d460 0 0 html/r36_0072.html -3351fedc 6741ce23 0 0 html/r36_0073.html -3351fedc 71624ff0 0 0 html/r36_0074.html -3351fedc 42f8efe3 0 0 html/r36_0075.html -3351fedc 3c2ef867 0 0 html/r36_0076.html -3351fedc 2aa5a787 0 0 html/r36_0077.html -3351fede 1b430c01 0 0 html/r36_0078.html -3351fede 22865d46 0 0 html/r36_0079.html -3351fede 7620fe90 0 0 html/r36_0080.html -3351fede 62af8400 0 0 html/r36_0081.html -3351fede 0d72b2f6 0 0 html/r36_0082.html -3351fede 2b4a10a5 0 0 html/r36_0083.html -3351fede 72121841 0 0 html/r36_0084.html -3351fede 4a05771e 0 0 html/r36_0085.html -3351fede 36f1b441 0 0 html/r36_0086.html -3351fede 0ad01253 0 0 html/r36_0087.html -3351fede 642959b7 0 0 html/r36_0088.html -3351fede 3a72e3be 0 0 html/r36_0089.html -3351fede 06aacffa 0 0 html/r36_0090.html -3351fede 6ce64be7 0 0 html/r36_0091.html -3351fede 1706e850 0 0 html/r36_0092.html -3351fede 687a8ee2 0 0 html/r36_0093.html -3351fede 6ec96ce4 0 0 html/r36_0094.html -3351fede 2ef60b83 0 0 html/r36_0095.html -3351fede 30b66e28 0 0 html/r36_0096.html -3351fede 0573ab0d 0 0 html/r36_0097.html -3351fede 43cc0d65 0 0 html/r36_0098.html -3351fede 646739fd 0 0 html/r36_0099.html -3351fede 0878e75c 0 0 html/r36_0100.html -3351fede 72c835e2 0 0 html/r36_0101.html -3351fede 0f03cf09 0 0 html/r36_0102.html -3351fede 758ae9ea 0 0 html/r36_0103.html -3351fede 74e99fa1 0 0 html/r36_0104.html -3351fede 4862237f 0 0 html/r36_0105.html -3351fee0 40743915 0 0 html/r36_0106.html -3351fee0 044c71cf 0 0 html/r36_0107.html -3351fee0 08995257 0 0 html/r36_0108.html -3351fee0 0274617a 0 0 html/r36_0109.html -3351fee0 27a54d37 0 0 html/r36_0110.html -3351fee0 1972920c 0 0 html/r36_0111.html -3351fee0 6732d0d8 0 0 html/r36_0112.html -3351fee0 7e765bc0 0 0 html/r36_0113.html -3351fee0 09316b02 0 0 html/r36_0114.html -3351fee0 592eae61 0 0 html/r36_0115.html -3351fee0 3fb638f5 0 0 html/r36_0116.html -3351fee0 11c86628 0 0 html/r36_0117.html -3351fee0 44e3a546 0 0 html/r36_0118.html -3351fee0 546d68bf 0 0 html/r36_0119.html -3351fee0 6d94e9f5 0 0 html/r36_0120.html -3351fee0 3e8400aa 0 0 html/r36_0121.html -3351fee0 089128c9 0 0 html/r36_0122.html -3351fee0 739af7cf 0 0 html/r36_0123.html -3351fee0 4e684cff 0 0 html/r36_0124.html -3351fee0 6ff33528 0 0 html/r36_0125.html -3351fee0 59025b76 0 0 html/r36_0126.html -3351fee0 2b7fee84 0 0 html/r36_0127.html -3351fee2 15c489e0 0 0 html/r36_0128.html -3351fee2 0fc570b5 0 0 html/r36_0129.html -3351fee2 2a646562 0 0 html/r36_0130.html -3351fee2 73a1b4c8 0 0 html/r36_0131.html -3351fee2 7c6a831e 0 0 html/r36_0132.html -3351fee2 764301ba 0 0 html/r36_0133.html -3351fee2 394d1d73 0 0 html/r36_0134.html -3351fee2 27c81033 0 0 html/r36_0135.html -3351fee2 438fc672 0 0 html/r36_0136.html -3351fee2 510576ec 0 0 html/r36_0137.html -3351fee2 3aeabc78 0 0 html/r36_0138.html -3351fee2 5184fbc9 0 0 html/r36_0139.html -3351fee2 0743089c 0 0 html/r36_0140.html -3351fee2 3558e4c9 0 0 html/r36_0141.html -3351fee2 3b01520e 0 0 html/r36_0142.html -3351fee2 39134d74 0 0 html/r36_0143.html -3351fee2 25a53910 0 0 html/r36_0144.html -3351fee2 71706c8d 0 0 html/r36_0145.html -3351fee2 2e4354e7 0 0 html/r36_0146.html -3351fee2 08d6b254 0 0 html/r36_0147.html -3351fee2 76105ff6 0 0 html/r36_0148.html -3351fee2 4beb3c08 0 0 html/r36_0149.html -3351fee2 4092a200 0 0 html/r36_0150.html -3351fee4 5b43dffe 0 0 html/r36_0151.html -3351fee4 5dc4d5ac 0 0 html/r36_0152.html -3351fee4 37a31e64 0 0 html/r36_0153.html -3351fee4 29c6eb17 0 0 html/r36_0154.html -3351fee4 5f0b1542 0 0 html/r36_0155.html -3351fee4 3dd47aa3 0 0 html/r36_0156.html -3351fee4 3e657577 0 0 html/r36_0157.html -3351fee4 02201574 0 0 html/r36_0158.html -3351fee4 62702c0b 0 0 html/r36_0159.html -3351fee4 67396757 0 0 html/r36_0160.html -3351fee4 36b668df 0 0 html/r36_0161.html -3351fee4 0d1ecb8c 0 0 html/r36_0162.html -3351fee4 662009cf 0 0 html/r36_0163.html -3351fee4 76c089b8 0 0 html/r36_0164.html -3351fee4 1adeedfc 0 0 html/r36_0165.html -3351fee4 63bfce63 0 0 html/r36_0166.html -3351fee4 0f649b82 0 0 html/r36_0167.html -3351fee4 718d5e9a 0 0 html/r36_0168.html -3351fee4 75a03e1b 0 0 html/r36_0169.html -3351fee4 5bf506c4 0 0 html/r36_0170.html -3351fee4 661eb2e3 0 0 html/r36_0171.html -3351fee6 0a54fcf7 0 0 html/r36_0172.html -3351fee6 566a41d1 0 0 html/r36_0173.html -3351fee6 4550ea71 0 0 html/r36_0174.html -3351fee6 615c151c 0 0 html/r36_0175.html -3351fee6 575b491a 0 0 html/r36_0176.html -3351fee6 72b85eaf 0 0 html/r36_0177.html -3351fee6 74376e38 0 0 html/r36_0178.html -3351fee6 75391356 0 0 html/r36_0179.html -3351fee6 63645963 0 0 html/r36_0180.html -3351fee6 40970afc 0 0 html/r36_0181.html -3351fee6 560b7a3e 0 0 html/r36_0182.html -3351fee6 43de8d0f 0 0 html/r36_0183.html -3351fee8 4c1926e4 0 0 html/r36_0184.html -3351fee8 5c23a084 0 0 html/r36_0185.html -3351fee8 3066c527 0 0 html/r36_0186.html -3351fee8 1dd35f7c 0 0 html/r36_0187.html -3351fee8 22fcb928 0 0 html/r36_0188.html -3351fee8 1ceca5b2 0 0 html/r36_0189.html -3351fee8 7e536ada 0 0 html/r36_0190.html -3351fee8 3436a7f6 0 0 html/r36_0191.html -3351fee8 054f82de 0 0 html/r36_0192.html -3351fee8 141ffa5a 0 0 html/r36_0193.html -3351fee8 3e5b1c14 0 0 html/r36_0194.html -3351fee8 7fd6c734 0 0 html/r36_0195.html -3351fee8 255fc2e8 0 0 html/r36_0196.html -3351fee8 0329cd7c 0 0 html/r36_0197.html -3351fee8 786df66a 0 0 html/r36_0198.html -3351feea 649ea591 0 0 html/r36_0199.html -3351feea 15e148e8 0 0 html/r36_0200.html -3351feea 78782c8b 0 0 html/r36_0201.html -3351feea 0bc67a2f 0 0 html/r36_0202.html -3351feea 5367764c 0 0 html/r36_0203.html -3351feea 5a955f45 0 0 html/r36_0204.html -3351feea 15529288 0 0 html/r36_0205.html -3351feea 2a81b009 0 0 html/r36_0206.html -3351feea 4c2a33d3 0 0 html/r36_0207.html -3351feea 446e2705 0 0 html/r36_0208.html -3351feea 732f6fff 0 0 html/r36_0209.html -3351feea 13534f39 0 0 html/r36_0210.html -3351feea 43146fa1 0 0 html/r36_0211.html -3351feea 1347a6a7 0 0 html/r36_0212.html -3351feea 38cde0a8 0 0 html/r36_0213.html -3351feea 14471003 0 0 html/r36_0214.html -3351feea 7ba1b715 0 0 html/r36_0215.html -3351feea 692bd3e5 0 0 html/r36_0216.html -3351feea 6ac14eb6 0 0 html/r36_0217.html -3351feea 4db82a4a 0 0 html/r36_0218.html -3351feea 1eb40efa 0 0 html/r36_0219.html -3351feea 4aac3eee 0 0 html/r36_0220.html -3351feea 5da53ca8 0 0 html/r36_0221.html -3351feec 4f7ace4e 0 0 html/r36_0222.html -3351feec 3c61f971 0 0 html/r36_0223.html -3351feec 114884a4 0 0 html/r36_0224.html -3351feec 189a5561 0 0 html/r36_0225.html -3351feec 79725048 0 0 html/r36_0226.html -3351feec 79ec0d54 0 0 html/r36_0227.html -3351feec 1ab58c44 0 0 html/r36_0228.html -3351feec 7ae5cf58 0 0 html/r36_0229.html -3351feec 2161e8d0 0 0 html/r36_0230.html -3351feec 2ae5a206 0 0 html/r36_0231.html -3351feec 7b8da4aa 0 0 html/r36_0232.html -3351feec 24077de8 0 0 html/r36_0233.html -3351feec 4cda87ea 0 0 html/r36_0234.html -3351feec 0200348b 0 0 html/r36_0235.html -3351feec 0ca197be 0 0 html/r36_0236.html -3351feec 16f67880 0 0 html/r36_0237.html -3351feec 1e8d5af6 0 0 html/r36_0238.html -3351feec 31db0a34 0 0 html/r36_0239.html -3351feec 3d8c422e 0 0 html/r36_0240.html -3351feec 2ce974bd 0 0 html/r36_0241.html -3351feee 469f2dec 0 0 html/r36_0242.html -3351feee 69bc5ad1 0 0 html/r36_0243.html -3351feee 42b67c0f 0 0 html/r36_0244.html -3351feee 55b46ad3 0 0 html/r36_0245.html -3351feee 79c903c0 0 0 html/r36_0246.html -3351feee 2ce2aea3 0 0 html/r36_0247.html -3351feee 5fa7a21d 0 0 html/r36_0248.html -3351feee 6f2c4b1d 0 0 html/r36_0249.html -3351feee 14dd3b77 0 0 html/r36_0250.html -3351feee 5eeae40b 0 0 html/r36_0251.html -3351feee 16ca5935 0 0 html/r36_0252.html -3351feee 3b904908 0 0 html/r36_0253.html -3351feee 1f1dce9c 0 0 html/r36_0254.html -3351feee 3ff598f7 0 0 html/r36_0255.html -3351feee 120d58c0 0 0 html/r36_0256.html -3351feee 67334baa 0 0 html/r36_0257.html -3351feee 68e6527f 0 0 html/r36_0258.html -3351feee 1ef1f10d 0 0 html/r36_0259.html -3351feee 0ed23fb5 0 0 html/r36_0260.html -3351feee 341585f8 0 0 html/r36_0261.html -3351feee 3a043d53 0 0 html/r36_0262.html -3351feee 5e932d3b 0 0 html/r36_0263.html -3351feee 1634772e 0 0 html/r36_0264.html -3351feee 61006327 0 0 html/r36_0265.html -3351feee 1abddb94 0 0 html/r36_0266.html -3351feee 782aa216 0 0 html/r36_0267.html -3351fef0 0dfb9304 0 0 html/r36_0268.html -3351fef0 05de0184 0 0 html/r36_0269.html -3351fef0 53f392de 0 0 html/r36_0270.html -3351fef0 4cd38871 0 0 html/r36_0271.html -3351fef0 273ec5a9 0 0 html/r36_0272.html -3351fef0 02c20ca2 0 0 html/r36_0273.html -3351fef0 44b9f7b1 0 0 html/r36_0274.html -3351fef0 20e50bb8 0 0 html/r36_0275.html -3351fef0 3baa2673 0 0 html/r36_0276.html -3351fef0 0afd1c2b 0 0 html/r36_0277.html -3351fef0 68de9007 0 0 html/r36_0278.html -3351fef0 4e01f889 0 0 html/r36_0279.html -3351fef0 4aa41101 0 0 html/r36_0280.html -3351fef0 507dc4c7 0 0 html/r36_0281.html -3351fef0 7dbe341c 0 0 html/r36_0282.html -3351fef0 5dd2eee3 0 0 html/r36_0283.html -3351fef0 500e9477 0 0 html/r36_0284.html -3351fef0 19053ee0 0 0 html/r36_0285.html -3351fef0 7adbeb6a 0 0 html/r36_0286.html -3351fef0 0c28b6dc 0 0 html/r36_0287.html -3351fef0 6c6bfc74 0 0 html/r36_0288.html -3351fef2 5e420f23 0 0 html/r36_0289.html -3351fef2 3e219e7c 0 0 html/r36_0290.html -3351fef2 5b068515 0 0 html/r36_0291.html -3351fef2 3cb9e895 0 0 html/r36_0292.html -3351fef2 3c18ab54 0 0 html/r36_0293.html -3351fef2 02f19110 0 0 html/r36_0294.html -3351fef2 4f649ec3 0 0 html/r36_0295.html -3351fef2 0b55d96a 0 0 html/r36_0296.html -3351fef2 146d1736 0 0 html/r36_0297.html -3351fef2 1905ec2c 0 0 html/r36_0298.html -3351fef2 4b11a9e8 0 0 html/r36_0299.html -3351fef2 5d40a3b0 0 0 html/r36_0300.html -3351fef2 7402b314 0 0 html/r36_0301.html -3351fef2 7e92838b 0 0 html/r36_0302.html -3351fef2 7255ad8d 0 0 html/r36_0303.html -3351fef4 77e814d3 0 0 html/r36_0304.html -3351fef4 71aeeba3 0 0 html/r36_0305.html -3351fef4 4f4ff58b 0 0 html/r36_0306.html -3351fef4 4326743a 0 0 html/r36_0307.html -3351fef4 03ae9fd2 0 0 html/r36_0308.html -3351fef4 5dd12581 0 0 html/r36_0309.html -3351fef4 723da7aa 0 0 html/r36_0310.html -3351fef4 447e3575 0 0 html/r36_0311.html -3351fef4 6bff5e12 0 0 html/r36_0312.html -3351fef4 31b6f001 0 0 html/r36_0313.html -3351fef4 3b019d88 0 0 html/r36_0314.html -3351fef4 6e667bcc 0 0 html/r36_0315.html -3351fef4 67dc73d2 0 0 html/r36_0316.html -3351fef4 349aaac4 0 0 html/r36_0317.html -3351fef4 41087618 0 0 html/r36_0318.html -3351fef4 5f019bb3 0 0 html/r36_0319.html -3351fef4 42a88f05 0 0 html/r36_0320.html -3351fef4 50bbf153 0 0 html/r36_0321.html -3351fef4 5c1f8ad6 0 0 html/r36_0322.html -3351fef4 1f4ed70f 0 0 html/r36_0323.html -3351fef4 183cb53d 0 0 html/r36_0324.html -3351fef4 5d95a1b1 0 0 html/r36_0325.html -3351fef4 70dbf57e 0 0 html/r36_0326.html -3351fef4 31591666 0 0 html/r36_0327.html -3351fef4 758499cd 0 0 html/r36_0328.html -3351fef4 09dd2098 0 0 html/r36_0329.html -3351fef4 292fb449 0 0 html/r36_0330.html -3351fef6 5a8cf131 0 0 html/r36_0331.html -3351fef6 501f1d86 0 0 html/r36_0332.html -3351fef6 2de34f77 0 0 html/r36_0333.html -3351fef6 73e98a78 0 0 html/r36_0334.html -3351fef6 7b75f76e 0 0 html/r36_0335.html -3351fef6 22d08041 0 0 html/r36_0336.html -3351fef6 4a99d178 0 0 html/r36_0337.html -3351fef6 023314a5 0 0 html/r36_0338.html -3351fef6 3017c4fe 0 0 html/r36_0339.html -3351fef6 3c0ff92a 0 0 html/r36_0340.html -3351fef6 4b435b82 0 0 html/r36_0341.html -3351fef6 1fb0ae3e 0 0 html/r36_0342.html -3351fef6 095be64f 0 0 html/r36_0343.html -3351fef6 53b238b2 0 0 html/r36_0344.html -3351fef6 78563a5e 0 0 html/r36_0345.html -3351fef6 2e749ab4 0 0 html/r36_0346.html -3351fef6 7c0b143c 0 0 html/r36_0347.html -3351fef6 09f867ff 0 0 html/r36_0348.html -3351fef6 6d9cbf9b 0 0 html/r36_0349.html -3351fef6 5c5facec 0 0 html/r36_0350.html -3351fef6 49858db9 0 0 html/r36_0351.html -3351fef8 7b8b2833 0 0 html/r36_0352.html -3351fef8 79d48e05 0 0 html/r36_0353.html -3351fef8 0a830deb 0 0 html/r36_0354.html -3351fef8 1e6d08b3 0 0 html/r36_0355.html -3351fef8 20ead4d8 0 0 html/r36_0356.html -3351fef8 267deb98 0 0 html/r36_0357.html -3351fef8 37bf3fc8 0 0 html/r36_0358.html -3351fef8 7a69dbcd 0 0 html/r36_0359.html -3351fef8 2fe3042a 0 0 html/r36_0360.html -3351fef8 5606000f 0 0 html/r36_0361.html -3351fef8 49c4b21b 0 0 html/r36_0362.html -3351fef8 7082acf0 0 0 html/r36_0363.html -3351fef8 389798ca 0 0 html/r36_0364.html -3351fef8 5841ba0f 0 0 html/r36_0365.html -3351fef8 171fa8f2 0 0 html/r36_0366.html -3351fef8 6265346e 0 0 html/r36_0367.html -3351fef8 62650611 0 0 html/r36_0368.html -3351fef8 6df1b688 0 0 html/r36_0369.html -3351fef8 6630c7e2 0 0 html/r36_0370.html -3351fef8 5feab9df 0 0 html/r36_0371.html -3351fef8 2a54b9f1 0 0 html/r36_0372.html -3351fef8 2f9c388c 0 0 html/r36_0373.html -3351fef8 500f0bdb 0 0 html/r36_0374.html -3351fef8 1f46c6c8 0 0 html/r36_0375.html -3351fef8 57327ddb 0 0 html/r36_0376.html -3351fef8 568b05d5 0 0 html/r36_0377.html -3351fef8 4a0f8c48 0 0 html/r36_0378.html -3351fef8 19fa735f 0 0 html/r36_0379.html -3351fef8 4e895435 0 0 html/r36_0380.html -3351fef8 45442e58 0 0 html/r36_0381.html -3351fefa 0e7a7541 0 0 html/r36_0382.html -3351fefa 4fa16ea8 0 0 html/r36_0383.html -3351fefa 49c71091 0 0 html/r36_0384.html -3351fefa 4e8ebac0 0 0 html/r36_0385.html -3351fefa 1142aedd 0 0 html/r36_0386.html -3351fefa 6ba5213c 0 0 html/r36_0387.html -3351fefa 231db237 0 0 html/r36_0388.html -3351fefa 2f37a074 0 0 html/r36_0389.html -3351fefa 6b79a0bc 0 0 html/r36_0390.html -3351fefa 46db2126 0 0 html/r36_0391.html -3351fefa 4bd767a4 0 0 html/r36_0392.html -3351fefa 76e352d6 0 0 html/r36_0393.html -3351fefa 0b7253ba 0 0 html/r36_0394.html -3351fefa 308b364f 0 0 html/r36_0395.html -3351fefa 651830c6 0 0 html/r36_0396.html -3351fefa 03d4b766 0 0 html/r36_0397.html -3351fefa 7fb91770 0 0 html/r36_0398.html -3351fefa 40ffc96e 0 0 html/r36_0399.html -3351fefa 6b249eeb 0 0 html/r36_0400.html -3351fefa 6c8c4d40 0 0 html/r36_0401.html -3351fefa 1b299584 0 0 html/r36_0402.html -3351fefa 41959185 0 0 html/r36_0403.html -3351fefa 571cc82d 0 0 html/r36_0404.html -3351fefa 44029603 0 0 html/r36_0405.html -3351fefa 328e9ef0 0 0 html/r36_0406.html -3351fefa 27c1b8ec 0 0 html/r36_0407.html -3351fefa 21f3420c 0 0 html/r36_0408.html -3351fefa 1e8e651e 0 0 html/r36_0409.html -3351fefa 0e1e8247 0 0 html/r36_0410.html -3351fefa 49bee135 0 0 html/r36_0411.html -3351fefa 70d474b9 0 0 html/r36_0412.html -3351fefa 01f25f0f 0 0 html/r36_0413.html -3351fefc 55e37521 0 0 html/r36_0414.html -3351fefc 6e1a1196 0 0 html/r36_0415.html -3351fefc 646e5e12 0 0 html/r36_0416.html -3351fefc 28a11d17 0 0 html/r36_0417.html -3351fefc 4ae6b048 0 0 html/r36_0418.html -3351fefc 0ee41cd3 0 0 html/r36_0419.html -3351fefc 0f27456a 0 0 html/r36_0420.html -3351fefc 69094b65 0 0 html/r36_0421.html -3351fefc 13dafd18 0 0 html/r36_0422.html -3351fefc 3a481deb 0 0 html/r36_0423.html -3351fefc 1c166fd5 0 0 html/r36_0424.html -3351fefc 1a482d4c 0 0 html/r36_0425.html -3351fefc 18378de0 0 0 html/r36_0426.html -3351fefc 54762a24 0 0 html/r36_0427.html -3351fefc 384d0f0b 0 0 html/r36_0428.html -3351fefc 127c95d2 0 0 html/r36_0429.html -3351fefc 0e5d4bea 0 0 html/r36_0430.html -3351fefc 70583575 0 0 html/r36_0431.html -3351fefc 2bfcc8b5 0 0 html/r36_0432.html -3351fefc 7c399734 0 0 html/r36_0433.html -3351fefc 40372cad 0 0 html/r36_0434.html -3351fefc 761a8cee 0 0 html/r36_0435.html -3351fefc 1084ca4a 0 0 html/r36_0436.html -3351fefc 37f296e3 0 0 html/r36_0437.html -3351fefc 038f3036 0 0 html/r36_0438.html -3351fefe 73db3e63 0 0 html/r36_0439.html -3351fefe 6d81cc09 0 0 html/r36_0440.html -3351fefe 0586ddc8 0 0 html/r36_0441.html -3351fefe 15f4ded4 0 0 html/r36_0442.html -3351fefe 19337663 0 0 html/r36_0443.html -3351fefe 56ef60ce 0 0 html/r36_0444.html -3351fefe 2921774a 0 0 html/r36_0445.html -3351fefe 2a6dc51e 0 0 html/r36_0446.html -3351fefe 26faa403 0 0 html/r36_0447.html -3351fefe 4a9cc510 0 0 html/r36_0448.html -3351fefe 7bafe007 0 0 html/r36_0449.html -3351fefe 00e11861 0 0 html/r36_0450.html -3351fefe 6374ed69 0 0 html/r36_0451.html -3351fefe 0aef7f1f 0 0 html/r36_0452.html -3351fefe 7f074ce0 0 0 html/r36_0453.html -3351fefe 1911fbb4 0 0 html/r36_0454.html -3351fefe 13a33d6c 0 0 html/r36_0455.html -3351fefe 7eee8ec2 0 0 html/r36_0456.html -3351fefe 587d39ff 0 0 html/r36_0457.html -3351fefe 6abb0f00 0 0 html/r36_0458.html -3351fefe 15664ea6 0 0 html/r36_0459.html -3351fefe 78147daa 0 0 html/r36_0460.html -3351fefe 5ec66036 0 0 html/r36_0461.html -3351fefe 6b246b3a 0 0 html/r36_0462.html -3351fefe 3683f508 0 0 html/r36_0463.html -3351fefe 332cb244 0 0 html/r36_0464.html -3351fefe 2120f561 0 0 html/r36_0465.html -3351fefe 436ef325 0 0 html/r36_0466.html -3351fefe 35443271 0 0 html/r36_0467.html -3351fefe 213aaa7b 0 0 html/r36_0468.html -3351fefe 21b4dd9b 0 0 html/r36_0469.html -3351fefe 15eb7ac0 0 0 html/r36_0470.html -3351fefe 6743d4bf 0 0 html/r36_0471.html -3351fefe 4fc03749 0 0 html/r36_0472.html -3351fefe 6aa9e3cb 0 0 html/r36_0473.html -3351fefe 1c9c1c80 0 0 html/r36_0474.html -3351fefe 359f0e18 0 0 html/r36_0475.html -3351fefe 02466f9d 0 0 html/r36_0476.html -3351fefe 2fb818fe 0 0 html/r36_0477.html -3351fefe 1eda0740 0 0 html/r36_0478.html -3351fefe 16b8e48f 0 0 html/r36_0479.html -3351ff00 680e6873 0 0 html/r36_0480.html -3351ff00 1fad2f96 0 0 html/r36_0481.html -3351ff00 67503431 0 0 html/r36_0482.html -3351ff00 7568e801 0 0 html/r36_0483.html -3351ff00 28b8aef3 0 0 html/r36_0484.html -3351ff00 20ac4022 0 0 html/r36_0485.html -3351ff00 4ee2fada 0 0 html/r36_0486.html -3351ff00 53ac2c88 0 0 html/r36_0487.html -3351ff00 058ba857 0 0 html/r36_0488.html -3351ff00 61caeb60 0 0 html/r36_0489.html -3351ff00 39b23003 0 0 html/r36_0490.html -3351ff00 3d24aa88 0 0 html/r36_0491.html -3351ff00 64cf4ead 0 0 html/r36_0492.html -3351ff00 5401dbbc 0 0 html/r36_0493.html -3351ff00 56ed6edd 0 0 html/r36_0494.html -3351ff00 2804ed69 0 0 html/r36_0495.html -3351ff00 69d03294 0 0 html/r36_0496.html -3351ff00 5a82143b 0 0 html/r36_0497.html -3351ff00 7111ddf6 0 0 html/r36_0498.html -3351ff00 63d5264c 0 0 html/r36_0499.html -3351ff00 3e5cbdf1 0 0 html/r36_0500.html -3351ff00 611e8d09 0 0 html/r36_0501.html -3351ff00 6e172d51 0 0 html/r36_0502.html -3351ff00 06e94019 0 0 html/r36_0503.html -3351ff00 1cd0ff47 0 0 html/r36_0504.html -3351ff00 48e2d9f2 0 0 html/r36_0505.html -3351ff00 12f19343 0 0 html/r36_0506.html -3351ff00 7b9e96a5 0 0 html/r36_0507.html -3351ff00 2713aa95 0 0 html/r36_0508.html -3351ff02 77ba7849 0 0 html/r36_0509.html -3351ff02 25c0487d 0 0 html/r36_0510.html -3351ff02 46be1a24 0 0 html/r36_0511.html -3351ff02 5673d210 0 0 html/r36_0512.html -3351ff02 38ccd99e 0 0 html/r36_0513.html -3351ff02 35828322 0 0 html/r36_0514.html -3351ff02 52a2bf7e 0 0 html/r36_0515.html -3351ff02 4cbf9822 0 0 html/r36_0516.html -3351ff02 22303dfd 0 0 html/r36_0517.html -3351ff02 7f5e393f 0 0 html/r36_0518.html -3351ff02 56b2287a 0 0 html/r36_0519.html -3351ff02 0357239a 0 0 html/r36_0520.html -3351ff02 7e7f2f26 0 0 html/r36_0521.html -3351ff02 48768c40 0 0 html/r36_0522.html -3351ff02 6b08519f 0 0 html/r36_0523.html -3351ff02 47007ed9 0 0 html/r36_0524.html -3351ff02 0d747faf 0 0 html/r36_0525.html -3351ff02 4035cad5 0 0 html/r36_0526.html -3351ff02 7752ea55 0 0 html/r36_0527.html -3351ff02 3a267b92 0 0 html/r36_0528.html -3351ff02 06f717e8 0 0 html/r36_0529.html -3351ff02 709aa7cd 0 0 html/r36_0530.html -3351ff02 516c2bcd 0 0 html/r36_0531.html -3351ff02 79833cee 0 0 html/r36_0532.html -3351ff02 0a2d1782 0 0 html/r36_0533.html -3351ff02 33a9e4cf 0 0 html/r36_0534.html -3351ff02 1aacae2c 0 0 html/r36_0535.html -3351ff02 6af9b283 0 0 html/r36_0536.html -3351ff04 73207392 0 0 html/r36_0537.html -3351ff04 3939d73b 0 0 html/r36_0538.html -3351ff04 4c9c6f8d 0 0 html/r36_0539.html -3351ff04 157f741b 0 0 html/r36_0540.html -3351ff04 7b775430 0 0 html/r36_0541.html -3351ff04 36fd5f73 0 0 html/r36_0542.html -3351ff04 384a3445 0 0 html/r36_0543.html -3351ff04 4d12f82d 0 0 html/r36_0544.html -3351ff04 53888326 0 0 html/r36_0545.html -3351ff04 4b3ae7b0 0 0 html/r36_0546.html -3351ff04 17a70e49 0 0 html/r36_0547.html -3351ff04 23ffd2ad 0 0 html/r36_0548.html -3351ff04 6ac30d75 0 0 html/r36_0549.html -3351ff04 117efbc6 0 0 html/r36_0550.html -3351ff04 4d6f7c1f 0 0 html/r36_0551.html -3351ff04 50ee5ee4 0 0 html/r36_0552.html -3351ff04 0cc918fc 0 0 html/r36_0553.html -3351ff04 25a43c94 0 0 html/r36_0554.html -3351ff04 5f53d5ed 0 0 html/r36_0555.html -3351ff04 65f81e9d 0 0 html/r36_0556.html -3351ff04 38033dc9 0 0 html/r36_0557.html -3351ff04 698b3314 0 0 html/r36_0558.html -3351ff04 78613977 0 0 html/r36_0559.html -3351ff04 2f625d47 0 0 html/r36_0560.html -3351ff04 46552feb 0 0 html/r36_0561.html -3351ff04 07713eac 0 0 html/r36_0562.html -3351ff04 7a0d4254 0 0 html/r36_0563.html -3351ff04 13b58e2a 0 0 html/r36_0564.html -3351ff04 5a9112bb 0 0 html/r36_0565.html -3351ff04 00bed861 0 0 html/r36_0566.html -3351ff06 05ed2683 0 0 html/r36_0567.html -3351ff06 609a4fca 0 0 html/r36_0568.html -3351ff06 2b99f0dc 0 0 html/r36_0569.html -3351ff06 60d2f416 0 0 html/r36_0570.html -3351ff06 37a03fbf 0 0 html/r36_0571.html -3351ff06 35d81d16 0 0 html/r36_0572.html -3351ff06 1b561ab7 0 0 html/r36_0573.html -3351ff06 69360378 0 0 html/r36_0574.html -3351ff06 441b3c56 0 0 html/r36_0575.html -3351ff06 4e44b09c 0 0 html/r36_0576.html -3351ff06 456ba814 0 0 html/r36_0577.html -3351ff06 09d26004 0 0 html/r36_0578.html -3351ff06 7e87d4be 0 0 html/r36_0579.html -3351ff06 492600b9 0 0 html/r36_0580.html -3351ff06 1f330829 0 0 html/r36_0581.html -3351ff06 277764ac 0 0 html/r36_0582.html -3351ff06 7f343184 0 0 html/r36_0583.html -3351ff06 2261600a 0 0 html/r36_0584.html -3351ff06 7f6e88d0 0 0 html/r36_0585.html -3351ff08 0d173730 0 0 html/r36_0586.html -3351ff08 5e7d5576 0 0 html/r36_0587.html -3351ff08 3c63a15e 0 0 html/r36_0588.html -3351ff08 225120a7 0 0 html/r36_0589.html -3351ff08 7e3dee00 0 0 html/r36_0590.html -3351ff08 6594fdc9 0 0 html/r36_0591.html -3351ff08 316c3ebe 0 0 html/r36_0592.html -3351ff08 2ceeb320 0 0 html/r36_0593.html -3351ff08 671abe39 0 0 html/r36_0594.html -3351ff08 389ab30a 0 0 html/r36_0595.html -3351ff08 2a207346 0 0 html/r36_0596.html -3351ff08 4f779db9 0 0 html/r36_0597.html -3351ff08 77706184 0 0 html/r36_0598.html -3351ff08 1d109cb9 0 0 html/r36_0599.html -3351ff08 6f513500 0 0 html/r36_0600.html -3351ff08 5e0fae8a 0 0 html/r36_0601.html -3351ff08 577f6ae5 0 0 html/r36_0602.html -3351ff08 4ba9acdc 0 0 html/r36_0603.html -3351ff08 79862521 0 0 html/r36_0604.html -3351ff08 1e447c23 0 0 html/r36_0605.html -3351ff08 2591f389 0 0 html/r36_0606.html -3351ff08 60b07451 0 0 html/r36_0607.html -3351ff08 7be7a466 0 0 html/r36_0608.html -3351ff08 4b57bab6 0 0 html/r36_0609.html -3351ff08 0109ad7e 0 0 html/r36_0610.html -3351ff08 20764d61 0 0 html/r36_0611.html -3351ff08 534dc3d2 0 0 html/r36_0612.html -3351ff08 64cfe445 0 0 html/r36_0613.html -3351ff0a 4259b32f 0 0 html/r36_0614.html -3351ff0a 3269c61f 0 0 html/r36_0615.html -3351ff0a 329e3f9d 0 0 html/r36_0616.html -3351ff0a 42aae59c 0 0 html/r36_0617.html -3351ff0a 019efbcb 0 0 html/r36_0618.html -3351ff0a 5861a35c 0 0 html/r36_0619.html -3351ff0a 106e7d3c 0 0 html/r36_0620.html -3351ff0a 02a5eb15 0 0 html/r36_0621.html -3351ff0a 7db1b1c6 0 0 html/r36_0622.html -3351ff0a 3ea52ae5 0 0 html/r36_0623.html -3351ff0a 1a69fb32 0 0 html/r36_0624.html -3351ff0a 5f7785c3 0 0 html/r36_0625.html -3351ff0a 5d0321f7 0 0 html/r36_0626.html -3351ff0a 14d7417b 0 0 html/r36_0627.html -3351ff0a 16a3d795 0 0 html/r36_0628.html -3351ff0a 6257bce1 0 0 html/r36_0629.html -3351ff0c 46626369 0 0 html/r36_0630.html -3351ff0c 4653040c 0 0 html/r36_0631.html -3351ff0c 3cffa3fb 0 0 html/r36_0632.html -3351ff0c 3f67d025 0 0 html/r36_0633.html -3351ff0c 505e9a66 0 0 html/r36_0634.html -3351ff0c 3b804364 0 0 html/r36_0635.html -3351ff0c 5112a45a 0 0 html/r36_0636.html -3351ff0c 6775f99c 0 0 html/r36_0637.html -3351ff0c 1cbf3806 0 0 html/r36_0638.html -3351ff0c 478de809 0 0 html/r36_0639.html -3351ff0c 3b0bc838 0 0 html/r36_0640.html -3351ff0c 6c5df8fa 0 0 html/r36_0641.html -3351ff0c 44a169ec 0 0 html/r36_0642.html -3351ff0c 7c64ece3 0 0 html/r36_0643.html -3351ff0c 29e589f3 0 0 html/r36_0644.html -3351ff0c 11f691c6 0 0 html/r36_0645.html -3351ff0c 54a1e9b4 0 0 html/r36_0646.html -3351ff0c 30b4b0e7 0 0 html/r36_0647.html -3351ff0c 4d129556 0 0 html/r36_0648.html -3351ff0c 41aec3b6 0 0 html/r36_0649.html -3351ff0c 35240532 0 0 html/r36_0650.html -3351ff0c 0a7770af 0 0 html/r36_0651.html -3351ff0c 7d1d2a41 0 0 html/r36_0652.html -3351ff0c 20c06fb2 0 0 html/r36_0653.html -3351ff0c 1bb4b7fb 0 0 html/r36_0654.html -3351ff0c 340f39ef 0 0 html/r36_0655.html -3351ff0c 2bb31dc1 0 0 html/r36_0656.html -3351ff0c 45cd57b0 0 0 html/r36_0657.html -3351ff0c 09fcd5d2 0 0 html/r36_0658.html -3351ff0c 12e242d5 0 0 html/r36_0659.html -3351ff0c 0107d61b 0 0 html/r36_0660.html -3351ff0e 0d60203b 0 0 html/r36_0661.html -3351ff0e 2abd9dbd 0 0 html/r36_0662.html -3351ff0e 3bff79fb 0 0 html/r36_0663.html -3351ff0e 7f59778b 0 0 html/r36_0664.html -3351ff0e 05f1dd99 0 0 html/r36_0665.html -3351ff0e 0dba3aef 0 0 html/r36_0666.html -3351ff0e 15c89d1c 0 0 html/r36_0667.html -3351ff0e 37734301 0 0 html/r36_0668.html -3351ff0e 6ecf1905 0 0 html/r36_0669.html -3351ff0e 502a8076 0 0 html/r36_0670.html -3351ff0e 6480bef7 0 0 html/r36_0671.html -3351ff0e 5b6c40bb 0 0 html/r36_0672.html -3351ff0e 21fbf138 0 0 html/r36_0673.html -3351ff0e 6764b9fa 0 0 html/r36_0674.html -3351ff0e 5950e26b 0 0 html/r36_0675.html -3351ff0e 3a3f7f5d 0 0 html/r36_0676.html -3351ff0e 06ceeef3 0 0 html/r36_0677.html -3351ff0e 0db65421 0 0 html/r36_0678.html -3351ff0e 3a9175ea 0 0 html/r36_0679.html -3351ff0e 589dedc1 0 0 html/r36_0680.html -3351ff0e 657771eb 0 0 html/r36_0681.html -3351ff0e 28f662c8 0 0 html/r36_0682.html -3351ff1a 1381b754 0 0 html/r36_idx.html -3326c25e 0138986e 0 0 minitex.red -335124f2 2c9e6abe 0 0 mkhelpw.bat -3351f3c8 225cdbdb 0 0 mkhelpw.log -33512d36 6534818c 0 0 mkhelpw.red -33513e96 1b6a021f 0 0 mkhtml.bat -3351ff26 51d3f0e8 0 0 mkhtml.log -335140a6 6b134969 0 0 mkhtml.red -335124ac 045114e3 0 0 mkinfo.bat -3351fe62 62b66d70 0 0 mkinfo.log -33511920 0ac72de6 0 0 mkinfo.red -3351ff26 54b42256 0 0 r36.hdx -3351f402 09860b36 0 1 r36.hlp -3327d0ba 2c77a408 0 0 r36.hpj -3351f3de 677880c6 0 0 r36.ph -3351fe94 0cbd9f57 0 0 redhelp.inf -3351f3c8 451ad691 0 0 redhelp.rtf -3351fe92 1e5c4020 0 0 sed.log -33511944 283df8f4 0 0 sed.red +EXPORT: Signatures 13-Dec-1995.10:03:00 <@@@@DGG@@JGD> +334f5664 668dead6 0 0 comphelp.red +334f5cb8 11111111 0 0 export.chk +334f5cb0 7379df02 0 0 export.pat +33516222 73e22f17 0 0 helphtml.red +334f7514 36f40873 0 0 helpunx.red +3350cba6 081c3bd0 0 0 helpwin.red +33513144 00000000 1 0 html +3351ff0e 71e410f7 0 0 html/r36.html +3351fed6 2a361437 0 0 html/r36_0001.html +3351fed6 3f8c974b 0 0 html/r36_0002.html +3351fed6 0f70f2a9 0 0 html/r36_0003.html +3351fed6 634241c9 0 0 html/r36_0004.html +3351fed6 3429fba4 0 0 html/r36_0005.html +3351fed6 2ea15831 0 0 html/r36_0006.html +3351fed6 58483e30 0 0 html/r36_0007.html +3351fed6 5fc1f2d8 0 0 html/r36_0008.html +3351fed6 1b93d3bf 0 0 html/r36_0009.html +3351fed6 4a5fe382 0 0 html/r36_0010.html +3351fed6 731f1c9b 0 0 html/r36_0011.html +3351fed6 27338ccc 0 0 html/r36_0012.html +3351fed6 3d9c9356 0 0 html/r36_0013.html +3351fed6 55d2fc9c 0 0 html/r36_0014.html +3351fed6 1bc7e511 0 0 html/r36_0015.html +3351fed6 4b27bbc5 0 0 html/r36_0016.html +3351fed8 78ce9a10 0 0 html/r36_0017.html +3351fed8 32c32073 0 0 html/r36_0018.html +3351fed8 79ff8d3b 0 0 html/r36_0019.html +3351fed8 00410671 0 0 html/r36_0020.html +3351fed8 4aa16a66 0 0 html/r36_0021.html +3351fed8 37723174 0 0 html/r36_0022.html +3351fed8 486713d3 0 0 html/r36_0023.html +3351fed8 138acc22 0 0 html/r36_0024.html +3351fed8 4f4fc836 0 0 html/r36_0025.html +3351fed8 5e603dc9 0 0 html/r36_0026.html +3351fed8 16145976 0 0 html/r36_0027.html +3351fed8 636aa7ca 0 0 html/r36_0028.html +3351fed8 6700a6f6 0 0 html/r36_0029.html +3351fed8 1e0a1718 0 0 html/r36_0030.html +3351fed8 3e5723ac 0 0 html/r36_0031.html +3351fed8 196a3168 0 0 html/r36_0032.html +3351fed8 0d43897e 0 0 html/r36_0033.html +3351fed8 4e36e3bd 0 0 html/r36_0034.html +3351fed8 43e4b024 0 0 html/r36_0035.html +3351fed8 48c79df7 0 0 html/r36_0036.html +3351fed8 55ad050c 0 0 html/r36_0037.html +3351fed8 53643130 0 0 html/r36_0038.html +3351feda 1f21bbce 0 0 html/r36_0039.html +3351feda 5e3c2912 0 0 html/r36_0040.html +3351feda 135a27d1 0 0 html/r36_0041.html +3351feda 54ea4370 0 0 html/r36_0042.html +3351feda 0c0e1ff7 0 0 html/r36_0043.html +3351feda 23c89fdd 0 0 html/r36_0044.html +3351feda 7fbaba46 0 0 html/r36_0045.html +3351feda 5dafc08f 0 0 html/r36_0046.html +3351feda 639fa8cc 0 0 html/r36_0047.html +3351feda 0c8f7a8b 0 0 html/r36_0048.html +3351feda 3e1e4113 0 0 html/r36_0049.html +3351feda 46811fec 0 0 html/r36_0050.html +3351feda 24e8cab5 0 0 html/r36_0051.html +3351feda 65aa1dc6 0 0 html/r36_0052.html +3351feda 493642f7 0 0 html/r36_0053.html +3351feda 0d5ebc10 0 0 html/r36_0054.html +3351fedc 7d338010 0 0 html/r36_0055.html +3351fedc 31e75c0d 0 0 html/r36_0056.html +3351fedc 782183aa 0 0 html/r36_0057.html +3351fedc 49d050e9 0 0 html/r36_0058.html +3351fedc 6c9981f6 0 0 html/r36_0059.html +3351fedc 369fb96b 0 0 html/r36_0060.html +3351fedc 1ded9cbc 0 0 html/r36_0061.html +3351fedc 21912cdf 0 0 html/r36_0062.html +3351fedc 5e883609 0 0 html/r36_0063.html +3351fedc 4bf914f6 0 0 html/r36_0064.html +3351fedc 66a20a14 0 0 html/r36_0065.html +3351fedc 514e7342 0 0 html/r36_0066.html +3351fedc 5ab28831 0 0 html/r36_0067.html +3351fedc 64ee5bf3 0 0 html/r36_0068.html +3351fedc 2e1b4ab7 0 0 html/r36_0069.html +3351fedc 38d7ca15 0 0 html/r36_0070.html +3351fedc 29a01022 0 0 html/r36_0071.html +3351fedc 1596d460 0 0 html/r36_0072.html +3351fedc 6741ce23 0 0 html/r36_0073.html +3351fedc 71624ff0 0 0 html/r36_0074.html +3351fedc 42f8efe3 0 0 html/r36_0075.html +3351fedc 3c2ef867 0 0 html/r36_0076.html +3351fedc 2aa5a787 0 0 html/r36_0077.html +3351fede 1b430c01 0 0 html/r36_0078.html +3351fede 22865d46 0 0 html/r36_0079.html +3351fede 7620fe90 0 0 html/r36_0080.html +3351fede 62af8400 0 0 html/r36_0081.html +3351fede 0d72b2f6 0 0 html/r36_0082.html +3351fede 2b4a10a5 0 0 html/r36_0083.html +3351fede 72121841 0 0 html/r36_0084.html +3351fede 4a05771e 0 0 html/r36_0085.html +3351fede 36f1b441 0 0 html/r36_0086.html +3351fede 0ad01253 0 0 html/r36_0087.html +3351fede 642959b7 0 0 html/r36_0088.html +3351fede 3a72e3be 0 0 html/r36_0089.html +3351fede 06aacffa 0 0 html/r36_0090.html +3351fede 6ce64be7 0 0 html/r36_0091.html +3351fede 1706e850 0 0 html/r36_0092.html +3351fede 687a8ee2 0 0 html/r36_0093.html +3351fede 6ec96ce4 0 0 html/r36_0094.html +3351fede 2ef60b83 0 0 html/r36_0095.html +3351fede 30b66e28 0 0 html/r36_0096.html +3351fede 0573ab0d 0 0 html/r36_0097.html +3351fede 43cc0d65 0 0 html/r36_0098.html +3351fede 646739fd 0 0 html/r36_0099.html +3351fede 0878e75c 0 0 html/r36_0100.html +3351fede 72c835e2 0 0 html/r36_0101.html +3351fede 0f03cf09 0 0 html/r36_0102.html +3351fede 758ae9ea 0 0 html/r36_0103.html +3351fede 74e99fa1 0 0 html/r36_0104.html +3351fede 4862237f 0 0 html/r36_0105.html +3351fee0 40743915 0 0 html/r36_0106.html +3351fee0 044c71cf 0 0 html/r36_0107.html +3351fee0 08995257 0 0 html/r36_0108.html +3351fee0 0274617a 0 0 html/r36_0109.html +3351fee0 27a54d37 0 0 html/r36_0110.html +3351fee0 1972920c 0 0 html/r36_0111.html +3351fee0 6732d0d8 0 0 html/r36_0112.html +3351fee0 7e765bc0 0 0 html/r36_0113.html +3351fee0 09316b02 0 0 html/r36_0114.html +3351fee0 592eae61 0 0 html/r36_0115.html +3351fee0 3fb638f5 0 0 html/r36_0116.html +3351fee0 11c86628 0 0 html/r36_0117.html +3351fee0 44e3a546 0 0 html/r36_0118.html +3351fee0 546d68bf 0 0 html/r36_0119.html +3351fee0 6d94e9f5 0 0 html/r36_0120.html +3351fee0 3e8400aa 0 0 html/r36_0121.html +3351fee0 089128c9 0 0 html/r36_0122.html +3351fee0 739af7cf 0 0 html/r36_0123.html +3351fee0 4e684cff 0 0 html/r36_0124.html +3351fee0 6ff33528 0 0 html/r36_0125.html +3351fee0 59025b76 0 0 html/r36_0126.html +3351fee0 2b7fee84 0 0 html/r36_0127.html +3351fee2 15c489e0 0 0 html/r36_0128.html +3351fee2 0fc570b5 0 0 html/r36_0129.html +3351fee2 2a646562 0 0 html/r36_0130.html +3351fee2 73a1b4c8 0 0 html/r36_0131.html +3351fee2 7c6a831e 0 0 html/r36_0132.html +3351fee2 764301ba 0 0 html/r36_0133.html +3351fee2 394d1d73 0 0 html/r36_0134.html +3351fee2 27c81033 0 0 html/r36_0135.html +3351fee2 438fc672 0 0 html/r36_0136.html +3351fee2 510576ec 0 0 html/r36_0137.html +3351fee2 3aeabc78 0 0 html/r36_0138.html +3351fee2 5184fbc9 0 0 html/r36_0139.html +3351fee2 0743089c 0 0 html/r36_0140.html +3351fee2 3558e4c9 0 0 html/r36_0141.html +3351fee2 3b01520e 0 0 html/r36_0142.html +3351fee2 39134d74 0 0 html/r36_0143.html +3351fee2 25a53910 0 0 html/r36_0144.html +3351fee2 71706c8d 0 0 html/r36_0145.html +3351fee2 2e4354e7 0 0 html/r36_0146.html +3351fee2 08d6b254 0 0 html/r36_0147.html +3351fee2 76105ff6 0 0 html/r36_0148.html +3351fee2 4beb3c08 0 0 html/r36_0149.html +3351fee2 4092a200 0 0 html/r36_0150.html +3351fee4 5b43dffe 0 0 html/r36_0151.html +3351fee4 5dc4d5ac 0 0 html/r36_0152.html +3351fee4 37a31e64 0 0 html/r36_0153.html +3351fee4 29c6eb17 0 0 html/r36_0154.html +3351fee4 5f0b1542 0 0 html/r36_0155.html +3351fee4 3dd47aa3 0 0 html/r36_0156.html +3351fee4 3e657577 0 0 html/r36_0157.html +3351fee4 02201574 0 0 html/r36_0158.html +3351fee4 62702c0b 0 0 html/r36_0159.html +3351fee4 67396757 0 0 html/r36_0160.html +3351fee4 36b668df 0 0 html/r36_0161.html +3351fee4 0d1ecb8c 0 0 html/r36_0162.html +3351fee4 662009cf 0 0 html/r36_0163.html +3351fee4 76c089b8 0 0 html/r36_0164.html +3351fee4 1adeedfc 0 0 html/r36_0165.html +3351fee4 63bfce63 0 0 html/r36_0166.html +3351fee4 0f649b82 0 0 html/r36_0167.html +3351fee4 718d5e9a 0 0 html/r36_0168.html +3351fee4 75a03e1b 0 0 html/r36_0169.html +3351fee4 5bf506c4 0 0 html/r36_0170.html +3351fee4 661eb2e3 0 0 html/r36_0171.html +3351fee6 0a54fcf7 0 0 html/r36_0172.html +3351fee6 566a41d1 0 0 html/r36_0173.html +3351fee6 4550ea71 0 0 html/r36_0174.html +3351fee6 615c151c 0 0 html/r36_0175.html +3351fee6 575b491a 0 0 html/r36_0176.html +3351fee6 72b85eaf 0 0 html/r36_0177.html +3351fee6 74376e38 0 0 html/r36_0178.html +3351fee6 75391356 0 0 html/r36_0179.html +3351fee6 63645963 0 0 html/r36_0180.html +3351fee6 40970afc 0 0 html/r36_0181.html +3351fee6 560b7a3e 0 0 html/r36_0182.html +3351fee6 43de8d0f 0 0 html/r36_0183.html +3351fee8 4c1926e4 0 0 html/r36_0184.html +3351fee8 5c23a084 0 0 html/r36_0185.html +3351fee8 3066c527 0 0 html/r36_0186.html +3351fee8 1dd35f7c 0 0 html/r36_0187.html +3351fee8 22fcb928 0 0 html/r36_0188.html +3351fee8 1ceca5b2 0 0 html/r36_0189.html +3351fee8 7e536ada 0 0 html/r36_0190.html +3351fee8 3436a7f6 0 0 html/r36_0191.html +3351fee8 054f82de 0 0 html/r36_0192.html +3351fee8 141ffa5a 0 0 html/r36_0193.html +3351fee8 3e5b1c14 0 0 html/r36_0194.html +3351fee8 7fd6c734 0 0 html/r36_0195.html +3351fee8 255fc2e8 0 0 html/r36_0196.html +3351fee8 0329cd7c 0 0 html/r36_0197.html +3351fee8 786df66a 0 0 html/r36_0198.html +3351feea 649ea591 0 0 html/r36_0199.html +3351feea 15e148e8 0 0 html/r36_0200.html +3351feea 78782c8b 0 0 html/r36_0201.html +3351feea 0bc67a2f 0 0 html/r36_0202.html +3351feea 5367764c 0 0 html/r36_0203.html +3351feea 5a955f45 0 0 html/r36_0204.html +3351feea 15529288 0 0 html/r36_0205.html +3351feea 2a81b009 0 0 html/r36_0206.html +3351feea 4c2a33d3 0 0 html/r36_0207.html +3351feea 446e2705 0 0 html/r36_0208.html +3351feea 732f6fff 0 0 html/r36_0209.html +3351feea 13534f39 0 0 html/r36_0210.html +3351feea 43146fa1 0 0 html/r36_0211.html +3351feea 1347a6a7 0 0 html/r36_0212.html +3351feea 38cde0a8 0 0 html/r36_0213.html +3351feea 14471003 0 0 html/r36_0214.html +3351feea 7ba1b715 0 0 html/r36_0215.html +3351feea 692bd3e5 0 0 html/r36_0216.html +3351feea 6ac14eb6 0 0 html/r36_0217.html +3351feea 4db82a4a 0 0 html/r36_0218.html +3351feea 1eb40efa 0 0 html/r36_0219.html +3351feea 4aac3eee 0 0 html/r36_0220.html +3351feea 5da53ca8 0 0 html/r36_0221.html +3351feec 4f7ace4e 0 0 html/r36_0222.html +3351feec 3c61f971 0 0 html/r36_0223.html +3351feec 114884a4 0 0 html/r36_0224.html +3351feec 189a5561 0 0 html/r36_0225.html +3351feec 79725048 0 0 html/r36_0226.html +3351feec 79ec0d54 0 0 html/r36_0227.html +3351feec 1ab58c44 0 0 html/r36_0228.html +3351feec 7ae5cf58 0 0 html/r36_0229.html +3351feec 2161e8d0 0 0 html/r36_0230.html +3351feec 2ae5a206 0 0 html/r36_0231.html +3351feec 7b8da4aa 0 0 html/r36_0232.html +3351feec 24077de8 0 0 html/r36_0233.html +3351feec 4cda87ea 0 0 html/r36_0234.html +3351feec 0200348b 0 0 html/r36_0235.html +3351feec 0ca197be 0 0 html/r36_0236.html +3351feec 16f67880 0 0 html/r36_0237.html +3351feec 1e8d5af6 0 0 html/r36_0238.html +3351feec 31db0a34 0 0 html/r36_0239.html +3351feec 3d8c422e 0 0 html/r36_0240.html +3351feec 2ce974bd 0 0 html/r36_0241.html +3351feee 469f2dec 0 0 html/r36_0242.html +3351feee 69bc5ad1 0 0 html/r36_0243.html +3351feee 42b67c0f 0 0 html/r36_0244.html +3351feee 55b46ad3 0 0 html/r36_0245.html +3351feee 79c903c0 0 0 html/r36_0246.html +3351feee 2ce2aea3 0 0 html/r36_0247.html +3351feee 5fa7a21d 0 0 html/r36_0248.html +3351feee 6f2c4b1d 0 0 html/r36_0249.html +3351feee 14dd3b77 0 0 html/r36_0250.html +3351feee 5eeae40b 0 0 html/r36_0251.html +3351feee 16ca5935 0 0 html/r36_0252.html +3351feee 3b904908 0 0 html/r36_0253.html +3351feee 1f1dce9c 0 0 html/r36_0254.html +3351feee 3ff598f7 0 0 html/r36_0255.html +3351feee 120d58c0 0 0 html/r36_0256.html +3351feee 67334baa 0 0 html/r36_0257.html +3351feee 68e6527f 0 0 html/r36_0258.html +3351feee 1ef1f10d 0 0 html/r36_0259.html +3351feee 0ed23fb5 0 0 html/r36_0260.html +3351feee 341585f8 0 0 html/r36_0261.html +3351feee 3a043d53 0 0 html/r36_0262.html +3351feee 5e932d3b 0 0 html/r36_0263.html +3351feee 1634772e 0 0 html/r36_0264.html +3351feee 61006327 0 0 html/r36_0265.html +3351feee 1abddb94 0 0 html/r36_0266.html +3351feee 782aa216 0 0 html/r36_0267.html +3351fef0 0dfb9304 0 0 html/r36_0268.html +3351fef0 05de0184 0 0 html/r36_0269.html +3351fef0 53f392de 0 0 html/r36_0270.html +3351fef0 4cd38871 0 0 html/r36_0271.html +3351fef0 273ec5a9 0 0 html/r36_0272.html +3351fef0 02c20ca2 0 0 html/r36_0273.html +3351fef0 44b9f7b1 0 0 html/r36_0274.html +3351fef0 20e50bb8 0 0 html/r36_0275.html +3351fef0 3baa2673 0 0 html/r36_0276.html +3351fef0 0afd1c2b 0 0 html/r36_0277.html +3351fef0 68de9007 0 0 html/r36_0278.html +3351fef0 4e01f889 0 0 html/r36_0279.html +3351fef0 4aa41101 0 0 html/r36_0280.html +3351fef0 507dc4c7 0 0 html/r36_0281.html +3351fef0 7dbe341c 0 0 html/r36_0282.html +3351fef0 5dd2eee3 0 0 html/r36_0283.html +3351fef0 500e9477 0 0 html/r36_0284.html +3351fef0 19053ee0 0 0 html/r36_0285.html +3351fef0 7adbeb6a 0 0 html/r36_0286.html +3351fef0 0c28b6dc 0 0 html/r36_0287.html +3351fef0 6c6bfc74 0 0 html/r36_0288.html +3351fef2 5e420f23 0 0 html/r36_0289.html +3351fef2 3e219e7c 0 0 html/r36_0290.html +3351fef2 5b068515 0 0 html/r36_0291.html +3351fef2 3cb9e895 0 0 html/r36_0292.html +3351fef2 3c18ab54 0 0 html/r36_0293.html +3351fef2 02f19110 0 0 html/r36_0294.html +3351fef2 4f649ec3 0 0 html/r36_0295.html +3351fef2 0b55d96a 0 0 html/r36_0296.html +3351fef2 146d1736 0 0 html/r36_0297.html +3351fef2 1905ec2c 0 0 html/r36_0298.html +3351fef2 4b11a9e8 0 0 html/r36_0299.html +3351fef2 5d40a3b0 0 0 html/r36_0300.html +3351fef2 7402b314 0 0 html/r36_0301.html +3351fef2 7e92838b 0 0 html/r36_0302.html +3351fef2 7255ad8d 0 0 html/r36_0303.html +3351fef4 77e814d3 0 0 html/r36_0304.html +3351fef4 71aeeba3 0 0 html/r36_0305.html +3351fef4 4f4ff58b 0 0 html/r36_0306.html +3351fef4 4326743a 0 0 html/r36_0307.html +3351fef4 03ae9fd2 0 0 html/r36_0308.html +3351fef4 5dd12581 0 0 html/r36_0309.html +3351fef4 723da7aa 0 0 html/r36_0310.html +3351fef4 447e3575 0 0 html/r36_0311.html +3351fef4 6bff5e12 0 0 html/r36_0312.html +3351fef4 31b6f001 0 0 html/r36_0313.html +3351fef4 3b019d88 0 0 html/r36_0314.html +3351fef4 6e667bcc 0 0 html/r36_0315.html +3351fef4 67dc73d2 0 0 html/r36_0316.html +3351fef4 349aaac4 0 0 html/r36_0317.html +3351fef4 41087618 0 0 html/r36_0318.html +3351fef4 5f019bb3 0 0 html/r36_0319.html +3351fef4 42a88f05 0 0 html/r36_0320.html +3351fef4 50bbf153 0 0 html/r36_0321.html +3351fef4 5c1f8ad6 0 0 html/r36_0322.html +3351fef4 1f4ed70f 0 0 html/r36_0323.html +3351fef4 183cb53d 0 0 html/r36_0324.html +3351fef4 5d95a1b1 0 0 html/r36_0325.html +3351fef4 70dbf57e 0 0 html/r36_0326.html +3351fef4 31591666 0 0 html/r36_0327.html +3351fef4 758499cd 0 0 html/r36_0328.html +3351fef4 09dd2098 0 0 html/r36_0329.html +3351fef4 292fb449 0 0 html/r36_0330.html +3351fef6 5a8cf131 0 0 html/r36_0331.html +3351fef6 501f1d86 0 0 html/r36_0332.html +3351fef6 2de34f77 0 0 html/r36_0333.html +3351fef6 73e98a78 0 0 html/r36_0334.html +3351fef6 7b75f76e 0 0 html/r36_0335.html +3351fef6 22d08041 0 0 html/r36_0336.html +3351fef6 4a99d178 0 0 html/r36_0337.html +3351fef6 023314a5 0 0 html/r36_0338.html +3351fef6 3017c4fe 0 0 html/r36_0339.html +3351fef6 3c0ff92a 0 0 html/r36_0340.html +3351fef6 4b435b82 0 0 html/r36_0341.html +3351fef6 1fb0ae3e 0 0 html/r36_0342.html +3351fef6 095be64f 0 0 html/r36_0343.html +3351fef6 53b238b2 0 0 html/r36_0344.html +3351fef6 78563a5e 0 0 html/r36_0345.html +3351fef6 2e749ab4 0 0 html/r36_0346.html +3351fef6 7c0b143c 0 0 html/r36_0347.html +3351fef6 09f867ff 0 0 html/r36_0348.html +3351fef6 6d9cbf9b 0 0 html/r36_0349.html +3351fef6 5c5facec 0 0 html/r36_0350.html +3351fef6 49858db9 0 0 html/r36_0351.html +3351fef8 7b8b2833 0 0 html/r36_0352.html +3351fef8 79d48e05 0 0 html/r36_0353.html +3351fef8 0a830deb 0 0 html/r36_0354.html +3351fef8 1e6d08b3 0 0 html/r36_0355.html +3351fef8 20ead4d8 0 0 html/r36_0356.html +3351fef8 267deb98 0 0 html/r36_0357.html +3351fef8 37bf3fc8 0 0 html/r36_0358.html +3351fef8 7a69dbcd 0 0 html/r36_0359.html +3351fef8 2fe3042a 0 0 html/r36_0360.html +3351fef8 5606000f 0 0 html/r36_0361.html +3351fef8 49c4b21b 0 0 html/r36_0362.html +3351fef8 7082acf0 0 0 html/r36_0363.html +3351fef8 389798ca 0 0 html/r36_0364.html +3351fef8 5841ba0f 0 0 html/r36_0365.html +3351fef8 171fa8f2 0 0 html/r36_0366.html +3351fef8 6265346e 0 0 html/r36_0367.html +3351fef8 62650611 0 0 html/r36_0368.html +3351fef8 6df1b688 0 0 html/r36_0369.html +3351fef8 6630c7e2 0 0 html/r36_0370.html +3351fef8 5feab9df 0 0 html/r36_0371.html +3351fef8 2a54b9f1 0 0 html/r36_0372.html +3351fef8 2f9c388c 0 0 html/r36_0373.html +3351fef8 500f0bdb 0 0 html/r36_0374.html +3351fef8 1f46c6c8 0 0 html/r36_0375.html +3351fef8 57327ddb 0 0 html/r36_0376.html +3351fef8 568b05d5 0 0 html/r36_0377.html +3351fef8 4a0f8c48 0 0 html/r36_0378.html +3351fef8 19fa735f 0 0 html/r36_0379.html +3351fef8 4e895435 0 0 html/r36_0380.html +3351fef8 45442e58 0 0 html/r36_0381.html +3351fefa 0e7a7541 0 0 html/r36_0382.html +3351fefa 4fa16ea8 0 0 html/r36_0383.html +3351fefa 49c71091 0 0 html/r36_0384.html +3351fefa 4e8ebac0 0 0 html/r36_0385.html +3351fefa 1142aedd 0 0 html/r36_0386.html +3351fefa 6ba5213c 0 0 html/r36_0387.html +3351fefa 231db237 0 0 html/r36_0388.html +3351fefa 2f37a074 0 0 html/r36_0389.html +3351fefa 6b79a0bc 0 0 html/r36_0390.html +3351fefa 46db2126 0 0 html/r36_0391.html +3351fefa 4bd767a4 0 0 html/r36_0392.html +3351fefa 76e352d6 0 0 html/r36_0393.html +3351fefa 0b7253ba 0 0 html/r36_0394.html +3351fefa 308b364f 0 0 html/r36_0395.html +3351fefa 651830c6 0 0 html/r36_0396.html +3351fefa 03d4b766 0 0 html/r36_0397.html +3351fefa 7fb91770 0 0 html/r36_0398.html +3351fefa 40ffc96e 0 0 html/r36_0399.html +3351fefa 6b249eeb 0 0 html/r36_0400.html +3351fefa 6c8c4d40 0 0 html/r36_0401.html +3351fefa 1b299584 0 0 html/r36_0402.html +3351fefa 41959185 0 0 html/r36_0403.html +3351fefa 571cc82d 0 0 html/r36_0404.html +3351fefa 44029603 0 0 html/r36_0405.html +3351fefa 328e9ef0 0 0 html/r36_0406.html +3351fefa 27c1b8ec 0 0 html/r36_0407.html +3351fefa 21f3420c 0 0 html/r36_0408.html +3351fefa 1e8e651e 0 0 html/r36_0409.html +3351fefa 0e1e8247 0 0 html/r36_0410.html +3351fefa 49bee135 0 0 html/r36_0411.html +3351fefa 70d474b9 0 0 html/r36_0412.html +3351fefa 01f25f0f 0 0 html/r36_0413.html +3351fefc 55e37521 0 0 html/r36_0414.html +3351fefc 6e1a1196 0 0 html/r36_0415.html +3351fefc 646e5e12 0 0 html/r36_0416.html +3351fefc 28a11d17 0 0 html/r36_0417.html +3351fefc 4ae6b048 0 0 html/r36_0418.html +3351fefc 0ee41cd3 0 0 html/r36_0419.html +3351fefc 0f27456a 0 0 html/r36_0420.html +3351fefc 69094b65 0 0 html/r36_0421.html +3351fefc 13dafd18 0 0 html/r36_0422.html +3351fefc 3a481deb 0 0 html/r36_0423.html +3351fefc 1c166fd5 0 0 html/r36_0424.html +3351fefc 1a482d4c 0 0 html/r36_0425.html +3351fefc 18378de0 0 0 html/r36_0426.html +3351fefc 54762a24 0 0 html/r36_0427.html +3351fefc 384d0f0b 0 0 html/r36_0428.html +3351fefc 127c95d2 0 0 html/r36_0429.html +3351fefc 0e5d4bea 0 0 html/r36_0430.html +3351fefc 70583575 0 0 html/r36_0431.html +3351fefc 2bfcc8b5 0 0 html/r36_0432.html +3351fefc 7c399734 0 0 html/r36_0433.html +3351fefc 40372cad 0 0 html/r36_0434.html +3351fefc 761a8cee 0 0 html/r36_0435.html +3351fefc 1084ca4a 0 0 html/r36_0436.html +3351fefc 37f296e3 0 0 html/r36_0437.html +3351fefc 038f3036 0 0 html/r36_0438.html +3351fefe 73db3e63 0 0 html/r36_0439.html +3351fefe 6d81cc09 0 0 html/r36_0440.html +3351fefe 0586ddc8 0 0 html/r36_0441.html +3351fefe 15f4ded4 0 0 html/r36_0442.html +3351fefe 19337663 0 0 html/r36_0443.html +3351fefe 56ef60ce 0 0 html/r36_0444.html +3351fefe 2921774a 0 0 html/r36_0445.html +3351fefe 2a6dc51e 0 0 html/r36_0446.html +3351fefe 26faa403 0 0 html/r36_0447.html +3351fefe 4a9cc510 0 0 html/r36_0448.html +3351fefe 7bafe007 0 0 html/r36_0449.html +3351fefe 00e11861 0 0 html/r36_0450.html +3351fefe 6374ed69 0 0 html/r36_0451.html +3351fefe 0aef7f1f 0 0 html/r36_0452.html +3351fefe 7f074ce0 0 0 html/r36_0453.html +3351fefe 1911fbb4 0 0 html/r36_0454.html +3351fefe 13a33d6c 0 0 html/r36_0455.html +3351fefe 7eee8ec2 0 0 html/r36_0456.html +3351fefe 587d39ff 0 0 html/r36_0457.html +3351fefe 6abb0f00 0 0 html/r36_0458.html +3351fefe 15664ea6 0 0 html/r36_0459.html +3351fefe 78147daa 0 0 html/r36_0460.html +3351fefe 5ec66036 0 0 html/r36_0461.html +3351fefe 6b246b3a 0 0 html/r36_0462.html +3351fefe 3683f508 0 0 html/r36_0463.html +3351fefe 332cb244 0 0 html/r36_0464.html +3351fefe 2120f561 0 0 html/r36_0465.html +3351fefe 436ef325 0 0 html/r36_0466.html +3351fefe 35443271 0 0 html/r36_0467.html +3351fefe 213aaa7b 0 0 html/r36_0468.html +3351fefe 21b4dd9b 0 0 html/r36_0469.html +3351fefe 15eb7ac0 0 0 html/r36_0470.html +3351fefe 6743d4bf 0 0 html/r36_0471.html +3351fefe 4fc03749 0 0 html/r36_0472.html +3351fefe 6aa9e3cb 0 0 html/r36_0473.html +3351fefe 1c9c1c80 0 0 html/r36_0474.html +3351fefe 359f0e18 0 0 html/r36_0475.html +3351fefe 02466f9d 0 0 html/r36_0476.html +3351fefe 2fb818fe 0 0 html/r36_0477.html +3351fefe 1eda0740 0 0 html/r36_0478.html +3351fefe 16b8e48f 0 0 html/r36_0479.html +3351ff00 680e6873 0 0 html/r36_0480.html +3351ff00 1fad2f96 0 0 html/r36_0481.html +3351ff00 67503431 0 0 html/r36_0482.html +3351ff00 7568e801 0 0 html/r36_0483.html +3351ff00 28b8aef3 0 0 html/r36_0484.html +3351ff00 20ac4022 0 0 html/r36_0485.html +3351ff00 4ee2fada 0 0 html/r36_0486.html +3351ff00 53ac2c88 0 0 html/r36_0487.html +3351ff00 058ba857 0 0 html/r36_0488.html +3351ff00 61caeb60 0 0 html/r36_0489.html +3351ff00 39b23003 0 0 html/r36_0490.html +3351ff00 3d24aa88 0 0 html/r36_0491.html +3351ff00 64cf4ead 0 0 html/r36_0492.html +3351ff00 5401dbbc 0 0 html/r36_0493.html +3351ff00 56ed6edd 0 0 html/r36_0494.html +3351ff00 2804ed69 0 0 html/r36_0495.html +3351ff00 69d03294 0 0 html/r36_0496.html +3351ff00 5a82143b 0 0 html/r36_0497.html +3351ff00 7111ddf6 0 0 html/r36_0498.html +3351ff00 63d5264c 0 0 html/r36_0499.html +3351ff00 3e5cbdf1 0 0 html/r36_0500.html +3351ff00 611e8d09 0 0 html/r36_0501.html +3351ff00 6e172d51 0 0 html/r36_0502.html +3351ff00 06e94019 0 0 html/r36_0503.html +3351ff00 1cd0ff47 0 0 html/r36_0504.html +3351ff00 48e2d9f2 0 0 html/r36_0505.html +3351ff00 12f19343 0 0 html/r36_0506.html +3351ff00 7b9e96a5 0 0 html/r36_0507.html +3351ff00 2713aa95 0 0 html/r36_0508.html +3351ff02 77ba7849 0 0 html/r36_0509.html +3351ff02 25c0487d 0 0 html/r36_0510.html +3351ff02 46be1a24 0 0 html/r36_0511.html +3351ff02 5673d210 0 0 html/r36_0512.html +3351ff02 38ccd99e 0 0 html/r36_0513.html +3351ff02 35828322 0 0 html/r36_0514.html +3351ff02 52a2bf7e 0 0 html/r36_0515.html +3351ff02 4cbf9822 0 0 html/r36_0516.html +3351ff02 22303dfd 0 0 html/r36_0517.html +3351ff02 7f5e393f 0 0 html/r36_0518.html +3351ff02 56b2287a 0 0 html/r36_0519.html +3351ff02 0357239a 0 0 html/r36_0520.html +3351ff02 7e7f2f26 0 0 html/r36_0521.html +3351ff02 48768c40 0 0 html/r36_0522.html +3351ff02 6b08519f 0 0 html/r36_0523.html +3351ff02 47007ed9 0 0 html/r36_0524.html +3351ff02 0d747faf 0 0 html/r36_0525.html +3351ff02 4035cad5 0 0 html/r36_0526.html +3351ff02 7752ea55 0 0 html/r36_0527.html +3351ff02 3a267b92 0 0 html/r36_0528.html +3351ff02 06f717e8 0 0 html/r36_0529.html +3351ff02 709aa7cd 0 0 html/r36_0530.html +3351ff02 516c2bcd 0 0 html/r36_0531.html +3351ff02 79833cee 0 0 html/r36_0532.html +3351ff02 0a2d1782 0 0 html/r36_0533.html +3351ff02 33a9e4cf 0 0 html/r36_0534.html +3351ff02 1aacae2c 0 0 html/r36_0535.html +3351ff02 6af9b283 0 0 html/r36_0536.html +3351ff04 73207392 0 0 html/r36_0537.html +3351ff04 3939d73b 0 0 html/r36_0538.html +3351ff04 4c9c6f8d 0 0 html/r36_0539.html +3351ff04 157f741b 0 0 html/r36_0540.html +3351ff04 7b775430 0 0 html/r36_0541.html +3351ff04 36fd5f73 0 0 html/r36_0542.html +3351ff04 384a3445 0 0 html/r36_0543.html +3351ff04 4d12f82d 0 0 html/r36_0544.html +3351ff04 53888326 0 0 html/r36_0545.html +3351ff04 4b3ae7b0 0 0 html/r36_0546.html +3351ff04 17a70e49 0 0 html/r36_0547.html +3351ff04 23ffd2ad 0 0 html/r36_0548.html +3351ff04 6ac30d75 0 0 html/r36_0549.html +3351ff04 117efbc6 0 0 html/r36_0550.html +3351ff04 4d6f7c1f 0 0 html/r36_0551.html +3351ff04 50ee5ee4 0 0 html/r36_0552.html +3351ff04 0cc918fc 0 0 html/r36_0553.html +3351ff04 25a43c94 0 0 html/r36_0554.html +3351ff04 5f53d5ed 0 0 html/r36_0555.html +3351ff04 65f81e9d 0 0 html/r36_0556.html +3351ff04 38033dc9 0 0 html/r36_0557.html +3351ff04 698b3314 0 0 html/r36_0558.html +3351ff04 78613977 0 0 html/r36_0559.html +3351ff04 2f625d47 0 0 html/r36_0560.html +3351ff04 46552feb 0 0 html/r36_0561.html +3351ff04 07713eac 0 0 html/r36_0562.html +3351ff04 7a0d4254 0 0 html/r36_0563.html +3351ff04 13b58e2a 0 0 html/r36_0564.html +3351ff04 5a9112bb 0 0 html/r36_0565.html +3351ff04 00bed861 0 0 html/r36_0566.html +3351ff06 05ed2683 0 0 html/r36_0567.html +3351ff06 609a4fca 0 0 html/r36_0568.html +3351ff06 2b99f0dc 0 0 html/r36_0569.html +3351ff06 60d2f416 0 0 html/r36_0570.html +3351ff06 37a03fbf 0 0 html/r36_0571.html +3351ff06 35d81d16 0 0 html/r36_0572.html +3351ff06 1b561ab7 0 0 html/r36_0573.html +3351ff06 69360378 0 0 html/r36_0574.html +3351ff06 441b3c56 0 0 html/r36_0575.html +3351ff06 4e44b09c 0 0 html/r36_0576.html +3351ff06 456ba814 0 0 html/r36_0577.html +3351ff06 09d26004 0 0 html/r36_0578.html +3351ff06 7e87d4be 0 0 html/r36_0579.html +3351ff06 492600b9 0 0 html/r36_0580.html +3351ff06 1f330829 0 0 html/r36_0581.html +3351ff06 277764ac 0 0 html/r36_0582.html +3351ff06 7f343184 0 0 html/r36_0583.html +3351ff06 2261600a 0 0 html/r36_0584.html +3351ff06 7f6e88d0 0 0 html/r36_0585.html +3351ff08 0d173730 0 0 html/r36_0586.html +3351ff08 5e7d5576 0 0 html/r36_0587.html +3351ff08 3c63a15e 0 0 html/r36_0588.html +3351ff08 225120a7 0 0 html/r36_0589.html +3351ff08 7e3dee00 0 0 html/r36_0590.html +3351ff08 6594fdc9 0 0 html/r36_0591.html +3351ff08 316c3ebe 0 0 html/r36_0592.html +3351ff08 2ceeb320 0 0 html/r36_0593.html +3351ff08 671abe39 0 0 html/r36_0594.html +3351ff08 389ab30a 0 0 html/r36_0595.html +3351ff08 2a207346 0 0 html/r36_0596.html +3351ff08 4f779db9 0 0 html/r36_0597.html +3351ff08 77706184 0 0 html/r36_0598.html +3351ff08 1d109cb9 0 0 html/r36_0599.html +3351ff08 6f513500 0 0 html/r36_0600.html +3351ff08 5e0fae8a 0 0 html/r36_0601.html +3351ff08 577f6ae5 0 0 html/r36_0602.html +3351ff08 4ba9acdc 0 0 html/r36_0603.html +3351ff08 79862521 0 0 html/r36_0604.html +3351ff08 1e447c23 0 0 html/r36_0605.html +3351ff08 2591f389 0 0 html/r36_0606.html +3351ff08 60b07451 0 0 html/r36_0607.html +3351ff08 7be7a466 0 0 html/r36_0608.html +3351ff08 4b57bab6 0 0 html/r36_0609.html +3351ff08 0109ad7e 0 0 html/r36_0610.html +3351ff08 20764d61 0 0 html/r36_0611.html +3351ff08 534dc3d2 0 0 html/r36_0612.html +3351ff08 64cfe445 0 0 html/r36_0613.html +3351ff0a 4259b32f 0 0 html/r36_0614.html +3351ff0a 3269c61f 0 0 html/r36_0615.html +3351ff0a 329e3f9d 0 0 html/r36_0616.html +3351ff0a 42aae59c 0 0 html/r36_0617.html +3351ff0a 019efbcb 0 0 html/r36_0618.html +3351ff0a 5861a35c 0 0 html/r36_0619.html +3351ff0a 106e7d3c 0 0 html/r36_0620.html +3351ff0a 02a5eb15 0 0 html/r36_0621.html +3351ff0a 7db1b1c6 0 0 html/r36_0622.html +3351ff0a 3ea52ae5 0 0 html/r36_0623.html +3351ff0a 1a69fb32 0 0 html/r36_0624.html +3351ff0a 5f7785c3 0 0 html/r36_0625.html +3351ff0a 5d0321f7 0 0 html/r36_0626.html +3351ff0a 14d7417b 0 0 html/r36_0627.html +3351ff0a 16a3d795 0 0 html/r36_0628.html +3351ff0a 6257bce1 0 0 html/r36_0629.html +3351ff0c 46626369 0 0 html/r36_0630.html +3351ff0c 4653040c 0 0 html/r36_0631.html +3351ff0c 3cffa3fb 0 0 html/r36_0632.html +3351ff0c 3f67d025 0 0 html/r36_0633.html +3351ff0c 505e9a66 0 0 html/r36_0634.html +3351ff0c 3b804364 0 0 html/r36_0635.html +3351ff0c 5112a45a 0 0 html/r36_0636.html +3351ff0c 6775f99c 0 0 html/r36_0637.html +3351ff0c 1cbf3806 0 0 html/r36_0638.html +3351ff0c 478de809 0 0 html/r36_0639.html +3351ff0c 3b0bc838 0 0 html/r36_0640.html +3351ff0c 6c5df8fa 0 0 html/r36_0641.html +3351ff0c 44a169ec 0 0 html/r36_0642.html +3351ff0c 7c64ece3 0 0 html/r36_0643.html +3351ff0c 29e589f3 0 0 html/r36_0644.html +3351ff0c 11f691c6 0 0 html/r36_0645.html +3351ff0c 54a1e9b4 0 0 html/r36_0646.html +3351ff0c 30b4b0e7 0 0 html/r36_0647.html +3351ff0c 4d129556 0 0 html/r36_0648.html +3351ff0c 41aec3b6 0 0 html/r36_0649.html +3351ff0c 35240532 0 0 html/r36_0650.html +3351ff0c 0a7770af 0 0 html/r36_0651.html +3351ff0c 7d1d2a41 0 0 html/r36_0652.html +3351ff0c 20c06fb2 0 0 html/r36_0653.html +3351ff0c 1bb4b7fb 0 0 html/r36_0654.html +3351ff0c 340f39ef 0 0 html/r36_0655.html +3351ff0c 2bb31dc1 0 0 html/r36_0656.html +3351ff0c 45cd57b0 0 0 html/r36_0657.html +3351ff0c 09fcd5d2 0 0 html/r36_0658.html +3351ff0c 12e242d5 0 0 html/r36_0659.html +3351ff0c 0107d61b 0 0 html/r36_0660.html +3351ff0e 0d60203b 0 0 html/r36_0661.html +3351ff0e 2abd9dbd 0 0 html/r36_0662.html +3351ff0e 3bff79fb 0 0 html/r36_0663.html +3351ff0e 7f59778b 0 0 html/r36_0664.html +3351ff0e 05f1dd99 0 0 html/r36_0665.html +3351ff0e 0dba3aef 0 0 html/r36_0666.html +3351ff0e 15c89d1c 0 0 html/r36_0667.html +3351ff0e 37734301 0 0 html/r36_0668.html +3351ff0e 6ecf1905 0 0 html/r36_0669.html +3351ff0e 502a8076 0 0 html/r36_0670.html +3351ff0e 6480bef7 0 0 html/r36_0671.html +3351ff0e 5b6c40bb 0 0 html/r36_0672.html +3351ff0e 21fbf138 0 0 html/r36_0673.html +3351ff0e 6764b9fa 0 0 html/r36_0674.html +3351ff0e 5950e26b 0 0 html/r36_0675.html +3351ff0e 3a3f7f5d 0 0 html/r36_0676.html +3351ff0e 06ceeef3 0 0 html/r36_0677.html +3351ff0e 0db65421 0 0 html/r36_0678.html +3351ff0e 3a9175ea 0 0 html/r36_0679.html +3351ff0e 589dedc1 0 0 html/r36_0680.html +3351ff0e 657771eb 0 0 html/r36_0681.html +3351ff0e 28f662c8 0 0 html/r36_0682.html +3351ff1a 1381b754 0 0 html/r36_idx.html +3326c25e 0138986e 0 0 minitex.red +335124f2 2c9e6abe 0 0 mkhelpw.bat +3351f3c8 225cdbdb 0 0 mkhelpw.log +33512d36 6534818c 0 0 mkhelpw.red +33513e96 1b6a021f 0 0 mkhtml.bat +3351ff26 51d3f0e8 0 0 mkhtml.log +335140a6 6b134969 0 0 mkhtml.red +335124ac 045114e3 0 0 mkinfo.bat +3351fe62 62b66d70 0 0 mkinfo.log +33511920 0ac72de6 0 0 mkinfo.red +3351ff26 54b42256 0 0 r36.hdx +3351f402 09860b36 0 1 r36.hlp +3327d0ba 2c77a408 0 0 r36.hpj +3351f3de 677880c6 0 0 r36.ph +3351fe94 0cbd9f57 0 0 redhelp.inf +3351f3c8 451ad691 0 0 redhelp.rtf +3351fe92 1e5c4020 0 0 sed.log +33511944 283df8f4 0 0 sed.red Index: r36/mkhelp/EXPORT.PAT ================================================================== --- r36/mkhelp/EXPORT.PAT +++ r36/mkhelp/EXPORT.PAT @@ -1,5 +1,5 @@ -# The file indicates which files in the current directory should -# be exported and which should not. -Omit *.bak -Binary *.exe *.img *.hlp +# The file indicates which files in the current directory should +# be exported and which should not. +Omit *.bak +Binary *.exe *.img *.hlp MixedCase Makefile Index: r36/mkhelp/MKHELPW.RED ================================================================== --- r36/mkhelp/MKHELPW.RED +++ r36/mkhelp/MKHELPW.RED @@ -1,78 +1,78 @@ -% -% This file runs the "*.tex" to "redhelp.rtf" conversion code. As -% well as providing the top level direction to the process it patches up -% for at least some of the places where the conversion code had been -% written in a manner not strongly related to the portability objectives of -% Standard Lisp... -% - -symbolic; -off echo; -on backtrace; -on comp; -!*windows := t; - -fluid '(package); - -package := 'redhelp; - -symbolic procedure inf x; - char!-code x; - -symbolic procedure channellinelength(f, l); - begin - f := wrs f; - l := linelength l; - wrs f; - return l - end; - -symbolic procedure channelprin2(f, x); - begin - f := wrs f; - prin2 x; - wrs f; - return x - end; - -symbolic macro procedure channelprintf u; - begin - scalar g; - g := gensym(); - return list('prog, list g, - list('setq, g, list('wrs, cadr u)), - 'printf . cddr u, - list('wrs, g)) - end; - -symbolic procedure channelterpri f; - begin - f := wrs f; - terpri(); - wrs f; - end; - -symbolic procedure channelreadch f; - begin - scalar c; - f := rds f; - c := readch(); - rds f; - return c - end; - -in "comphelp.red"$ -in "helpwin.red"$ -in "minitex.red"$ - -dir_src := "../help/"; - -job(bldmsg("%w.tex",package),"null.fil"); - -delete!-file "null.fil"; - -job(bldmsg("%w.tex",package),bldmsg("%w.rtf",package)); - -bye; - +% +% This file runs the "*.tex" to "redhelp.rtf" conversion code. As +% well as providing the top level direction to the process it patches up +% for at least some of the places where the conversion code had been +% written in a manner not strongly related to the portability objectives of +% Standard Lisp... +% + +symbolic; +off echo; +on backtrace; +on comp; +!*windows := t; + +fluid '(package); + +package := 'redhelp; + +symbolic procedure inf x; + char!-code x; + +symbolic procedure channellinelength(f, l); + begin + f := wrs f; + l := linelength l; + wrs f; + return l + end; + +symbolic procedure channelprin2(f, x); + begin + f := wrs f; + prin2 x; + wrs f; + return x + end; + +symbolic macro procedure channelprintf u; + begin + scalar g; + g := gensym(); + return list('prog, list g, + list('setq, g, list('wrs, cadr u)), + 'printf . cddr u, + list('wrs, g)) + end; + +symbolic procedure channelterpri f; + begin + f := wrs f; + terpri(); + wrs f; + end; + +symbolic procedure channelreadch f; + begin + scalar c; + f := rds f; + c := readch(); + rds f; + return c + end; + +in "comphelp.red"$ +in "helpwin.red"$ +in "minitex.red"$ + +dir_src := "../help/"; + +job(bldmsg("%w.tex",package),"null.fil"); + +delete!-file "null.fil"; + +job(bldmsg("%w.tex",package),bldmsg("%w.rtf",package)); + +bye; +  Index: r36/mkhelp/MKHTML.RED ================================================================== --- r36/mkhelp/MKHTML.RED +++ r36/mkhelp/MKHTML.RED @@ -1,101 +1,101 @@ -% -% This file runs the "*.tex" to "redhelp.html" conversion code. As -% well as providing the top level direction to the process it patches up -% for at least some of the places where the conversion code had been -% written in a manner not strongly related to the portability objectives of -% Standard Lisp... -% - -symbolic; -off echo; -on backtrace; -on comp; -!*windows := t; - -fluid '(package); - -package := 'redhelp; - -symbolic procedure deletip(a, b); - delete(a, b); - -symbolic procedure inf x; - char!-code x; - -symbolic procedure channellinelength(f, l); - begin - f := wrs f; - l := linelength l; - wrs f; - return l - end; - -symbolic procedure channelprin2(f, x); - begin - f := wrs f; - prin2 x; - wrs f; - return x - end; - -symbolic procedure channelprin2t(f, x); - begin - f := wrs f; - prin2t x; - wrs f; - return x - end; - -symbolic macro procedure channelprintf u; - begin - scalar g; - g := gensym(); - return list('prog, list g, - list('setq, g, list('wrs, cadr u)), - 'printf . cddr u, - list('wrs, g)) - end; - -symbolic procedure channelterpri f; - begin - f := wrs f; - terpri(); - wrs f; - end; - -symbolic procedure channelreadch f; - begin - scalar c; - f := rds f; - c := readch(); - rds f; - return c - end; - -in "comphelp.red"$ -in "helphtml.red"$ -in "minitex.red"$ - -dir_src := "../help/"; - -tr get_label, node, emit_node_label, - emit_node_title, emit_node_browse, emit_node_keys, make_label, - emit_hidden_node_key; - -reset_html(); - -job(bldmsg("%w.tex",package), "null.fil"); - -reset_html(); - -job(bldmsg("%w.tex",package), "null.fil"); - -html_indexfile(); - -LISP_indexfile(); - -delete!-file "null.fil"; - -bye; - +% +% This file runs the "*.tex" to "redhelp.html" conversion code. As +% well as providing the top level direction to the process it patches up +% for at least some of the places where the conversion code had been +% written in a manner not strongly related to the portability objectives of +% Standard Lisp... +% + +symbolic; +off echo; +on backtrace; +on comp; +!*windows := t; + +fluid '(package); + +package := 'redhelp; + +symbolic procedure deletip(a, b); + delete(a, b); + +symbolic procedure inf x; + char!-code x; + +symbolic procedure channellinelength(f, l); + begin + f := wrs f; + l := linelength l; + wrs f; + return l + end; + +symbolic procedure channelprin2(f, x); + begin + f := wrs f; + prin2 x; + wrs f; + return x + end; + +symbolic procedure channelprin2t(f, x); + begin + f := wrs f; + prin2t x; + wrs f; + return x + end; + +symbolic macro procedure channelprintf u; + begin + scalar g; + g := gensym(); + return list('prog, list g, + list('setq, g, list('wrs, cadr u)), + 'printf . cddr u, + list('wrs, g)) + end; + +symbolic procedure channelterpri f; + begin + f := wrs f; + terpri(); + wrs f; + end; + +symbolic procedure channelreadch f; + begin + scalar c; + f := rds f; + c := readch(); + rds f; + return c + end; + +in "comphelp.red"$ +in "helphtml.red"$ +in "minitex.red"$ + +dir_src := "../help/"; + +tr get_label, node, emit_node_label, + emit_node_title, emit_node_browse, emit_node_keys, make_label, + emit_hidden_node_key; + +reset_html(); + +job(bldmsg("%w.tex",package), "null.fil"); + +reset_html(); + +job(bldmsg("%w.tex",package), "null.fil"); + +html_indexfile(); + +LISP_indexfile(); + +delete!-file "null.fil"; + +bye; +  Index: r36/mkhelp/MKINFO.RED ================================================================== --- r36/mkhelp/MKINFO.RED +++ r36/mkhelp/MKINFO.RED @@ -1,73 +1,73 @@ -% -% This file arranges to convert the TEX-formatted Reduce help files -% info GNU-info format. -% - -symbolic; -off echo; -on comp; - -fluid '(package); - -package := 'redhelp; - -symbolic procedure inf x; - char!-code x; - -symbolic procedure channellinelength(f, l); - begin - f := wrs f; - l := linelength l; - wrs f; - return l - end; - -symbolic procedure channelprin2(f, x); - begin - f := wrs f; - prin2 x; - wrs f; - return x - end; - -symbolic macro procedure channelprintf u; - begin - scalar g; - g := gensym(); - return list('prog, list g, - list('setq, g, list('wrs, cadr u)), - 'printf . cddr u, - list('wrs, g)) - end; - -symbolic procedure channelterpri f; - begin - f := wrs f; - terpri(); - wrs f; - end; - -symbolic procedure channelreadch f; - begin - scalar c; - f := rds f; - c := readch(); - rds f; - return c - end; - -in "comphelp.red"$ -in "helpunx.red"$ -in "minitex.red"$ - -dir_src := "../help/"; - -job(bldmsg("%w.tex",package), "null.fil"); - -delete!-file "null.fil"; - -job(bldmsg("%w.tex",package), bldmsg("%w.x",package)); - -bye; - +% +% This file arranges to convert the TEX-formatted Reduce help files +% info GNU-info format. +% + +symbolic; +off echo; +on comp; + +fluid '(package); + +package := 'redhelp; + +symbolic procedure inf x; + char!-code x; + +symbolic procedure channellinelength(f, l); + begin + f := wrs f; + l := linelength l; + wrs f; + return l + end; + +symbolic procedure channelprin2(f, x); + begin + f := wrs f; + prin2 x; + wrs f; + return x + end; + +symbolic macro procedure channelprintf u; + begin + scalar g; + g := gensym(); + return list('prog, list g, + list('setq, g, list('wrs, cadr u)), + 'printf . cddr u, + list('wrs, g)) + end; + +symbolic procedure channelterpri f; + begin + f := wrs f; + terpri(); + wrs f; + end; + +symbolic procedure channelreadch f; + begin + scalar c; + f := rds f; + c := readch(); + rds f; + return c + end; + +in "comphelp.red"$ +in "helpunx.red"$ +in "minitex.red"$ + +dir_src := "../help/"; + +job(bldmsg("%w.tex",package), "null.fil"); + +delete!-file "null.fil"; + +job(bldmsg("%w.tex",package), bldmsg("%w.x",package)); + +bye; +  Index: r36/mkhelp/SED.RED ================================================================== --- r36/mkhelp/SED.RED +++ r36/mkhelp/SED.RED @@ -1,96 +1,96 @@ -% -% This program makes some systematic edits, and some that are clearly -% ad hoc. The syematic changes include expanding tabs and cleaning up -% trailing whitespace, plus processing of some escapes that "info" format -% uses. The ad hoc ones appear to relate to "words" that have embedded -% apostrophes. -% -% It replaces a sequence of Unix-specific commands, which included use of -% expand to dispose of tabs and several uses of sed to perform the other -% transformations. -% It transforms from redhelp.x into redhelp.y -% It will also be MUCH slower than direct use of Unix utilities, in part -% because it has been coded here with simplicity, portability and clarity -% as objectives above speed. After all the help file is not re-created -% by end-users and not altered very often anyway. -% -% A C Norman. December 1995 - -symbolic; -on comp; - -fluid '(edits n_edits); - -edits := for each p in '( - ("Euler's" . "Euler") - ("EULER'S" . "EULER") - ("Euler constant can" . "Euler's constant can") - ("Catalan's" . "Catalan") - ("CATALAN'S" . "CATALAN") - ("Khinchin's" . "Khinchin") - ("KHINCHIN'S" . "KHINCHIN") - ("Khinchin book" . "Khinchin's book") - ("Jacobi's" . "Jacobi") - ("@$" . "$") - ("@key" . "(Key)") - ("@%" . "%") - ("@_" . "_") - ) collect (explode2 car p . explode2 cdr p); - - - -symbolic procedure matches(x, p); - if null p then list x - else if null x then nil - else if car x eq car p then matches(cdr x, cdr p) - else nil; - -symbolic procedure make_edits(); - begin - scalar fi, fo, c, line, n, p, w, t0, n_edits, - !*echo, !*raise, !*lower; - t0 := time(); - fi := open("redhelp.x", 'input); - if null fi then error(0, "Input file not available"); - fo := open("redhelp.y", 'output); - if null fo then error(0, "Output file not available"); - fi := rds fi; - fo := wrs fo; - linelength 1000; % Output must never wrap. - n_edits := 0; - c := !$eol!$; - while not (c = !$eof!$) do << - line := nil; - n := 0; -% While reading a line in I will process tabs, counting a tab as at least -% one blank and then enough to pad out to the next multiple of 8. - while not ((c := readch()) = !$eol!$ or c = !$eof!$) do << - if c = tab!* then << - repeat << line := '! . line; - n := n + 1 >> until zerop remainder(n, 8) >> - else << line := c . line; n := n + 1 >> >>; -% Next I act on 's/ *$//g', which discards trailing blanks. - while eqcar(line, '! ) do line := cdr line; - line := reversip line; - while line do << - for each p in edits do - if (w := matches(line, car p)) then << - n_edits := n_edits + 1; - line := append(cdr p, car w) >>; - prin2 car line; - line := cdr line >>; - terpri() >>; - rds fi; - wrs fo; - close fi; - close fo; - prin2 n_edits; prin2t " edits performed"; - return (time() - t0)/1000.0 - end; - -make_edits(); - -quit; - - +% +% This program makes some systematic edits, and some that are clearly +% ad hoc. The syematic changes include expanding tabs and cleaning up +% trailing whitespace, plus processing of some escapes that "info" format +% uses. The ad hoc ones appear to relate to "words" that have embedded +% apostrophes. +% +% It replaces a sequence of Unix-specific commands, which included use of +% expand to dispose of tabs and several uses of sed to perform the other +% transformations. +% It transforms from redhelp.x into redhelp.y +% It will also be MUCH slower than direct use of Unix utilities, in part +% because it has been coded here with simplicity, portability and clarity +% as objectives above speed. After all the help file is not re-created +% by end-users and not altered very often anyway. +% +% A C Norman. December 1995 + +symbolic; +on comp; + +fluid '(edits n_edits); + +edits := for each p in '( + ("Euler's" . "Euler") + ("EULER'S" . "EULER") + ("Euler constant can" . "Euler's constant can") + ("Catalan's" . "Catalan") + ("CATALAN'S" . "CATALAN") + ("Khinchin's" . "Khinchin") + ("KHINCHIN'S" . "KHINCHIN") + ("Khinchin book" . "Khinchin's book") + ("Jacobi's" . "Jacobi") + ("@$" . "$") + ("@key" . "(Key)") + ("@%" . "%") + ("@_" . "_") + ) collect (explode2 car p . explode2 cdr p); + + + +symbolic procedure matches(x, p); + if null p then list x + else if null x then nil + else if car x eq car p then matches(cdr x, cdr p) + else nil; + +symbolic procedure make_edits(); + begin + scalar fi, fo, c, line, n, p, w, t0, n_edits, + !*echo, !*raise, !*lower; + t0 := time(); + fi := open("redhelp.x", 'input); + if null fi then error(0, "Input file not available"); + fo := open("redhelp.y", 'output); + if null fo then error(0, "Output file not available"); + fi := rds fi; + fo := wrs fo; + linelength 1000; % Output must never wrap. + n_edits := 0; + c := !$eol!$; + while not (c = !$eof!$) do << + line := nil; + n := 0; +% While reading a line in I will process tabs, counting a tab as at least +% one blank and then enough to pad out to the next multiple of 8. + while not ((c := readch()) = !$eol!$ or c = !$eof!$) do << + if c = tab!* then << + repeat << line := '! . line; + n := n + 1 >> until zerop remainder(n, 8) >> + else << line := c . line; n := n + 1 >> >>; +% Next I act on 's/ *$//g', which discards trailing blanks. + while eqcar(line, '! ) do line := cdr line; + line := reversip line; + while line do << + for each p in edits do + if (w := matches(line, car p)) then << + n_edits := n_edits + 1; + line := append(cdr p, car w) >>; + prin2 car line; + line := cdr line >>; + terpri() >>; + rds fi; + wrs fo; + close fi; + close fo; + prin2 n_edits; prin2t " edits performed"; + return (time() - t0)/1000.0 + end; + +make_edits(); + +quit; + +  Index: r36/mkhelp/comphelp.red ================================================================== --- r36/mkhelp/comphelp.red +++ r36/mkhelp/comphelp.red @@ -1,1081 +1,1081 @@ -% comphelp.red: -% -% first part of the REDUCE help compiler: syntax analysis -% and structure generation. -% -% the second part contains target specific code. -% -% Author: Herbert Melenk, ZIB Berlin -% -% November 1992 -% - -symbolic; - -fluid '(char!* infile!* outfile!* !*windows !*test !*myeof); -fluid '(printfunction!* sect_count endchar current_node!*); -fluid '(!*verbatim !*sqbkt !*opennode currentfont topiccount!*); -fluid '(courier helvetica outc beginstack filestack level); -fluid '(nodechain undo match_point_lft match_point_rgt); -fluid '(run!* dir_src); -fluid '(aliases package); -fluid '(section_list regoup_sections); -fluid '(help_gensym_count); - - -run!* := 0; - -% !*test := t; -regoup_sections := nil; - -%------------------------------------------------------------ -% -% MAIN PROGRAM -% -%------------------------------------------------------------ - -symbolic procedure job(infile,outfile); - begin scalar !*raise, !*lower; - help_gensym_count := 1; - section_list := nil; - !*myeof := nil; - if getenv "echo" then !*echo:=t; - run!* := run!* + 1; - reset(); terpri(); - if run!* = 2 then update_labels(); - !*opennode := nil; - sect_count:=1; - topiccount!* := 0; - printfunction!*:=nil; - if infile!* then close infile!*; - if outfile!* then close outfile!*; - infile!*:=open(bldmsg("%w%w",dir_src,infile),'input); - outfile!*:=open(outfile,'output); - channellinelength(outfile!*,200); - initoutput(); - newfont helvetica; - mainloop(); - close_section 'document; - write_sections(); - fontoff(); - endoutput(); - close infile!*; - infile!* :=nil; - if outfile!* then close outfile!*; - outfile!*:=nil; - % printstruct(); - end; - -%------------------------------------------------------------ -% -% file input -% -%------------------------------------------------------------ - -fluid '(oldchar !*myecho !*myeof); - -!*myecho := nil; -!*myeof := nil; - -symbolic procedure rdch(); rdchr0(nil); - -symbolic procedure rdch!*(); rdchr0(t); - -symbolic procedure rdchr0(q); - if !*myeof then !$eof!$ else - if oldchar then <> where old = oldchar - else - <>; - % if we have found a token, eat up the following blanks. -% if cdr tok then while c='! do c:=rdch(); % ACH: loses a char. - if null cdr tok then return nil; - tok := compress reverse('!".tok); - return intern tok; -end; - -symbolic procedure mystring(); - begin scalar tok,c; - while digit(c:=rdch()) or liter c or c='! or - (endchar and c neq endchar) do - tok:=c.tok; - return reversip(tok); -end; - -symbolic procedure mystring2(); - % read string util }, but ignore \} - begin scalar tok,c; - while (c:=rdch()) neq '!} do tok:=c.tok; - return reversip(tok); -end; - -symbolic procedure mystring2!](); - % read string util ], but ignore \} - begin scalar tok,c; - while (c:=rdch!*()) neq '!] do tok:=c.tok; - return reversip(tok); -end; - -symbolic procedure mystring_nodename(); - % read node name, eventually updating the name translation table - % for entries like "\begin{Command}[percent]{%}" - % read string util }, but ignore \} - begin scalar tok,c,alt; - c:=myskipl '(!{ ![); - if c='![ then - << alt := mystring2!](); myskip '!{ >>; - while (c:=rdch!*()) neq '!} do tok:=c.tok; - tok := reversip tok; - if alt then aliases := (alt . tok) . aliases; - return alt or tok; -end; - -symbolic procedure mystring3(); - begin scalar tok,c; - loop: - c:=rdch(); - if c='!\ then <>; - if c= '!} then return reversip(tok); - tok := c.tok; goto loop; -end; - -symbolic procedure raisestring(s); - begin scalar n; - return for each c in s collect - if (n:=id2int c)>95 then - int2id(n-32) else c; - end; - -symbolic procedure lowerstring(s); - begin scalar n; - return for each c in s collect - if liter c and (n:=id2int c)<95 then - int2id(n+32) else c; - end; - -symbolic procedure mycompress u; - compress reversip('!" . reverse('!" . u)); - -%---------------------- main loop ---------------------------- - -symbolic procedure mainloop(); - begin scalar u,c,tok,f,undo; - loop: - c:=rdch(); - if c=!$eof!$ then goto finis; - if endchar and c=endchar then - <>; - if c='!{ then - << - begin scalar endchar; - endchar := '!}; - mainloop(); - end; - goto loop; - >>; - if c='!\ then - <>; - if tok='documentstyle then - <> - else - if tok='end then - <>; - if u neq car beginstack then - <>; - if !*test then printf(" (main pop %w)",beginstack); - beginstack := cdr beginstack; - goto finis>> - else - if(f:=get(tok,'act)) then - << - if !*test then <>; - apply1(f,tok); - if flagp(f,'simple) then oldchar := char!*; - goto loop; - >> - else - printf("**** unknown token: %w %n",tok); - >>; - char: - if printfunction!* then apply1(printfunction!*,c); - goto loop; - finis: - for each u in undo do eval(u); - end; - -%-----------------\input{...} \include{ ...}----------------- - -symbolic procedure include(u); - begin scalar file,fname,fname1,endchar; - endchar := '!}; - fname:=mycompress mystring(); - if fname = "intro" then return; - fname:=bldmsg("%w%w",dir_src,fname); - endchar := nil; - file:=errorset({'open,mkquote fname,mkquote 'input},nil,nil); - if not errorp file then goto found; - fname1:=bldmsg("%w.tex",fname); - file:=errorset({'open,mkquote fname1,mkquote 'input},nil,nil); - if not errorp file then goto found; - printf("***** cannot open file >%w< resp. >%w< %n",fname,fname1); - return nil; - found: - if fname1 then fname := fname1; - filestack:=infile!*.filestack; - infile!* :=car file; - terpri(); prin2 "--- input file "; prin2t fname; - mainloop(); - terpri(); prin2 "--- return from file "; prin2t fname; - close infile!*; - !*myeof := nil; - infile!*:=car filestack; - filestack := cdr filestack; - end; - -put('input,'act,'include); -put('include,'act,'include); - -put('makeindex,'act,'null); -put('tt,'act,'null); - -%-------------------section hierarchy ----------------------- - -symbolic procedure print_indent(); - if numberp level then for i:=1:level do prin2 " "; - -fluid '(record act_rec node_count); - -node_count := 0; - -smacro procedure type(u); car u; -smacro procedure seq(u); cadr u; -smacro procedure lab(u); caddr u; -smacro procedure count(u); cadddr u; -smacro procedure name(u);car cddddr u; - -symbolic procedure reset(); - << - record := - { - % type seq lab nr name - {'document, nil, "main_index", - 1, '(!T !o !p)}, -% 1, "Top"}, - {'section, nil, nil, 1, nil}, - {'subsection,nil, nil, 1, nil}, - {'subsubsection,nil, nil, 1, nil}}; - act_rec:= car record; - >>; - -symbolic procedure sectappend r; - % link tail from next record to cont of first one - car cdar r :=(cdr cadr r) . seq car r; - -%-------------------- section ------------------------------- - - -symbolic procedure section(s); - begin scalar name; - current_node!* := nil; - name:=mystring2(); - close_section(s); - open_section(s,name); - end; - -symbolic procedure close_section(s); - begin scalar r; - r:=record; - while r and caar r neq s do r:= cdr r; - if null r then error({"record empty",s},99); - for each u in reverse r do close_section1 u; - end; - -symbolic procedure close_section1(rec); - if name rec then - begin - if !*windows then - << print_indent(); reporttopic(" section end: "); - terpri(); - >>; - if regoup_sections then - section_list := append(rec,nil) . section_list - else - write_section(rec); - cdr rec:={nil,nil,0,nil}; - end; - -symbolic procedure write_sections(); - for each s in section_list do write_section s; - -symbolic procedure write_section(rec); - if name rec then - begin - if !*opennode then emit_node_separator(); - !*opennode:=nil; - emit_dir_new(); - emit_dir_label(lab rec); - emit_dir_title name rec; - emit_dir_browse('index,count rec); - emit_dir_key(name rec); - print_bold name rec; - emit_dir_header(); - for each x in reverse seq rec do - make_dir_entry (nil.x); - emit_dir_separator(); - end; - -symbolic procedure make_dir_entry rec; - emit_dir_entry(name rec,lab rec); - -symbolic procedure help_gensym(); - compress ('!g . explode2 (help_gensym_count := help_gensym_count+1)); - -symbolic procedure open_section(s,n); - begin scalar r; - sect_count:=sect_count+1; - r:= record; - while r and cdr r and caadr r neq s do r:=cdr r; - if null r then error({"record empty",s},99); - % initialize new section and link to parent - if not !*windows then n:=append(n, '(! !s !e !c !t !i !o !n)); - cdr cadr r:={nil,help_gensym(),sect_count,n}; - sectappend r; - r:= cadr r; - level := if s='section then 0 else - if s='subsection then 1 else - if s='subsubsection then 2 else 3; - print_indent(); - for each c in lowerstring explode2 s do prin2 c; - prin2 " "; - prin2 count r; prin2 " "; - prin2 lab r; prin2 " "; - mapc(name r,'prin2); terpri(); - act_rec := r; - base_new_dir name r; - level := if s='section then 1 else - if s='subsection then 2 else - if s='subsubsection then 3 else 4; - end; - -put('section,'act,'section); -put('subsection,'act,'section); -put('subsubsection,'act,'section); - - -%------------------- begin-end contexts --------------------------- - -symbolic procedure beg(u); - begin scalar tok,f,w; - tok:=mytoken(t); - for each c in beginstack do w:=w or (get(c,'context)='node); - if w and 'node=get(tok,'context) then - <>; - if !*test then <>; - if !*test then printf(" (push %w)",tok); - beginstack := tok.beginstack; - f:=get(tok,'context); - if f then apply1(f,tok) else - <>; - end; - -put('begin,'act,'beg); - -symbolic procedure mmain(u); mainloop(); - -put('document,'context,'mmain); - -%------------------- generate unique labels ---------------------- - -fluid '(labels!* l_list name_trans); - -symbolic procedure clean_name u; - if null u then nil else - if car u memq '(!- !, !? !* !> !< !. ! ) - then '!_ . clean_name cdr u else - car u . clean_name cdr u; - - -name_trans :='( - ((!,) . COMMA_sign) - ((!.) . DOT_sign) - ((!;) . SEMICOLON_sign) - ((!%) . PERCENT_sign) - ((!$) . DOLLAR_sign) - ((!: !=) . ASSIGN_sign) - ((!=) . EQUAL_sign) - ((!+) . PLUS_sign) - ((!-) . MINUS_sign) - ((!*) . TIMES_sign) - ((!/) . SLASH_sign) - ((!* !*) . POWER_sign) - ((!$ !> != !$) . GEQ_sign) - ((!> !=) . GEQ_sign) - ((!>) . GREATER_sign) - ((!$ !< != !$) . LEQ_sign) - ((!< != ) . LEQ_sign) - ((!<) . LESS_sign) - ((!< !<) . BLOCK)); - - -symbolic procedure make_label(name, type, alias); - begin scalar u,s,w,uname; - uname := raisestring name; - if !*windows then - << alias := clean_name alias; - name := clean_name name>>; - s := uname . type; - u := assoc (s,labels!*); - if u and run!* = 1 then - <>; - if u then return cadr u; - labels!* := (s.(w:=alias.name.type)). labels!*; - if not member(uname,l_list) then - l_list := uname . l_list; - return car w; - end; - -symbolic procedure get_label name; - (if l then car l) where l=get_label1 name; - -symbolic procedure patch_ u; - if null u then nil else - if car u = '!_ then '!\ . '!_ . patch_ cdr u - else car u . patch_ cdr u; - -symbolic procedure get_label1 name; - begin scalar u,uname; - uname := raisestring name; - u := get_label2 uname or get_label2 patch_ uname; - if null u and (run!* > 1) then - <>; - return if u then cdr u else nil; - end; - -symbolic procedure get_label2 uname; - begin scalar u,uname; - u := assoc((uname . 'operator),labels!*) - or assoc((uname . 'function),labels!*) - or assoc((uname . 'switch),labels!*) - or assoc((uname . 'statement),labels!*) - or assoc((uname . 'command),labels!*) - or assoc((uname . 'declaration),labels!*) - or assoc((uname . 'variable),labels!*) - or assoc((uname . 'type),labels!*) - or assoc((uname . 'constant),labels!*) - or assoc((uname . 'concept),labels!*) - or assoc((uname . 'package),labels!*) - or assoc((uname . 'introduction),labels!*); - return u; - end; - -symbolic procedure update_labels(); - % for unique names use the name as label. - begin scalar new,old; - terpri(); - prin2t "------ updating node labels -----"; - for each p in l_list do - if (p:=get_label1 p) then - <>; - prin2t "------ updating done ------------"; - end; - -%------------------- nodes ------------------------------------ - -symbolic procedure node(type); - begin scalar name,name2,rname,type2,name3,rec,type3,name4,label; - scalar altname,alias; - printfunction!* := 'textout; - if !*opennode then emit_node_separator(); - !*opennode:=t; - % myskip '!{; - name:=mystring_nodename(); - if altname:=assoc(name,name_trans) then - name := explode2 cdr altname; -% alias := if !*windows and assoc(name,aliases) then -% cdr assoc(name,aliases); - alias := if assoc(name,aliases) then - cdr assoc(name,aliases); - type3 := lowerstring (type2:=explode2 type); - name2 :=type . '! . (rname:=raisestring name); - name3 := append(type3,'! . name); - name4 := append(name, '! . type3); - label := make_label(name,type,name4); - rec := {'node, - nil, - label, - node_count:=add1 node_count, - name4}; - car cdr act_rec:= cdr rec . seq act_rec; - fonton(); - print_indent(); - mapc(name3,'prin2); reporttopic(" "); terpri(); - emit_node_label(lab rec); - emit_node_title(lab rec,name,type); - emit_node_browse(lab act_rec,count rec); - emit_node_keys(name4); - current_node!* := name4; - emit_hidden_node_key(type3); - emit_hidden_node_key(name rec); - % header line; - myterpri(); - if alias then <>; - print_bold rname; - if type2 neq '(C O N C E P T) then - << print_tab(); print_tab(); print_tab(); print_tab(); - print_bold type2; - >>; - print_newline(); second_newline(); - mainloop (); - end; - -put('switch,'context,'node); -put('variable,'context,'node); -put('operator,'context,'node); -put('function,'context,'node); -put('command,'context,'node); -put('statement,'context,'node); -put('declaration,'context,'node); -put('concept,'context,'node); -put('introduction,'context,'node); -put('package,'context,'node); -put('type,'context,'node); -put('constant,'context,'node); - - -symbolic procedure part(type); - begin - outc:='! ; - if type='examples or type='syntax or type='related - then par_heading(type) else - if type='bigexample then par_heading('example); - - if type='bigexample or type='verbatim then return vpart(type) else - if type='examples then return examples_part(type); - if type='syntax or type='examples then newfont courier; - mainloop(); - second_newline(); second_newline(); - newfont helvetica; - end; - -symbolic procedure par_heading(type); - <>; - -symbolic procedure vpart(type); - % formatted / verbatim part. - begin - emit_start_verbatim(); - set_tab(); - newfont courier; - - vpart0(); - - emit_end_verbatim(); - newfont helvetica; - end; - -symbolic procedure vpart0(); - begin scalar c,c1,c2,c3; - loop: - c:=rdch(); - if c=!$eof!$ then rederr "#### EOF in verbatim part"; - if c='!\ then - <>; - if c1 = '!e and (c2:=rdch()) = '!n and (c3:=rdch()) = '!d - then goto done; - verbprin2 '!\; verbprin2 c1; - if c2 then verbprin2 c2; - if c3 then verbprin2 c3; - goto loop>>; - verbprin2 c; - goto loop; -done: - rdch(); - mytoken(t); - if !*test then printf(" (vpart pop %w)",beginstack); - beginstack := cdr beginstack; - release_tab(); - end; - -symbolic procedure compareahead(seq,l); compareahead1(seq,cdr seq,l); - -symbolic procedure compareahead1(base,seq,l); - if null l then t else - if null seq then compareahead1(nconc(base,c),c,l) where c={rdch()} - else - if not(car seq = car l) then nil else - compareahead1(base,cdr seq,cdr l); - -macro procedure look_ahead(m); - {'compareahead,'inlist,mkquote explode2 cadr m}; - -symbolic procedure examples_part(type); - % formatted / verbatim part. - begin scalar c,pg,state,tab_flag,pg,ll,l,endflag,eolflag,inlist; - emit_start_verbatim(); - set_tab(); - newfont courier; - state := 'lhs; - read_next: - eolflag := nil; - ll := nil; - read_loop: - c:=rdch(); - if c=!$eof!$ then rederr "#### EOF in examples part"; - if c='!\ then - <> - else - if look_ahead "explanation" - then << myskip '!{; - non_verb_block() where endchar='!}; - goto read_next; - >> else - if look_ahead "begin{multilineinput}" - then << - beginstack := 'multilineinput.beginstack; - vpart0(); - goto read_next; - >>; - if state neq 'rhs and look_ahead "begin{multilineoutput}" - then << - beginstack := 'multilineoutput.beginstack; - vpart0(); - goto read_next; - >>; - ll := '!\ . ll; - for each q in cdr inlist do if q then ll := q . ll; - goto read_loop - >> - else if c='!& then - <> - >> - else ll := c . ll; - goto read_loop; -tab_label: - while ll and cdr ll and car ll = '! and cadr ll = '! do - ll := cdr ll; % remove trailing blanks. - l := reversip ll; - for each c in l do - % if not c=!$eol!$ then - verbprin2 c; - if eolflag then - <>; - if length l > 35 then verbprin2 !$eol!$; - %% verbprin2 '!&; - %% verbprin2 "=>"; - state := 'rhs; - goto read_next; - - rhs_line: - verbprin2 !$eol!$; - ll:=reversip ll; - % remove leading blanks - ll := delete(!$eol!$,ll); - while ll and car ll = '! do ll:= cdr ll; - - goto no_expla; - if matchleft(ll,'(!\ !e !x !p !l !a !n !a)) - then - <>; - ll := cdr ll; - >>; - - no_expla: - % provide for multiline - if matchleft(ll,'(!\ !b !e !g !i !n - !{ !m !u !l !t !i !l !i !n !e !o !u !t !p !u !t !})) - then pg:=make_multi_out() ELSE pg:=minitex ll; - - if null pg then goto nix; - tab_flag := t; - %% if cadr pg > 35 then - <>; - pg := cddr pg; - while pg do - <>; - >>; - verbprin2 !$eol!$; - nix: - verbprin2 !$eol!$; - state := 'lhs; - if endflag then goto done; - goto read_next; - -done: - emit_end_verbatim(); - if !*test then printf(" (examples pop %w)",beginstack); - beginstack := cdr beginstack; - release_tab(); - newfont helvetica; - end; - -symbolic procedure non_verb_block(); - begin - emit_end_verbatim(); - release_tab(); - newfont helvetica; - mainloop (); - newfont courier; - set_tab(); - emit_start_verbatim(); - end; - -symbolic procedure make_multi_out(); - begin scalar con,w,pg,m,q; - con:=t; - w := cdr match_point_rgt; - % get rid of "{6cm}" - while w and car w neq '!} do w:=cdr w; - if w then w:=cdr w; - if member(!$eol!$,w) then - <>; - pg:=nil; - m:=0; - mult_loop: - match_point_lft:=nil; - if matcharb(w, '(!\ !e !n !d !{ !m !u !l !t !i !l !i !n !e )) - then<< con:=nil; - if match_point_lft then cdr match_point_lft:=nil else w:=nil; - >>; - if w then - <m then m:=length w; - if memq('!^,w) or memq('!{,w) then - pg := append(pg,cddr minitex w) - else - pg:=append(pg,{w}) - >>; - if con then - << - if q then <> else w:=read_one_line(); - goto mult_loop - >>; - pg := length pg . m . pg; - return pg; - end; - -symbolic procedure cut_lines(l,q); - if null l then {reversip q} else - if car l = !$eol!$ then reversip q . cut_lines(cdr l,nil) - else cut_lines(cdr l,car l . q); - -% match_point_lft: pair before match position -% match_point_rgt: last pair of matched string - -symbolic procedure matchleft(a,pat); - if null pat then t else - if null a then nil else - if car a neq car pat then - <> - else <>; - -symbolic procedure matcharb(a,pat); - if null a then nil else - matchleft(a,pat) or matcharb(cdr a,pat); - -symbolic procedure read_one_line(); - begin scalar l,c; - loop: - c := rdch(); - if c=!$eol!$ then return reversip l; - l := c.l; - goto loop; - end; - -put('comments,'context,'part); -put('examples,'context,'part); -put('bigexample,'context,'part); -put('syntax,'context,'part); -put('related,'context,'part); -put('text,'context,'part); -put('verbatim,'context,'part); -put('quote,'context,'part); % QUOTE -> VERBATIM (temporal) - -symbolic procedure do!-itemize(type); - begin - outc:='! ; - mainloop(); - second_newline(); - end; - -put('itemize,'context,'do!-itemize); - -symbolic procedure context_error(p,q); - << - terpri(); - prin2 "######### error in context "; - prin2 p; - prin2 " ### : "; - prin2t q; - >>; - -%-------------------- special item routines ---------------------- - -symbolic procedure verb(u); - begin scalar endchar,!*verbose; - endchar := char!*; !*verbose:=t; - mainloop(); - end; -put('verb,'act,'verb); - -symbolic procedure ldots(u); textout "..."; -put('ldots,'act,'ldots); -flag('(ldots),'simple); - -symbolic procedure cdots(u); textout "..."; -put('cdots,'act,'cdots); -flag('(cdots),'simple); - -symbolic procedure cdot(u); textout ". "; -put('cdot,'act,'cdot); -flag('(cdot),'simple); - - -symbolic procedure write_pi(u); textout "pi"; -put('pi,'act,'write_pi); -flag('(write_pi),'simple); - -symbolic procedure emphase(u); printem mystring3(); -put('key,'act,'emphase); - -symbolic procedure meta(u); - <">>; - -put('meta,'act,'meta); - -symbolic procedure italic(u); - <>; -put('index,'act,'myindex); - -symbolic procedure nameindex(u); - begin scalar s; - s:= mystring2(); - textout '! ; - emit_hidden_node_key s; - printem s; - end; -put('nameindex,'act,'nameindex); - -symbolic procedure reduce(u); textout "REDUCE"; -put('reduce,'act,'reduce); -flag('(reduce),'simple); - -symbolic procedure rept(u); textout "+"; -put('repeated,'act,'rept); -flag('(rept),'simple); - -symbolic procedure optional(u); textout "*"; -put('optional,'act,'optional); -flag('(optional),'simple); - -symbolic procedure myexp(u); <>; -put('exp,'act,'myexp); - -symbolic procedure formula(u); textoutl mystring2(); -put('variable,'act,'formula); -put('arg,'act,'formula); - -symbolic procedure rfrac(u); - <>; -put('rfrac,'act,'rfrac); - -symbolic procedure item(u); - begin scalar endchar; - endchar := '!]; - print_newline(); - if !*windows then print_tab(); - mainloop(); - end; - -put('item,'act,'item); - -%-------------------- support for iftex etc. --------------------- - -symbolic procedure texonly1(u); - begin scalar endchar,c; - integer count; - count:=1; - loop: - c:= rdch(); - if c='!\ then c:= rdch() else - if c='!{ then count:=count+1 else - if c='!} then count:=count-1; - if count>0 then goto loop; - myskip('!{); - endchar:='!}; - mainloop(); - end; - -put('iftex,'act,'texonly1); - -symbolic procedure texonly2(u); - begin scalar endchar,c,tok; - integer count; - count:=1; - loop: - c:= rdch(); - if c='!\ then - <>; - if count>0 then goto loop; - tok:=mytoken(t); - if tok neq 'tex then - <>; - if !*test then printf(" (texonly pop %w)",beginstack); - beginstack := cdr beginstack; - end; - -put('tex,'context,'texonly2); - -symbolic procedure infoonly(u); - begin scalar endchar; - mainloop(); - end; - -put('info,'context,'infoonly); - -symbolic procedure reporttopic u; - if !*windows then - <>; - -%----------------- untilities ------------------------------ - -symbolic procedure substipq(new,old,l); - % destructive substip based on eq test. - if not pairp l then l else - << - if car l eq old then car l := new; - if cdr l eq old then cdr l := new; - substipq(new,old,car l); - substipq(new,old,cdr l); - l>>; - -end; - - +% comphelp.red: +% +% first part of the REDUCE help compiler: syntax analysis +% and structure generation. +% +% the second part contains target specific code. +% +% Author: Herbert Melenk, ZIB Berlin +% +% November 1992 +% + +symbolic; + +fluid '(char!* infile!* outfile!* !*windows !*test !*myeof); +fluid '(printfunction!* sect_count endchar current_node!*); +fluid '(!*verbatim !*sqbkt !*opennode currentfont topiccount!*); +fluid '(courier helvetica outc beginstack filestack level); +fluid '(nodechain undo match_point_lft match_point_rgt); +fluid '(run!* dir_src); +fluid '(aliases package); +fluid '(section_list regoup_sections); +fluid '(help_gensym_count); + + +run!* := 0; + +% !*test := t; +regoup_sections := nil; + +%------------------------------------------------------------ +% +% MAIN PROGRAM +% +%------------------------------------------------------------ + +symbolic procedure job(infile,outfile); + begin scalar !*raise, !*lower; + help_gensym_count := 1; + section_list := nil; + !*myeof := nil; + if getenv "echo" then !*echo:=t; + run!* := run!* + 1; + reset(); terpri(); + if run!* = 2 then update_labels(); + !*opennode := nil; + sect_count:=1; + topiccount!* := 0; + printfunction!*:=nil; + if infile!* then close infile!*; + if outfile!* then close outfile!*; + infile!*:=open(bldmsg("%w%w",dir_src,infile),'input); + outfile!*:=open(outfile,'output); + channellinelength(outfile!*,200); + initoutput(); + newfont helvetica; + mainloop(); + close_section 'document; + write_sections(); + fontoff(); + endoutput(); + close infile!*; + infile!* :=nil; + if outfile!* then close outfile!*; + outfile!*:=nil; + % printstruct(); + end; + +%------------------------------------------------------------ +% +% file input +% +%------------------------------------------------------------ + +fluid '(oldchar !*myecho !*myeof); + +!*myecho := nil; +!*myeof := nil; + +symbolic procedure rdch(); rdchr0(nil); + +symbolic procedure rdch!*(); rdchr0(t); + +symbolic procedure rdchr0(q); + if !*myeof then !$eof!$ else + if oldchar then <> where old = oldchar + else + <>; + % if we have found a token, eat up the following blanks. +% if cdr tok then while c='! do c:=rdch(); % ACH: loses a char. + if null cdr tok then return nil; + tok := compress reverse('!".tok); + return intern tok; +end; + +symbolic procedure mystring(); + begin scalar tok,c; + while digit(c:=rdch()) or liter c or c='! or + (endchar and c neq endchar) do + tok:=c.tok; + return reversip(tok); +end; + +symbolic procedure mystring2(); + % read string util }, but ignore \} + begin scalar tok,c; + while (c:=rdch()) neq '!} do tok:=c.tok; + return reversip(tok); +end; + +symbolic procedure mystring2!](); + % read string util ], but ignore \} + begin scalar tok,c; + while (c:=rdch!*()) neq '!] do tok:=c.tok; + return reversip(tok); +end; + +symbolic procedure mystring_nodename(); + % read node name, eventually updating the name translation table + % for entries like "\begin{Command}[percent]{%}" + % read string util }, but ignore \} + begin scalar tok,c,alt; + c:=myskipl '(!{ ![); + if c='![ then + << alt := mystring2!](); myskip '!{ >>; + while (c:=rdch!*()) neq '!} do tok:=c.tok; + tok := reversip tok; + if alt then aliases := (alt . tok) . aliases; + return alt or tok; +end; + +symbolic procedure mystring3(); + begin scalar tok,c; + loop: + c:=rdch(); + if c='!\ then <>; + if c= '!} then return reversip(tok); + tok := c.tok; goto loop; +end; + +symbolic procedure raisestring(s); + begin scalar n; + return for each c in s collect + if (n:=id2int c)>95 then + int2id(n-32) else c; + end; + +symbolic procedure lowerstring(s); + begin scalar n; + return for each c in s collect + if liter c and (n:=id2int c)<95 then + int2id(n+32) else c; + end; + +symbolic procedure mycompress u; + compress reversip('!" . reverse('!" . u)); + +%---------------------- main loop ---------------------------- + +symbolic procedure mainloop(); + begin scalar u,c,tok,f,undo; + loop: + c:=rdch(); + if c=!$eof!$ then goto finis; + if endchar and c=endchar then + <>; + if c='!{ then + << + begin scalar endchar; + endchar := '!}; + mainloop(); + end; + goto loop; + >>; + if c='!\ then + <>; + if tok='documentstyle then + <> + else + if tok='end then + <>; + if u neq car beginstack then + <>; + if !*test then printf(" (main pop %w)",beginstack); + beginstack := cdr beginstack; + goto finis>> + else + if(f:=get(tok,'act)) then + << + if !*test then <>; + apply1(f,tok); + if flagp(f,'simple) then oldchar := char!*; + goto loop; + >> + else + printf("**** unknown token: %w %n",tok); + >>; + char: + if printfunction!* then apply1(printfunction!*,c); + goto loop; + finis: + for each u in undo do eval(u); + end; + +%-----------------\input{...} \include{ ...}----------------- + +symbolic procedure include(u); + begin scalar file,fname,fname1,endchar; + endchar := '!}; + fname:=mycompress mystring(); + if fname = "intro" then return; + fname:=bldmsg("%w%w",dir_src,fname); + endchar := nil; + file:=errorset({'open,mkquote fname,mkquote 'input},nil,nil); + if not errorp file then goto found; + fname1:=bldmsg("%w.tex",fname); + file:=errorset({'open,mkquote fname1,mkquote 'input},nil,nil); + if not errorp file then goto found; + printf("***** cannot open file >%w< resp. >%w< %n",fname,fname1); + return nil; + found: + if fname1 then fname := fname1; + filestack:=infile!*.filestack; + infile!* :=car file; + terpri(); prin2 "--- input file "; prin2t fname; + mainloop(); + terpri(); prin2 "--- return from file "; prin2t fname; + close infile!*; + !*myeof := nil; + infile!*:=car filestack; + filestack := cdr filestack; + end; + +put('input,'act,'include); +put('include,'act,'include); + +put('makeindex,'act,'null); +put('tt,'act,'null); + +%-------------------section hierarchy ----------------------- + +symbolic procedure print_indent(); + if numberp level then for i:=1:level do prin2 " "; + +fluid '(record act_rec node_count); + +node_count := 0; + +smacro procedure type(u); car u; +smacro procedure seq(u); cadr u; +smacro procedure lab(u); caddr u; +smacro procedure count(u); cadddr u; +smacro procedure name(u);car cddddr u; + +symbolic procedure reset(); + << + record := + { + % type seq lab nr name + {'document, nil, "main_index", + 1, '(!T !o !p)}, +% 1, "Top"}, + {'section, nil, nil, 1, nil}, + {'subsection,nil, nil, 1, nil}, + {'subsubsection,nil, nil, 1, nil}}; + act_rec:= car record; + >>; + +symbolic procedure sectappend r; + % link tail from next record to cont of first one + car cdar r :=(cdr cadr r) . seq car r; + +%-------------------- section ------------------------------- + + +symbolic procedure section(s); + begin scalar name; + current_node!* := nil; + name:=mystring2(); + close_section(s); + open_section(s,name); + end; + +symbolic procedure close_section(s); + begin scalar r; + r:=record; + while r and caar r neq s do r:= cdr r; + if null r then error({"record empty",s},99); + for each u in reverse r do close_section1 u; + end; + +symbolic procedure close_section1(rec); + if name rec then + begin + if !*windows then + << print_indent(); reporttopic(" section end: "); + terpri(); + >>; + if regoup_sections then + section_list := append(rec,nil) . section_list + else + write_section(rec); + cdr rec:={nil,nil,0,nil}; + end; + +symbolic procedure write_sections(); + for each s in section_list do write_section s; + +symbolic procedure write_section(rec); + if name rec then + begin + if !*opennode then emit_node_separator(); + !*opennode:=nil; + emit_dir_new(); + emit_dir_label(lab rec); + emit_dir_title name rec; + emit_dir_browse('index,count rec); + emit_dir_key(name rec); + print_bold name rec; + emit_dir_header(); + for each x in reverse seq rec do + make_dir_entry (nil.x); + emit_dir_separator(); + end; + +symbolic procedure make_dir_entry rec; + emit_dir_entry(name rec,lab rec); + +symbolic procedure help_gensym(); + compress ('!g . explode2 (help_gensym_count := help_gensym_count+1)); + +symbolic procedure open_section(s,n); + begin scalar r; + sect_count:=sect_count+1; + r:= record; + while r and cdr r and caadr r neq s do r:=cdr r; + if null r then error({"record empty",s},99); + % initialize new section and link to parent + if not !*windows then n:=append(n, '(! !s !e !c !t !i !o !n)); + cdr cadr r:={nil,help_gensym(),sect_count,n}; + sectappend r; + r:= cadr r; + level := if s='section then 0 else + if s='subsection then 1 else + if s='subsubsection then 2 else 3; + print_indent(); + for each c in lowerstring explode2 s do prin2 c; + prin2 " "; + prin2 count r; prin2 " "; + prin2 lab r; prin2 " "; + mapc(name r,'prin2); terpri(); + act_rec := r; + base_new_dir name r; + level := if s='section then 1 else + if s='subsection then 2 else + if s='subsubsection then 3 else 4; + end; + +put('section,'act,'section); +put('subsection,'act,'section); +put('subsubsection,'act,'section); + + +%------------------- begin-end contexts --------------------------- + +symbolic procedure beg(u); + begin scalar tok,f,w; + tok:=mytoken(t); + for each c in beginstack do w:=w or (get(c,'context)='node); + if w and 'node=get(tok,'context) then + <>; + if !*test then <>; + if !*test then printf(" (push %w)",tok); + beginstack := tok.beginstack; + f:=get(tok,'context); + if f then apply1(f,tok) else + <>; + end; + +put('begin,'act,'beg); + +symbolic procedure mmain(u); mainloop(); + +put('document,'context,'mmain); + +%------------------- generate unique labels ---------------------- + +fluid '(labels!* l_list name_trans); + +symbolic procedure clean_name u; + if null u then nil else + if car u memq '(!- !, !? !* !> !< !. ! ) + then '!_ . clean_name cdr u else + car u . clean_name cdr u; + + +name_trans :='( + ((!,) . COMMA_sign) + ((!.) . DOT_sign) + ((!;) . SEMICOLON_sign) + ((!%) . PERCENT_sign) + ((!$) . DOLLAR_sign) + ((!: !=) . ASSIGN_sign) + ((!=) . EQUAL_sign) + ((!+) . PLUS_sign) + ((!-) . MINUS_sign) + ((!*) . TIMES_sign) + ((!/) . SLASH_sign) + ((!* !*) . POWER_sign) + ((!$ !> != !$) . GEQ_sign) + ((!> !=) . GEQ_sign) + ((!>) . GREATER_sign) + ((!$ !< != !$) . LEQ_sign) + ((!< != ) . LEQ_sign) + ((!<) . LESS_sign) + ((!< !<) . BLOCK)); + + +symbolic procedure make_label(name, type, alias); + begin scalar u,s,w,uname; + uname := raisestring name; + if !*windows then + << alias := clean_name alias; + name := clean_name name>>; + s := uname . type; + u := assoc (s,labels!*); + if u and run!* = 1 then + <>; + if u then return cadr u; + labels!* := (s.(w:=alias.name.type)). labels!*; + if not member(uname,l_list) then + l_list := uname . l_list; + return car w; + end; + +symbolic procedure get_label name; + (if l then car l) where l=get_label1 name; + +symbolic procedure patch_ u; + if null u then nil else + if car u = '!_ then '!\ . '!_ . patch_ cdr u + else car u . patch_ cdr u; + +symbolic procedure get_label1 name; + begin scalar u,uname; + uname := raisestring name; + u := get_label2 uname or get_label2 patch_ uname; + if null u and (run!* > 1) then + <>; + return if u then cdr u else nil; + end; + +symbolic procedure get_label2 uname; + begin scalar u,uname; + u := assoc((uname . 'operator),labels!*) + or assoc((uname . 'function),labels!*) + or assoc((uname . 'switch),labels!*) + or assoc((uname . 'statement),labels!*) + or assoc((uname . 'command),labels!*) + or assoc((uname . 'declaration),labels!*) + or assoc((uname . 'variable),labels!*) + or assoc((uname . 'type),labels!*) + or assoc((uname . 'constant),labels!*) + or assoc((uname . 'concept),labels!*) + or assoc((uname . 'package),labels!*) + or assoc((uname . 'introduction),labels!*); + return u; + end; + +symbolic procedure update_labels(); + % for unique names use the name as label. + begin scalar new,old; + terpri(); + prin2t "------ updating node labels -----"; + for each p in l_list do + if (p:=get_label1 p) then + <>; + prin2t "------ updating done ------------"; + end; + +%------------------- nodes ------------------------------------ + +symbolic procedure node(type); + begin scalar name,name2,rname,type2,name3,rec,type3,name4,label; + scalar altname,alias; + printfunction!* := 'textout; + if !*opennode then emit_node_separator(); + !*opennode:=t; + % myskip '!{; + name:=mystring_nodename(); + if altname:=assoc(name,name_trans) then + name := explode2 cdr altname; +% alias := if !*windows and assoc(name,aliases) then +% cdr assoc(name,aliases); + alias := if assoc(name,aliases) then + cdr assoc(name,aliases); + type3 := lowerstring (type2:=explode2 type); + name2 :=type . '! . (rname:=raisestring name); + name3 := append(type3,'! . name); + name4 := append(name, '! . type3); + label := make_label(name,type,name4); + rec := {'node, + nil, + label, + node_count:=add1 node_count, + name4}; + car cdr act_rec:= cdr rec . seq act_rec; + fonton(); + print_indent(); + mapc(name3,'prin2); reporttopic(" "); terpri(); + emit_node_label(lab rec); + emit_node_title(lab rec,name,type); + emit_node_browse(lab act_rec,count rec); + emit_node_keys(name4); + current_node!* := name4; + emit_hidden_node_key(type3); + emit_hidden_node_key(name rec); + % header line; + myterpri(); + if alias then <>; + print_bold rname; + if type2 neq '(C O N C E P T) then + << print_tab(); print_tab(); print_tab(); print_tab(); + print_bold type2; + >>; + print_newline(); second_newline(); + mainloop (); + end; + +put('switch,'context,'node); +put('variable,'context,'node); +put('operator,'context,'node); +put('function,'context,'node); +put('command,'context,'node); +put('statement,'context,'node); +put('declaration,'context,'node); +put('concept,'context,'node); +put('introduction,'context,'node); +put('package,'context,'node); +put('type,'context,'node); +put('constant,'context,'node); + + +symbolic procedure part(type); + begin + outc:='! ; + if type='examples or type='syntax or type='related + then par_heading(type) else + if type='bigexample then par_heading('example); + + if type='bigexample or type='verbatim then return vpart(type) else + if type='examples then return examples_part(type); + if type='syntax or type='examples then newfont courier; + mainloop(); + second_newline(); second_newline(); + newfont helvetica; + end; + +symbolic procedure par_heading(type); + <>; + +symbolic procedure vpart(type); + % formatted / verbatim part. + begin + emit_start_verbatim(); + set_tab(); + newfont courier; + + vpart0(); + + emit_end_verbatim(); + newfont helvetica; + end; + +symbolic procedure vpart0(); + begin scalar c,c1,c2,c3; + loop: + c:=rdch(); + if c=!$eof!$ then rederr "#### EOF in verbatim part"; + if c='!\ then + <>; + if c1 = '!e and (c2:=rdch()) = '!n and (c3:=rdch()) = '!d + then goto done; + verbprin2 '!\; verbprin2 c1; + if c2 then verbprin2 c2; + if c3 then verbprin2 c3; + goto loop>>; + verbprin2 c; + goto loop; +done: + rdch(); + mytoken(t); + if !*test then printf(" (vpart pop %w)",beginstack); + beginstack := cdr beginstack; + release_tab(); + end; + +symbolic procedure compareahead(seq,l); compareahead1(seq,cdr seq,l); + +symbolic procedure compareahead1(base,seq,l); + if null l then t else + if null seq then compareahead1(nconc(base,c),c,l) where c={rdch()} + else + if not(car seq = car l) then nil else + compareahead1(base,cdr seq,cdr l); + +macro procedure look_ahead(m); + {'compareahead,'inlist,mkquote explode2 cadr m}; + +symbolic procedure examples_part(type); + % formatted / verbatim part. + begin scalar c,pg,state,tab_flag,pg,ll,l,endflag,eolflag,inlist; + emit_start_verbatim(); + set_tab(); + newfont courier; + state := 'lhs; + read_next: + eolflag := nil; + ll := nil; + read_loop: + c:=rdch(); + if c=!$eof!$ then rederr "#### EOF in examples part"; + if c='!\ then + <> + else + if look_ahead "explanation" + then << myskip '!{; + non_verb_block() where endchar='!}; + goto read_next; + >> else + if look_ahead "begin{multilineinput}" + then << + beginstack := 'multilineinput.beginstack; + vpart0(); + goto read_next; + >>; + if state neq 'rhs and look_ahead "begin{multilineoutput}" + then << + beginstack := 'multilineoutput.beginstack; + vpart0(); + goto read_next; + >>; + ll := '!\ . ll; + for each q in cdr inlist do if q then ll := q . ll; + goto read_loop + >> + else if c='!& then + <> + >> + else ll := c . ll; + goto read_loop; +tab_label: + while ll and cdr ll and car ll = '! and cadr ll = '! do + ll := cdr ll; % remove trailing blanks. + l := reversip ll; + for each c in l do + % if not c=!$eol!$ then + verbprin2 c; + if eolflag then + <>; + if length l > 35 then verbprin2 !$eol!$; + %% verbprin2 '!&; + %% verbprin2 "=>"; + state := 'rhs; + goto read_next; + + rhs_line: + verbprin2 !$eol!$; + ll:=reversip ll; + % remove leading blanks + ll := delete(!$eol!$,ll); + while ll and car ll = '! do ll:= cdr ll; + + goto no_expla; + if matchleft(ll,'(!\ !e !x !p !l !a !n !a)) + then + <>; + ll := cdr ll; + >>; + + no_expla: + % provide for multiline + if matchleft(ll,'(!\ !b !e !g !i !n + !{ !m !u !l !t !i !l !i !n !e !o !u !t !p !u !t !})) + then pg:=make_multi_out() ELSE pg:=minitex ll; + + if null pg then goto nix; + tab_flag := t; + %% if cadr pg > 35 then + <>; + pg := cddr pg; + while pg do + <>; + >>; + verbprin2 !$eol!$; + nix: + verbprin2 !$eol!$; + state := 'lhs; + if endflag then goto done; + goto read_next; + +done: + emit_end_verbatim(); + if !*test then printf(" (examples pop %w)",beginstack); + beginstack := cdr beginstack; + release_tab(); + newfont helvetica; + end; + +symbolic procedure non_verb_block(); + begin + emit_end_verbatim(); + release_tab(); + newfont helvetica; + mainloop (); + newfont courier; + set_tab(); + emit_start_verbatim(); + end; + +symbolic procedure make_multi_out(); + begin scalar con,w,pg,m,q; + con:=t; + w := cdr match_point_rgt; + % get rid of "{6cm}" + while w and car w neq '!} do w:=cdr w; + if w then w:=cdr w; + if member(!$eol!$,w) then + <>; + pg:=nil; + m:=0; + mult_loop: + match_point_lft:=nil; + if matcharb(w, '(!\ !e !n !d !{ !m !u !l !t !i !l !i !n !e )) + then<< con:=nil; + if match_point_lft then cdr match_point_lft:=nil else w:=nil; + >>; + if w then + <m then m:=length w; + if memq('!^,w) or memq('!{,w) then + pg := append(pg,cddr minitex w) + else + pg:=append(pg,{w}) + >>; + if con then + << + if q then <> else w:=read_one_line(); + goto mult_loop + >>; + pg := length pg . m . pg; + return pg; + end; + +symbolic procedure cut_lines(l,q); + if null l then {reversip q} else + if car l = !$eol!$ then reversip q . cut_lines(cdr l,nil) + else cut_lines(cdr l,car l . q); + +% match_point_lft: pair before match position +% match_point_rgt: last pair of matched string + +symbolic procedure matchleft(a,pat); + if null pat then t else + if null a then nil else + if car a neq car pat then + <> + else <>; + +symbolic procedure matcharb(a,pat); + if null a then nil else + matchleft(a,pat) or matcharb(cdr a,pat); + +symbolic procedure read_one_line(); + begin scalar l,c; + loop: + c := rdch(); + if c=!$eol!$ then return reversip l; + l := c.l; + goto loop; + end; + +put('comments,'context,'part); +put('examples,'context,'part); +put('bigexample,'context,'part); +put('syntax,'context,'part); +put('related,'context,'part); +put('text,'context,'part); +put('verbatim,'context,'part); +put('quote,'context,'part); % QUOTE -> VERBATIM (temporal) + +symbolic procedure do!-itemize(type); + begin + outc:='! ; + mainloop(); + second_newline(); + end; + +put('itemize,'context,'do!-itemize); + +symbolic procedure context_error(p,q); + << + terpri(); + prin2 "######### error in context "; + prin2 p; + prin2 " ### : "; + prin2t q; + >>; + +%-------------------- special item routines ---------------------- + +symbolic procedure verb(u); + begin scalar endchar,!*verbose; + endchar := char!*; !*verbose:=t; + mainloop(); + end; +put('verb,'act,'verb); + +symbolic procedure ldots(u); textout "..."; +put('ldots,'act,'ldots); +flag('(ldots),'simple); + +symbolic procedure cdots(u); textout "..."; +put('cdots,'act,'cdots); +flag('(cdots),'simple); + +symbolic procedure cdot(u); textout ". "; +put('cdot,'act,'cdot); +flag('(cdot),'simple); + + +symbolic procedure write_pi(u); textout "pi"; +put('pi,'act,'write_pi); +flag('(write_pi),'simple); + +symbolic procedure emphase(u); printem mystring3(); +put('key,'act,'emphase); + +symbolic procedure meta(u); + <">>; + +put('meta,'act,'meta); + +symbolic procedure italic(u); + <>; +put('index,'act,'myindex); + +symbolic procedure nameindex(u); + begin scalar s; + s:= mystring2(); + textout '! ; + emit_hidden_node_key s; + printem s; + end; +put('nameindex,'act,'nameindex); + +symbolic procedure reduce(u); textout "REDUCE"; +put('reduce,'act,'reduce); +flag('(reduce),'simple); + +symbolic procedure rept(u); textout "+"; +put('repeated,'act,'rept); +flag('(rept),'simple); + +symbolic procedure optional(u); textout "*"; +put('optional,'act,'optional); +flag('(optional),'simple); + +symbolic procedure myexp(u); <>; +put('exp,'act,'myexp); + +symbolic procedure formula(u); textoutl mystring2(); +put('variable,'act,'formula); +put('arg,'act,'formula); + +symbolic procedure rfrac(u); + <>; +put('rfrac,'act,'rfrac); + +symbolic procedure item(u); + begin scalar endchar; + endchar := '!]; + print_newline(); + if !*windows then print_tab(); + mainloop(); + end; + +put('item,'act,'item); + +%-------------------- support for iftex etc. --------------------- + +symbolic procedure texonly1(u); + begin scalar endchar,c; + integer count; + count:=1; + loop: + c:= rdch(); + if c='!\ then c:= rdch() else + if c='!{ then count:=count+1 else + if c='!} then count:=count-1; + if count>0 then goto loop; + myskip('!{); + endchar:='!}; + mainloop(); + end; + +put('iftex,'act,'texonly1); + +symbolic procedure texonly2(u); + begin scalar endchar,c,tok; + integer count; + count:=1; + loop: + c:= rdch(); + if c='!\ then + <>; + if count>0 then goto loop; + tok:=mytoken(t); + if tok neq 'tex then + <>; + if !*test then printf(" (texonly pop %w)",beginstack); + beginstack := cdr beginstack; + end; + +put('tex,'context,'texonly2); + +symbolic procedure infoonly(u); + begin scalar endchar; + mainloop(); + end; + +put('info,'context,'infoonly); + +symbolic procedure reporttopic u; + if !*windows then + <>; + +%----------------- untilities ------------------------------ + +symbolic procedure substipq(new,old,l); + % destructive substip based on eq test. + if not pairp l then l else + << + if car l eq old then car l := new; + if cdr l eq old then cdr l := new; + substipq(new,old,car l); + substipq(new,old,cdr l); + l>>; + +end; + +  Index: r36/mkhelp/helphtml.red ================================================================== --- r36/mkhelp/helphtml.red +++ r36/mkhelp/helphtml.red @@ -1,597 +1,597 @@ -% helphtml.red -% -% interfacing reduce help file to HTML (world wide web) -% -% Author: Herbert Melenk, ZIB Berlin -% -% November 1992 -% -% PSL dependent - -fluid '(outc newl par !*font !*newline !*html html_specials!* !*windows !*secondrun); - -fluid '(node_file_name!* current_base_dir !*directory_open CURRENT_NODE_NUMBER!*); - -!*HTML := t; -!*windows := t; -helvetica:= "R"; -courier:= "TT"; - -!#if (member 'csl lispsystem!*) - -symbolic procedure rootname(); - "r36"; - -symbolic procedure dest_directory(); - "html"; - -!#else - -symbolic procedure rootname(); - getenv "package"; - -symbolic procedure dest_directory(); - getenv "tdir"; - -!#endif - -fluid '(node_file_labels filenumber indexfilename labels2nodes); - -filenumber:=0; - -symbolic procedure reset_html(); - << - indexfilename := make_html_file_name "index"; - filenumber := 0; - >>; - - -symbolic procedure html_open(u); - myprin2(compress ('!" . ( '!< . append(explode2 u, '(!> !")) )) ); - -symbolic procedure html_close(u); - myprin2(compress ('!" . ( '!< . ( '!/ . append(explode2 u, '(!> !")) )) )); - - -symbolic procedure open_current_base_dir u; - % myprin2 " open_current_base_dir "; myprin2 u; - nil; - -symbolic procedure close_current_base_dir (); - % myprin2 " close_current_base_dir "; - nil; - -symbolic procedure make_html_file_name u; - begin scalar base,num; - base := reversip explode2 rootname(); - while length base > 4 do base := cdr base; - base := compress ('!" . reversip ('!" . base)); -!#if (member 'csl lispsystem!*) - if u="main_index" then return bldmsg("%w.html",base) - else if u="index" then num:="idx" - else <>; - return bldmsg("%w_%w.html",base,num); -!#else - if u="main_index" then num:="_dir" - else if u="index" then num:="_idx" - else <>; - return bldmsg("%w%w.html",base,num); -!#endif - end; - - - -symbolic procedure open_node_file u; - begin scalar dir,name; - dir:=if (dir:=dest_directory()) then bldmsg("%w/",dir) else ""; - name := node_file_name!* := make_html_file_name u; - labels2nodes := (name . u) . labels2nodes; -% non-unix and PSL: open with suffix "htm". - if not member('unix,lispsystem!*) and member('psl, lispsystem!*) then - name:= compress ('!" . reversip('!" . cdr reversip explode2 name)); - if outfile!* then close outfile!*; - outfile!* := open(bldmsg("%w%w",dir,name), 'output); - return outfile!*; - end; - -symbolic procedure close_node_file (); -if outfile!* then << close outfile!*; outfile!* := nil; - node_file_name!* := nil; - >>; - -symbolic procedure node_file_name(); node_file_name!*; - -symbolic procedure initoutput (); nil; - -symbolic procedure endoutput(); nil; - -symbolic procedure verbatim u; - !*verbatim := u; - -symbolic procedure newfont(f); - if currentfont neq f then - <>; - -symbolic procedure fontoff(); - <<% if !*font then channelprin2(outfile!*,"}"); - outc:=nil; - !*font:=nil>>; - -symbolic procedure fonton(); - <>; - !*font:=t>>; - -symbolic procedure myprin2 u; - <>; - -deflist( '((!< "<") - (!> ">") - (!" """) - (!& "&")), - 'HTML_Symbol_Name); - -html_specials!* := '(!< !> !" !&); - -symbolic procedure myprin2_protected u; - <>; - -fluid '(!*verbescape); - -symbolic procedure emit_start_verbatim(); - <>; - -symbolic procedure emit_end_verbatim(); - <> ; - -symbolic procedure verbprin2 u; - if u = '!\ then << !*verbescape :=t>> - else - if u=!$eol!$ then << myterpri();!*verbescape := nil>> - else - if (u = '!&) then - <> - else - if u memq html_specials!* then - <> - else - <>; - -symbolic procedure myterpri(); - channelterpri outfile!*; - -symbolic procedure number4out n; - % print number with 4 digits. - << if n<10 then textout "0"; - if n<100 then textout "0"; - if n<1000 then textout "0"; - textout n>>; - -% par = t: paragraph has been terminated - no new data so far -% newl = t: last character has been an EOL - -symbolic procedure textout(u); - if par and (u=!$eol!$ or u='! ) then nil else - if stringp u then mapc(explode2 u, 'textout) else - <> - else - if (u = '!$) then - newfont(if currentfont = helvetica then courier else helvetica) - else - if (u memq html_specials!*) then <> else - if (u neq '! ) or (outc neq '! ) or !*verbatim - then - <>; - >>; - -% -------- paragraph heading --------------------------- - -symbolic procedure par_heading(type); - <

"; - verbprin2 !$eol!$; - for each x in explode type do verbprin2 x; - verbprin2 ":

"; - verbprin2 !$eol!$; - >>; - -% -------- directory structure ------------------------- - -symbolic procedure base_new_dir(name); - <<%myprin2 "base_new_dir name="; myprin2 name; - close_current_base_dir(); - open_current_base_dir name; - current_base_dir := name>>; - -symbolic procedure emit_dir_new(); - <<%print current_base_dir; - %open_node_file current_base_dir - nil>>; - -symbolic procedure emit_dir_key u; - emit_node_key u; - -symbolic procedure emit_dir_separator(); - emit_node_separator(); - -symbolic procedure emit_dir_label u; - emit_node_label u; - -symbolic procedure emit_dir_title u; - emit_node_title(u,nil,'section); - -symbolic procedure emit_dir_browse(u,n); - emit_node_browse(u,n); - -% ---- node structure - -symbolic procedure emit_node_separator(); - <>; - %myterpri(); myterpri(); - %channelprin2(outfile!*,"emit_node_separator"); - %myterpri(); myterpri(); - outc:='! ; par:=t; - - close_node_file(); - >>; - -symbolic procedure set_tab(); nil; -% myprin2 "set_tab "; - -symbolic procedure release_tab(); nil; -% myprin2 "release_tab "; - -symbolic procedure textout_name(l); - % l is a list of characters to be printed. - % special action for names: \ in front of _ suppressed because - % of Microsoft HC logic (don't know why). - if atom l then textout l else - while l do - <>; - - -symbolic procedure textout2(l); - if l then - if atom l then myprin2 l else - for each x in l do myprin2 - if x='! then '!_ else x; - -symbolic procedure printem(s); - % print italic - begin - html_open "em"; - mapc(s,'myprin2); - html_close "em"; - end; - -symbolic procedure printem(s); - begin - fontoff(); - html_open "em"; - mapc(s,'myprin2_protected); - html_close "em"; - end; - -symbolic procedure printref u; - begin scalar r,s; - % print ( ">>>" . u); - r:= get_label u; -% s := assoc (u,node_file_labels); - s := assoc (r,node_file_labels); - if s then s := cdr s -% Debug lines here... - else if run!* > 1 then << - prin2 "### reference to "; prin u; - prin2 " with label "; prin r; - prin2t " not found." - >>; - if null r then return printem u; - fontoff(); - myterpri(); - myprin2 "
"; - mapc(u,'myprin2); html_close "A"; - end; - -symbolic procedure printnameref u; - printref u; - -fluid '(key_database); - -symbolic procedure emit_node_keys u; - begin scalar keys; - keys := assoc(u,key_database); - if null keys then return; - keys := cdr keys; - fonton(); - myterpri(); - while keys do - << %myprin2 ""; - % textout_name car keys; - % myprin2 " . "; -prin2 "### add node "; prin car keys, prin2 " "; print node_file_name!*; - node_file_labels := ( car keys . node_file_name!*) . node_file_labels; - % print ( "<=>" . car keys); - keys:= cdr keys; - %if keys then myprin2";" - >>; - myterpri(); - end; - -symbolic procedure emit_node_key u; - emit_hidden_node_key u; - -symbolic procedure emit_hidden_node_key u; - if current_node!* then - begin scalar q; - q:= assoc(current_node!*,key_database); - if null q then - key_database := (current_node!* . {u}).key_database - else - if not member(u,cdr q) then cdr q:=u.cdr q; - end; - -symbolic procedure emit_node_label u; - <"; - myterpri(); -prin2 "#### add node "; prin u, prin2 " "; print node_file_name!*; - node_file_labels := ( u . node_file_name!* ) . node_file_labels; - >>; - -symbolic procedure emit_node_title(u,dummy,type); - <INDEX

%n",indexfilename); - >>; - -symbolic procedure emit_node_browse(u,n); - < . "; - % myterpri(); -prin2 "##### add node "; prin u, prin2 " "; print node_file_name!*; - node_file_labels := ( u . node_file_name!* ) . node_file_labels; - - >>; - - -symbolic procedure print_bold u; - <>; - -symbolic procedure emit_dir_header(); - << - fontoff(); - html_open "MENU"; - !*directory_open := t; - myterpri(); - >>; - -symbolic procedure emit_dir_entry(name,lab); - begin scalar alias, s; - s:= assoc(lab,node_file_labels); if s then s := cdr s; - fontoff(); - html_open "LI"; myprin2 ""; - mapc(name,'myprin2); - html_close "A"; -% myterpri(); -% myprin2 "{\v\f2 "; - if (alias:=assoc(lab,aliases)) then - <"); channelterpri outfile!*>>; - !*newline:=t - >>; - - -symbolic procedure second_newline(); - <>; - -symbolic procedure print_tab (); - <>; - -%------------------- HTML index file -------------------------------- - - -symbolic procedure html_indexfile(); - begin scalar u,v,q,r,s,rr,!*lower; - prin2t "..... compiling html index file"; - s := for each q in node_file_labels join - if pairp car q then {sort_term car q . q}; - s := sort(s,'html_indexfile_sort); - % remove trivial entries - r:=s; - while r do - <>; - % remove duplicates - r:=s; - while r and cdr r do - <>; - >>; - - open_node_file "index"; - channelprintf(outfile!*, "%w search index%n",rootname()); - channelprintf(outfile!*, "

%n"); - channelprintf(outfile!*, "%n"); - for each x in s do - <"); - for each c in cadr x do - if c='!_ then channelprin2(outfile!*," ") else - if not(c='!\) then channelprin2(outfile!*,c); - channelprintf(outfile!*, ": ",cddr x); - q := cdr assoc(cddr x,labels2nodes); - for each c in q do - if c='!_ then channelprin2(outfile!*," ") else - if not(c='!\) then channelprin2(outfile!*,c); - channelprin2t(outfile!*, ""); - >>; - channelprintf(outfile!*, "%n"); - close outfile!*; - outfile!*:=nil; - end; - -symbolic procedure sort_term u; - for each c in raisestring u join - if liter c or digit c then {c}; - -symbolic procedure html_indexfile_sort(u,v); - html_indexfile_sort1(car u,car v); - -symbolic procedure html_indexfile_sort1(u,v); - if null u then t else - if null v then nil else - if car u = car v then html_indexfile_sort1(cdr u,cdr v) else - id2int car u < id2int car v; - -symbolic procedure html_indexfile_subsetp(a,b); - null a or - b and car a = car b and html_indexfile_subsetp(cdr a,cdr b); - -%------------------- LISP index file -------------------------------- - - -symbolic procedure LISP_indexfile(); - begin scalar u,v,q,r,s,rr,!*lower,pack; - prin2t "..... compiling independent index file"; - pack := rootname(); - s := for each q in node_file_labels join - if pairp car q then {sort_term car q . q}; - s := sort(s,'html_indexfile_sort); - % remove trivial entries - r:=s; - while r do - <>; - % remove duplicates - r:=s; - while r and cdr r do - <>; - >>; - - outfile!*:= open(bldmsg("%w.hdx",pack),'output); - channelprintf(outfile!*, "%w generated from reference manual >%w< %n",'!%,pack); - channelprintf(outfile!*, "%w (node text description status details) %n",'!%,pack); - for each x in s do - <>; - close outfile!*; - outfile!*:=nil; - end; - -%------------------- printstruct ------------------------------- - -symbolic procedure printstruct(); - <>; - -symbolic procedure printstruct1(r,n); - <>; - -end; - - - - +% helphtml.red +% +% interfacing reduce help file to HTML (world wide web) +% +% Author: Herbert Melenk, ZIB Berlin +% +% November 1992 +% +% PSL dependent + +fluid '(outc newl par !*font !*newline !*html html_specials!* !*windows !*secondrun); + +fluid '(node_file_name!* current_base_dir !*directory_open CURRENT_NODE_NUMBER!*); + +!*HTML := t; +!*windows := t; +helvetica:= "R"; +courier:= "TT"; + +!#if (member 'csl lispsystem!*) + +symbolic procedure rootname(); + "r36"; + +symbolic procedure dest_directory(); + "html"; + +!#else + +symbolic procedure rootname(); + getenv "package"; + +symbolic procedure dest_directory(); + getenv "tdir"; + +!#endif + +fluid '(node_file_labels filenumber indexfilename labels2nodes); + +filenumber:=0; + +symbolic procedure reset_html(); + << + indexfilename := make_html_file_name "index"; + filenumber := 0; + >>; + + +symbolic procedure html_open(u); + myprin2(compress ('!" . ( '!< . append(explode2 u, '(!> !")) )) ); + +symbolic procedure html_close(u); + myprin2(compress ('!" . ( '!< . ( '!/ . append(explode2 u, '(!> !")) )) )); + + +symbolic procedure open_current_base_dir u; + % myprin2 " open_current_base_dir "; myprin2 u; + nil; + +symbolic procedure close_current_base_dir (); + % myprin2 " close_current_base_dir "; + nil; + +symbolic procedure make_html_file_name u; + begin scalar base,num; + base := reversip explode2 rootname(); + while length base > 4 do base := cdr base; + base := compress ('!" . reversip ('!" . base)); +!#if (member 'csl lispsystem!*) + if u="main_index" then return bldmsg("%w.html",base) + else if u="index" then num:="idx" + else <>; + return bldmsg("%w_%w.html",base,num); +!#else + if u="main_index" then num:="_dir" + else if u="index" then num:="_idx" + else <>; + return bldmsg("%w%w.html",base,num); +!#endif + end; + + + +symbolic procedure open_node_file u; + begin scalar dir,name; + dir:=if (dir:=dest_directory()) then bldmsg("%w/",dir) else ""; + name := node_file_name!* := make_html_file_name u; + labels2nodes := (name . u) . labels2nodes; +% non-unix and PSL: open with suffix "htm". + if not member('unix,lispsystem!*) and member('psl, lispsystem!*) then + name:= compress ('!" . reversip('!" . cdr reversip explode2 name)); + if outfile!* then close outfile!*; + outfile!* := open(bldmsg("%w%w",dir,name), 'output); + return outfile!*; + end; + +symbolic procedure close_node_file (); +if outfile!* then << close outfile!*; outfile!* := nil; + node_file_name!* := nil; + >>; + +symbolic procedure node_file_name(); node_file_name!*; + +symbolic procedure initoutput (); nil; + +symbolic procedure endoutput(); nil; + +symbolic procedure verbatim u; + !*verbatim := u; + +symbolic procedure newfont(f); + if currentfont neq f then + <>; + +symbolic procedure fontoff(); + <<% if !*font then channelprin2(outfile!*,"}"); + outc:=nil; + !*font:=nil>>; + +symbolic procedure fonton(); + <>; + !*font:=t>>; + +symbolic procedure myprin2 u; + <>; + +deflist( '((!< "<") + (!> ">") + (!" """) + (!& "&")), + 'HTML_Symbol_Name); + +html_specials!* := '(!< !> !" !&); + +symbolic procedure myprin2_protected u; + <>; + +fluid '(!*verbescape); + +symbolic procedure emit_start_verbatim(); + <>; + +symbolic procedure emit_end_verbatim(); + <> ; + +symbolic procedure verbprin2 u; + if u = '!\ then << !*verbescape :=t>> + else + if u=!$eol!$ then << myterpri();!*verbescape := nil>> + else + if (u = '!&) then + <> + else + if u memq html_specials!* then + <> + else + <>; + +symbolic procedure myterpri(); + channelterpri outfile!*; + +symbolic procedure number4out n; + % print number with 4 digits. + << if n<10 then textout "0"; + if n<100 then textout "0"; + if n<1000 then textout "0"; + textout n>>; + +% par = t: paragraph has been terminated - no new data so far +% newl = t: last character has been an EOL + +symbolic procedure textout(u); + if par and (u=!$eol!$ or u='! ) then nil else + if stringp u then mapc(explode2 u, 'textout) else + <> + else + if (u = '!$) then + newfont(if currentfont = helvetica then courier else helvetica) + else + if (u memq html_specials!*) then <> else + if (u neq '! ) or (outc neq '! ) or !*verbatim + then + <>; + >>; + +% -------- paragraph heading --------------------------- + +symbolic procedure par_heading(type); + <

"; + verbprin2 !$eol!$; + for each x in explode type do verbprin2 x; + verbprin2 ":

"; + verbprin2 !$eol!$; + >>; + +% -------- directory structure ------------------------- + +symbolic procedure base_new_dir(name); + <<%myprin2 "base_new_dir name="; myprin2 name; + close_current_base_dir(); + open_current_base_dir name; + current_base_dir := name>>; + +symbolic procedure emit_dir_new(); + <<%print current_base_dir; + %open_node_file current_base_dir + nil>>; + +symbolic procedure emit_dir_key u; + emit_node_key u; + +symbolic procedure emit_dir_separator(); + emit_node_separator(); + +symbolic procedure emit_dir_label u; + emit_node_label u; + +symbolic procedure emit_dir_title u; + emit_node_title(u,nil,'section); + +symbolic procedure emit_dir_browse(u,n); + emit_node_browse(u,n); + +% ---- node structure + +symbolic procedure emit_node_separator(); + <>; + %myterpri(); myterpri(); + %channelprin2(outfile!*,"emit_node_separator"); + %myterpri(); myterpri(); + outc:='! ; par:=t; + + close_node_file(); + >>; + +symbolic procedure set_tab(); nil; +% myprin2 "set_tab "; + +symbolic procedure release_tab(); nil; +% myprin2 "release_tab "; + +symbolic procedure textout_name(l); + % l is a list of characters to be printed. + % special action for names: \ in front of _ suppressed because + % of Microsoft HC logic (don't know why). + if atom l then textout l else + while l do + <>; + + +symbolic procedure textout2(l); + if l then + if atom l then myprin2 l else + for each x in l do myprin2 + if x='! then '!_ else x; + +symbolic procedure printem(s); + % print italic + begin + html_open "em"; + mapc(s,'myprin2); + html_close "em"; + end; + +symbolic procedure printem(s); + begin + fontoff(); + html_open "em"; + mapc(s,'myprin2_protected); + html_close "em"; + end; + +symbolic procedure printref u; + begin scalar r,s; + % print ( ">>>" . u); + r:= get_label u; +% s := assoc (u,node_file_labels); + s := assoc (r,node_file_labels); + if s then s := cdr s +% Debug lines here... + else if run!* > 1 then << + prin2 "### reference to "; prin u; + prin2 " with label "; prin r; + prin2t " not found." + >>; + if null r then return printem u; + fontoff(); + myterpri(); + myprin2 ""; + mapc(u,'myprin2); html_close "A"; + end; + +symbolic procedure printnameref u; + printref u; + +fluid '(key_database); + +symbolic procedure emit_node_keys u; + begin scalar keys; + keys := assoc(u,key_database); + if null keys then return; + keys := cdr keys; + fonton(); + myterpri(); + while keys do + << %myprin2 ""; + % textout_name car keys; + % myprin2 " . "; +prin2 "### add node "; prin car keys, prin2 " "; print node_file_name!*; + node_file_labels := ( car keys . node_file_name!*) . node_file_labels; + % print ( "<=>" . car keys); + keys:= cdr keys; + %if keys then myprin2";" + >>; + myterpri(); + end; + +symbolic procedure emit_node_key u; + emit_hidden_node_key u; + +symbolic procedure emit_hidden_node_key u; + if current_node!* then + begin scalar q; + q:= assoc(current_node!*,key_database); + if null q then + key_database := (current_node!* . {u}).key_database + else + if not member(u,cdr q) then cdr q:=u.cdr q; + end; + +symbolic procedure emit_node_label u; + <"; + myterpri(); +prin2 "#### add node "; prin u, prin2 " "; print node_file_name!*; + node_file_labels := ( u . node_file_name!* ) . node_file_labels; + >>; + +symbolic procedure emit_node_title(u,dummy,type); + <INDEX

%n",indexfilename); + >>; + +symbolic procedure emit_node_browse(u,n); + < . "; + % myterpri(); +prin2 "##### add node "; prin u, prin2 " "; print node_file_name!*; + node_file_labels := ( u . node_file_name!* ) . node_file_labels; + + >>; + + +symbolic procedure print_bold u; + <>; + +symbolic procedure emit_dir_header(); + << + fontoff(); + html_open "MENU"; + !*directory_open := t; + myterpri(); + >>; + +symbolic procedure emit_dir_entry(name,lab); + begin scalar alias, s; + s:= assoc(lab,node_file_labels); if s then s := cdr s; + fontoff(); + html_open "LI"; myprin2 ""; + mapc(name,'myprin2); + html_close "A"; +% myterpri(); +% myprin2 "{\v\f2 "; + if (alias:=assoc(lab,aliases)) then + <"); channelterpri outfile!*>>; + !*newline:=t + >>; + + +symbolic procedure second_newline(); + <>; + +symbolic procedure print_tab (); + <>; + +%------------------- HTML index file -------------------------------- + + +symbolic procedure html_indexfile(); + begin scalar u,v,q,r,s,rr,!*lower; + prin2t "..... compiling html index file"; + s := for each q in node_file_labels join + if pairp car q then {sort_term car q . q}; + s := sort(s,'html_indexfile_sort); + % remove trivial entries + r:=s; + while r do + <>; + % remove duplicates + r:=s; + while r and cdr r do + <>; + >>; + + open_node_file "index"; + channelprintf(outfile!*, "%w search index%n",rootname()); + channelprintf(outfile!*, "

%n"); + channelprintf(outfile!*, "%n"); + for each x in s do + <"); + for each c in cadr x do + if c='!_ then channelprin2(outfile!*," ") else + if not(c='!\) then channelprin2(outfile!*,c); + channelprintf(outfile!*, ": ",cddr x); + q := cdr assoc(cddr x,labels2nodes); + for each c in q do + if c='!_ then channelprin2(outfile!*," ") else + if not(c='!\) then channelprin2(outfile!*,c); + channelprin2t(outfile!*, ""); + >>; + channelprintf(outfile!*, "%n"); + close outfile!*; + outfile!*:=nil; + end; + +symbolic procedure sort_term u; + for each c in raisestring u join + if liter c or digit c then {c}; + +symbolic procedure html_indexfile_sort(u,v); + html_indexfile_sort1(car u,car v); + +symbolic procedure html_indexfile_sort1(u,v); + if null u then t else + if null v then nil else + if car u = car v then html_indexfile_sort1(cdr u,cdr v) else + id2int car u < id2int car v; + +symbolic procedure html_indexfile_subsetp(a,b); + null a or + b and car a = car b and html_indexfile_subsetp(cdr a,cdr b); + +%------------------- LISP index file -------------------------------- + + +symbolic procedure LISP_indexfile(); + begin scalar u,v,q,r,s,rr,!*lower,pack; + prin2t "..... compiling independent index file"; + pack := rootname(); + s := for each q in node_file_labels join + if pairp car q then {sort_term car q . q}; + s := sort(s,'html_indexfile_sort); + % remove trivial entries + r:=s; + while r do + <>; + % remove duplicates + r:=s; + while r and cdr r do + <>; + >>; + + outfile!*:= open(bldmsg("%w.hdx",pack),'output); + channelprintf(outfile!*, "%w generated from reference manual >%w< %n",'!%,pack); + channelprintf(outfile!*, "%w (node text description status details) %n",'!%,pack); + for each x in s do + <>; + close outfile!*; + outfile!*:=nil; + end; + +%------------------- printstruct ------------------------------- + +symbolic procedure printstruct(); + <>; + +symbolic procedure printstruct1(r,n); + <>; + +end; + + + +  Index: r36/mkhelp/helpunx.red ================================================================== --- r36/mkhelp/helpunx.red +++ r36/mkhelp/helpunx.red @@ -1,333 +1,333 @@ -% helpunx.red -% -% interfacing reduce help file to unix GNU texinfo structure -% -% Author: Herbert Melenk, ZIB Berlin -% -% November 1992 -% -% PSL dependent - -%-------------------- output ------------------------------------ - - -fluid '(outc newl par !*font !*newline nodechain - prevnode upnodes !*terpri); - - -symbolic procedure initoutput(); - << - upnodes := {"Top"}; - if null nodechain then - nodechain:={{"dummy 2",nil,"dummy 1"}}; - prevnode :={nil}; - channellinelength(outfile!*,200); - myprin2 bldmsg("@setfilename %w.info",package); - myterpri(); - >>; - -symbolic procedure endoutput(); - nil; - -symbolic procedure verbatim(u); - <>; - !*verbatim:=u; - >>; - -symbolic procedure toggle_line(); - <>; - -symbolic procedure newfont(f); - if currentfont neq f then - <>; - -symbolic procedure fontoff(); - <<%%% if !*font then channelprin2(outfile!*,"}"); - outc:=nil; - !*font:=nil>>; - -symbolic procedure fonton(); - <>; - !*font:=t>>; - -symbolic procedure myprin2 u; - if not(u eq '!\) then - <>; - - -fluid '(!*verbescape); - -symbolic procedure emit_start_verbatim(); - << myprin2 "@example"; myterpri();toggle_line()>>; - -symbolic procedure emit_end_verbatim(); - << toggle_line();myterpri();myprin2 "@end example"; myterpri();>>; - -symbolic procedure verbprin2 u; (textout u) where !*verbatim=t; - -symbolic procedure verbprin2 u; - if u = '!\ then <> - else - if u=!$eol!$ then <> - else - if (u = '!&) then - <> - else - if u memq '(!{ !}) then - <> - else - <>; - -symbolic procedure myprin2t u; - <>; - -symbolic procedure myterpri!*(); - !*terpri or myterpri(); - -symbolic procedure myterpri(); - <>; - -symbolic procedure textout(u); - if par and (u=!$eol!$ or u='! ) then nil else - if u='!{ or u='!} then nil else - <> - else - if (u = '!$) then - newfont(if currentfont = helvetica then courier else helvetica) - else - if (u neq '! ) or (outc neq '! ) or !*verbatim - then - <>; - >>; - -symbolic procedure textoutl(l); - if null l then nil else - if atom l then textout l else - for each x in l do textout x; - -symbolic procedure textout2(l); - if atom l then myprin2 l else - for each x in l do myprin2 - if x='! then '!_ else x; - -% -------- paragraph heading --------------------------- - -symbolic procedure par_heading(type); - <>; -% -------- directory structure ------------------------- - -fluid '(!*in!-directory actdir); - -symbolic procedure base_new_dir name; - % initial call for new section - <<% name := mycompress name; - prevnode := nil . prevnode; - upnodes:= name.upnodes; - >>; - -symbolic procedure emit_dir_new(); - % closing a section. - << if upnodes then - <>; - if prevnode then prevnode:=cdr prevnode; - >>; - -symbolic procedure emit_dir_key u; nil; - -symbolic procedure emit_dir_entry(name,lab); - begin scalar n,alias; - if not !*in!-directory then - <>; - myprin2 "* "; - textoutl if atom lab then name else lab; - myprin2 "::"; - n:=length (if atom lab then name else lab)+2; - for i:=n:25 do myprin2 " "; - if (alias:=assoc(lab,aliases)) then - <>; - %%% Klappaltar textoutl name; - if find_type(name) then textoutl find_type(name); - myterpri(); - end; - -fluid '(typen); - -typen := for each x in - '("package" "operator" "type" "variable" "concept" - "switch" "command" "introduction" "declaration") - collect explode2 x; - -symbolic procedure find_type(name); - <>; - -symbolic procedure emit_dir_header(); nil; - -symbolic procedure emit_dir_separator(); - <>; - -symbolic procedure emit_dir_label u; nil; - -symbolic procedure emit_dir_title u; - % emit_node_title (nil,u,'section); - emit_node_title (u,u,'section); - -symbolic procedure emit_dir_browse(u,n); nil; - -% ---- node structure - -symbolic procedure emit_node_separator(); - << - myterpri(); myterpri(); - outc:='! ; par:=t; - >>; - -symbolic procedure printem(s); - begin - fontoff(); - myprin2 "@titlefont{"; - mapc(s,'myprin2); - myprin2 "}"; - end; - -symbolic procedure printem(s); - <>; - -symbolic procedure printref u; - begin scalar l; - l := get_label u; - if l then - <> - else - <>; - end; - -symbolic procedure printnameref u; - <>; - -symbolic procedure emit_node_keys u; nil; - -symbolic procedure emit_node_key u; - if !*verbatim then textoutl u else - <>; - -symbolic procedure emit_hidden_node_key u; - if !*verbatim then textoutl u else - <>; - -symbolic procedure emit_node_label u; nil; - -%symbolic procedure emit_node_title (dummy,u,type); -symbolic procedure emit_node_title (u,dummy,type); - begin scalar slot,prev,next,up,cu,z; - cu := u; % cu:=mycompress u; - prev := if prevnode then car prevnode; - slot := assoc(cu,nodechain); - if null slot then - <>; - if prevnode and car prevnode - and (z:=assoc(car prevnode,nodechain)) then - <>; - up := if upnodes then car upnodes; - fonton(); - myterpri(); - myprin2 "@node "; - textoutl u; myprin2 ", "; - textoutl cadr slot;myprin2 ", "; - textoutl caddr slot;myprin2 ", "; - textoutl (up or "(dir)"); - myterpri(); - if null up then <>; - if null prevnode then prevnode := {cu} - else car prevnode := cu; - end; - -symbolic procedure emit_node_browse(u,n); - nil; - -symbolic procedure set_tab(); nil; -symbolic procedure release_tab(); nil; - -symbolic procedure print_bold u; - <>; - -symbolic procedure print_newline(); - <>; - !*newline:=t - >>; - -symbolic procedure second_newline(); - <>; - -symbolic procedure print_tab (); textout " "; - -%-------------------------------------------------------------- -symbolic procedure tue(); - % job "c:\herbert\whelp\redindex.tex"$ - job("redindex.tex","hugo.x"); - -%------------------- printstruct ------------------------------- - -symbolic procedure printstruct(); - <>; - -symbolic procedure printstruct1(r,n); - <>; - -end; - - +% helpunx.red +% +% interfacing reduce help file to unix GNU texinfo structure +% +% Author: Herbert Melenk, ZIB Berlin +% +% November 1992 +% +% PSL dependent + +%-------------------- output ------------------------------------ + + +fluid '(outc newl par !*font !*newline nodechain + prevnode upnodes !*terpri); + + +symbolic procedure initoutput(); + << + upnodes := {"Top"}; + if null nodechain then + nodechain:={{"dummy 2",nil,"dummy 1"}}; + prevnode :={nil}; + channellinelength(outfile!*,200); + myprin2 bldmsg("@setfilename %w.info",package); + myterpri(); + >>; + +symbolic procedure endoutput(); + nil; + +symbolic procedure verbatim(u); + <>; + !*verbatim:=u; + >>; + +symbolic procedure toggle_line(); + <>; + +symbolic procedure newfont(f); + if currentfont neq f then + <>; + +symbolic procedure fontoff(); + <<%%% if !*font then channelprin2(outfile!*,"}"); + outc:=nil; + !*font:=nil>>; + +symbolic procedure fonton(); + <>; + !*font:=t>>; + +symbolic procedure myprin2 u; + if not(u eq '!\) then + <>; + + +fluid '(!*verbescape); + +symbolic procedure emit_start_verbatim(); + << myprin2 "@example"; myterpri();toggle_line()>>; + +symbolic procedure emit_end_verbatim(); + << toggle_line();myterpri();myprin2 "@end example"; myterpri();>>; + +symbolic procedure verbprin2 u; (textout u) where !*verbatim=t; + +symbolic procedure verbprin2 u; + if u = '!\ then <> + else + if u=!$eol!$ then <> + else + if (u = '!&) then + <> + else + if u memq '(!{ !}) then + <> + else + <>; + +symbolic procedure myprin2t u; + <>; + +symbolic procedure myterpri!*(); + !*terpri or myterpri(); + +symbolic procedure myterpri(); + <>; + +symbolic procedure textout(u); + if par and (u=!$eol!$ or u='! ) then nil else + if u='!{ or u='!} then nil else + <> + else + if (u = '!$) then + newfont(if currentfont = helvetica then courier else helvetica) + else + if (u neq '! ) or (outc neq '! ) or !*verbatim + then + <>; + >>; + +symbolic procedure textoutl(l); + if null l then nil else + if atom l then textout l else + for each x in l do textout x; + +symbolic procedure textout2(l); + if atom l then myprin2 l else + for each x in l do myprin2 + if x='! then '!_ else x; + +% -------- paragraph heading --------------------------- + +symbolic procedure par_heading(type); + <>; +% -------- directory structure ------------------------- + +fluid '(!*in!-directory actdir); + +symbolic procedure base_new_dir name; + % initial call for new section + <<% name := mycompress name; + prevnode := nil . prevnode; + upnodes:= name.upnodes; + >>; + +symbolic procedure emit_dir_new(); + % closing a section. + << if upnodes then + <>; + if prevnode then prevnode:=cdr prevnode; + >>; + +symbolic procedure emit_dir_key u; nil; + +symbolic procedure emit_dir_entry(name,lab); + begin scalar n,alias; + if not !*in!-directory then + <>; + myprin2 "* "; + textoutl if atom lab then name else lab; + myprin2 "::"; + n:=length (if atom lab then name else lab)+2; + for i:=n:25 do myprin2 " "; + if (alias:=assoc(lab,aliases)) then + <>; + %%% Klappaltar textoutl name; + if find_type(name) then textoutl find_type(name); + myterpri(); + end; + +fluid '(typen); + +typen := for each x in + '("package" "operator" "type" "variable" "concept" + "switch" "command" "introduction" "declaration") + collect explode2 x; + +symbolic procedure find_type(name); + <>; + +symbolic procedure emit_dir_header(); nil; + +symbolic procedure emit_dir_separator(); + <>; + +symbolic procedure emit_dir_label u; nil; + +symbolic procedure emit_dir_title u; + % emit_node_title (nil,u,'section); + emit_node_title (u,u,'section); + +symbolic procedure emit_dir_browse(u,n); nil; + +% ---- node structure + +symbolic procedure emit_node_separator(); + << + myterpri(); myterpri(); + outc:='! ; par:=t; + >>; + +symbolic procedure printem(s); + begin + fontoff(); + myprin2 "@titlefont{"; + mapc(s,'myprin2); + myprin2 "}"; + end; + +symbolic procedure printem(s); + <>; + +symbolic procedure printref u; + begin scalar l; + l := get_label u; + if l then + <> + else + <>; + end; + +symbolic procedure printnameref u; + <>; + +symbolic procedure emit_node_keys u; nil; + +symbolic procedure emit_node_key u; + if !*verbatim then textoutl u else + <>; + +symbolic procedure emit_hidden_node_key u; + if !*verbatim then textoutl u else + <>; + +symbolic procedure emit_node_label u; nil; + +%symbolic procedure emit_node_title (dummy,u,type); +symbolic procedure emit_node_title (u,dummy,type); + begin scalar slot,prev,next,up,cu,z; + cu := u; % cu:=mycompress u; + prev := if prevnode then car prevnode; + slot := assoc(cu,nodechain); + if null slot then + <>; + if prevnode and car prevnode + and (z:=assoc(car prevnode,nodechain)) then + <>; + up := if upnodes then car upnodes; + fonton(); + myterpri(); + myprin2 "@node "; + textoutl u; myprin2 ", "; + textoutl cadr slot;myprin2 ", "; + textoutl caddr slot;myprin2 ", "; + textoutl (up or "(dir)"); + myterpri(); + if null up then <>; + if null prevnode then prevnode := {cu} + else car prevnode := cu; + end; + +symbolic procedure emit_node_browse(u,n); + nil; + +symbolic procedure set_tab(); nil; +symbolic procedure release_tab(); nil; + +symbolic procedure print_bold u; + <>; + +symbolic procedure print_newline(); + <>; + !*newline:=t + >>; + +symbolic procedure second_newline(); + <>; + +symbolic procedure print_tab (); textout " "; + +%-------------------------------------------------------------- +symbolic procedure tue(); + % job "c:\herbert\whelp\redindex.tex"$ + job("redindex.tex","hugo.x"); + +%------------------- printstruct ------------------------------- + +symbolic procedure printstruct(); + <>; + +symbolic procedure printstruct1(r,n); + <>; + +end; + +  Index: r36/mkhelp/helpwin.red ================================================================== --- r36/mkhelp/helpwin.red +++ r36/mkhelp/helpwin.red @@ -1,464 +1,464 @@ -% helpwin.red -% -% interfacing reduce help file to Microsoft help compiler rtf structure -% -% Author: Herbert Melenk, ZIB Berlin -% -% November 1992 -% - -fluid '(outc newl par !*font !*newline !*windows); - -!*windows:=t; -helvetica:= "f2"; -courier:= "f4"; - -% The original version of this file had initoutput() as an empty -% procedure, but after the run it used shell commands to concatenate -% the following text at the start and end of the generated file. To -% reduce the amount of shell programming needed and keep as much as -% possible in REDUCE code the (fixed) header and trailer text is -% generated explicitly (albeit clumsily) here now. - -symbolic procedure initoutput (); - begin - scalar o; - o := wrs outfile!*; - prin2t "{\rtf1\ansi \deff0{\fonttbl{\f0\froman Tms Rmn;}"; - prin2t "{\f1\fdecor Symbol;}"; - prin2t "{\f2\fswiss Helv;}"; - prin2t "{\f3\fmodern pica;}"; - prin2t "{\f4\fmodern Courier;}"; - prin2t "{\f5\fmodern elite;}"; - prin2t "{\f6\fmodern prestige;}"; - prin2t "{\f7\fmodern lettergothic;}"; - prin2t "{\f8\fmodern gothicPS;}"; - prin2t "{\f9\fmodern cubicPS;}"; - prin2t "{\f10\fmodern lineprinter;}"; - prin2t "{\f11\fswiss Helvetica;}"; - prin2t "{\f12\fmodern avantegarde;}"; - prin2t "{\f13\fmodern spartan;}"; - prin2t "{\f14\fmodern metro;}"; - prin2t "{\f15\fmodern presentation;}"; - prin2t "{\f16\fmodern APL;}"; - prin2t "{\f17\fmodern OCRA;}"; - prin2t "{\f18\fmodern OCRB;}"; - prin2t "{\f19\froman boldPS;}"; - prin2t "{\f20\froman emperorPS;}"; - prin2t "{\f21\froman madaleine;}"; - prin2t "{\f22\froman zapf humanist;}"; - prin2t "{\f23\froman classic;}"; - prin2t "{\f24\froman roman f;}"; - prin2t "{\f25\froman roman g;}"; - prin2t "{\f26\froman roman h;}"; - prin2t "{\f27\froman timesroman;}"; - prin2t "{\f28\froman century;}"; - prin2t "{\f29\froman palantino;}"; - prin2t "{\f30\froman souvenir;}"; - prin2t "{\f31\froman garamond;}"; - prin2t "{\f32\froman caledonia;}"; - prin2t "{\f33\froman bodini;}"; - prin2t "{\f34\froman university;}"; - prin2t "{\f35\fscript Script;}"; - prin2t "{\f36\fscript scriptPS;}"; - prin2t "{\f37\fscript script c;}"; - prin2t "{\f38\fscript script d;}"; - prin2t "{\f39\fscript commercial script;}"; - prin2t "{\f40\fscript park avenue;}"; - prin2t "{\f41\fscript coronet;}"; - prin2t "{\f42\fscript script h;}"; - prin2t "{\f43\fscript greek;}"; - prin2t "{\f44\froman kana;}"; - prin2t "{\f45\froman hebrew;}"; - prin2t "{\f46\froman roman s;}"; - prin2t "{\f47\froman russian;}"; - prin2t "{\f48\froman roman u;}"; - prin2t "{\f49\froman roman v;}"; - prin2t "{\f50\froman roman w;}"; - prin2t "{\f51\fdecor narrator;}"; - prin2t "{\f52\fdecor emphasis;}"; - prin2t "{\f53\fdecor zapf chancery;}"; - prin2t "{\f54\fdecor decor d;}"; - prin2t "{\f55\fdecor old english;}"; - prin2t "{\f56\fdecor decor f;}"; - prin2t "{\f57\fdecor decor g;}"; - prin2t "{\f58\fdecor cooper black;}"; - prin2t "{\f59\fnil linedraw;}"; - prin2t "{\f60\fnil math7;}"; - prin2t "{\f61\fnil math8;}"; - prin2t "{\f62\fnil bar3of9;}"; - prin2t "{\f63\fnil EAN;}"; - prin2t "{\f64\fnil pcline;}"; - prin2t "{\f65\fnil tech h;}"; - prin2t "{\f66\fswiss Helvetica-Narrow;}"; - prin2t "{\f67\fmodern Modern;}"; - prin2t "{\f68\froman Roman;}}"; - terpri(); - princ "{\colortbl;\red0\green0\blue0;\red0\green0\blue255;"; - prin2t "\red0\green255\blue255;\red0\green255\blue0;"; - princ "\red255\green0\blue255;\red255\green0\blue0;"; - prin2t "\red255\green255\blue0;\red255\green255\blue255;}"; - princ "{\stylesheet{\s244 \fs16\up6 \sbasedon0\snext0"; - prin2t " footnote reference;}"; - prin2t "{\s245 \fs20 \sbasedon0\snext245 footnote text;}"; - prin2t "{\s246\li720 \i\fs20 "; - prin2t "\sbasedon0\snext255 heading 9;}"; - prin2t "{\s247\li720 \i\fs20 \sbasedon0\snext255 heading 8;}"; - prin2t "{\s248\li720 \i\fs20 \sbasedon0\snext255 heading 7;}"; - prin2t "{\s249\li720 \fs20\ul \sbasedon0\snext255 heading 6;}"; - prin2t "{\s250\li720 \b\fs20 \sbasedon0\snext255 heading 5;}"; - prin2t "{\s251\li360 "; - prin2t "\ul \sbasedon0\snext255 heading 4;}"; - prin2t "{\s252\li360 \b \sbasedon0\snext255 heading 3;}"; - prin2t "{\s253\sb120 \b\f2 \sbasedon0\snext0 heading 2;}"; - prin2t "{\s254\sb240 \b\f2\ul \sbasedon0\snext0 heading 1;}"; - prin2t "{\s255\li720 \fs20 \sbasedon0\snext255 Normal Indent;}"; - prin2t "{\fs20 "; - prin2t "\snext0 Normal;}"; - prin2t "{\s2\fi-240\li480\sb80\tx480 \f11 \sbasedon0\snext2 nscba;}"; - prin2t "{\s3\fi-240\li240\sa20 \f11 \sbasedon0\snext3 j;}"; - prin2t "{\s4\li480\sa20 \f11 \sbasedon0\snext4 ij;}"; - prin2t "{\s5\sb80\sa20 \f11 \sbasedon0\snext5 btb;}"; - prin2t "{\s6\fi-240\li2400\sb20\sa20 \f11\fs20 "; - prin2t "\sbasedon0\snext6 ctcb;}"; - prin2t "{\s7\fi-240\li480\sa40\tx480 \f11 \sbasedon0\snext7 ns;}"; - prin2t "{\s8\sa120 \f11\fs28 \sbasedon0\snext8 TT;}"; - prin2t "{\s9\fi-240\li2400\sa20 \f11 \sbasedon0\snext9 crtj;}"; - prin2t "{\s10\fi-240\li480\tx480 \f11 \sbasedon0\snext10 nsca;}"; - prin2t "{\s11\sa20 \f11 "; - prin2t "\sbasedon0\snext11 bt;}"; - prin2t "{\s12\li240\sb120\sa40 \f11 \sbasedon0\snext12 Hf;}"; - prin2t "{\s13\li240\sb120\sa40 \f11 \sbasedon0\snext13 Hs;}"; - prin2t "{\s14\li480\sb120\sa40 \f11 \sbasedon0\snext14 RT;}"; - princ "{\s15\fi-2160\li2160\sb240\sa80\tx2160 \f11"; - prin2t " \sbasedon0\snext15 c;}"; - prin2t "{"; - prin2t "\s16\li2160\sa20 \f11 \sbasedon0\snext16 ct;}"; - prin2t "{\s17\li240\sa20 \f11 \sbasedon0\snext17 it;}"; - prin2t "{\s18\li480 \f11\fs20 \sbasedon0\snext18 nsct;}"; - prin2t "{\s19\fi-160\li400\sb80\sa40 \f11 \sbasedon0\snext19 nscb;}"; - prin2t "{\s20\fi-2640\li2880\sb120\sa40\brdrb\brdrs \brdrbtw\brdrs "; - prin2t "\tx2880 \f11 \sbasedon0\snext20 HC2;}"; - princ "{\s21\fi-2640\li2880\sb120\sa20\tx2880 \f11"; - prin2t " \sbasedon0\snext21 C2;}"; - prin2t "{\s22\fi-240\li2400\sa20 \f11\fs20 \sbasedon0\snext22 ctc;}"; - prin2t "{\s23\li2160\sb160 \f11 \sbasedon0\snext23 crt;}"; - prin2t "{\s24\li480\sb20\sa40 \f11 "; - prin2t "\sbasedon0\snext24 or;}}"; - terpri(); - princ "{\info{\author Dan Davids}{\operator Dan Davids}"; - prin2t "{\creatim\yr2137\mo8\dy7}"; - princ "{\revtim\yr1990\mo5\dy9\hr16\min54}{\version3}"; - prin2t "{\edmins3134}{\nofpages0}"; - prin2t "{\nofwords65536}{\nofchars69885}{\vern8310}}"; - terpri(); - prin2t "\ftnbj \sectd \linex576\endnhere "; - prin2t "\pard\plain \sl240 \fs20 "; - terpri(); - terpri(); - terpri(); - wrs o; - end; - -symbolic procedure endoutput (); - begin - scalar o; - o := wrs outfile!*; - prin2t "}"; - wrs o - end; - -symbolic procedure verbatim u; !*verbatim := u; - -symbolic procedure newfont(f); - if currentfont neq f then - <>; - -symbolic procedure fontoff(); - <>; - -symbolic procedure fonton(); - <>; - !*font:=t>>; - -symbolic procedure myprin2 u; - <>; - -symbolic procedure myprin2_protected u; - <>; - -fluid '(!*verbescape); - -symbolic procedure emit_start_verbatim(); nil; -symbolic procedure emit_end_verbatim(); nil; -symbolic procedure verbprin2 u; - if u = '!\ then <> - else - if u=!$eol!$ then <> - else - if (u = '!&) then - <> - else - if u memq '(!{ !}) then - <> - else - <>; - -symbolic procedure myterpri(); - channelterpri outfile!*; - -symbolic procedure number4out n; - % print number with 4 digits. - << if n<10 then textout "0"; - if n<100 then textout "0"; - if n<1000 then textout "0"; - textout n>>; - -% par = t: paragraph has been terminated - no new data so far -% newl = t: last character has been an EOL - -symbolic procedure textout(u); - if par and (u=!$eol!$ or u='! ) then nil else - <> - else - if (u = '!$) then - newfont(if currentfont = helvetica then courier else helvetica) - else - if (u memq '(!{ !})) then <> else - if (u neq '! ) or (outc neq '! ) or !*verbatim - then - <>; - >>; - -% -------- paragraph heading --------------------------- - -symbolic procedure par_heading(type); - <>; - -% -------- directory structure ------------------------- - -symbolic procedure base_new_dir(name); nil; - -symbolic procedure emit_dir_new(); nil; - -symbolic procedure emit_dir_key u; - emit_node_key u; - -symbolic procedure emit_dir_separator(); - emit_node_separator(); - -symbolic procedure emit_dir_label u; - emit_node_label u; - -symbolic procedure emit_dir_title u; - emit_node_title(u,nil,'section); - -symbolic procedure emit_dir_browse(u,n); - emit_node_browse(u,n); - -% ---- node structure - -symbolic procedure emit_node_separator(); - <>; - - -symbolic procedure textout2(l); - if atom l then myprin2 l else - for each x in l do myprin2 - if x='! then '!_ else x; - -symbolic procedure printem(s); - % print italic - begin - myprin2 "{\i "; - mapc(s,'myprin2); - myprin2 "} "; - end; - -symbolic procedure printem(s); - begin - fontoff(); - myprin2 "{\f3 "; - mapc(s,'myprin2_protected); - myprin2 "} "; - end; - -symbolic procedure printref u; - begin scalar r; - r:= get_label u; - if null r then return printem u; - fontoff(); - myterpri(); - myprin2 "{\f2\uldb "; - mapc(u,'myprin2); - myprin2 "}{\v\f2 "; - mapc(r,'myprin2); - myprin2 "}"; myprin2 " "; - myterpri(); - end; - -symbolic procedure printnameref u; - printref u; - -fluid '(key_database); - -symbolic procedure emit_node_keys u; - begin scalar keys; - keys := assoc(u,key_database); - if null keys then return; - keys := cdr keys; - fonton(); - myterpri(); - myprin2 " K{\footnote \pard\plain \sl240 \fs20 K "; - while keys do - <>; - myprin2 "}"; - myterpri(); - end; - -symbolic procedure emit_node_key u; - emit_hidden_node_key u; - -symbolic procedure emit_hidden_node_key u; - if current_node!* then - begin scalar q; - q:= assoc(current_node!*,key_database); - if null q then - key_database := (current_node!* . {u}).key_database - else - if not member(u,cdr q) then cdr q:=u.cdr q; - end; - -symbolic procedure emit_node_label u; - <>; - -symbolic procedure emit_node_title(u,dummy,type); - <>; - -symbolic procedure emit_node_browse(u,n); - <>; - - -symbolic procedure print_bold u; - <>; - -symbolic procedure emit_dir_header(); - <>; - -symbolic procedure emit_dir_entry(name,lab); - begin scalar alias; - fontoff(); - myprin2 "{\f2 \tab}{\f2\uldb "; - mapc(name,'myprin2); - myprin2 "}"; - myterpri(); - myprin2 "{\v\f2 "; - textout2 lab; - myprin2 "}"; - if (alias:=assoc(lab,aliases)) then - <>; - print_newline(); - end; - -symbolic procedure print_newline(); - <>; - !*newline:=t - >>; - -symbolic procedure second_newline(); - <>; - -symbolic procedure print_tab (); - <>; - -%------------------- printstruct ------------------------------- - -symbolic procedure printstruct(); - <>; - -symbolic procedure printstruct1(r,n); - <>; - -end; - - +% helpwin.red +% +% interfacing reduce help file to Microsoft help compiler rtf structure +% +% Author: Herbert Melenk, ZIB Berlin +% +% November 1992 +% + +fluid '(outc newl par !*font !*newline !*windows); + +!*windows:=t; +helvetica:= "f2"; +courier:= "f4"; + +% The original version of this file had initoutput() as an empty +% procedure, but after the run it used shell commands to concatenate +% the following text at the start and end of the generated file. To +% reduce the amount of shell programming needed and keep as much as +% possible in REDUCE code the (fixed) header and trailer text is +% generated explicitly (albeit clumsily) here now. + +symbolic procedure initoutput (); + begin + scalar o; + o := wrs outfile!*; + prin2t "{\rtf1\ansi \deff0{\fonttbl{\f0\froman Tms Rmn;}"; + prin2t "{\f1\fdecor Symbol;}"; + prin2t "{\f2\fswiss Helv;}"; + prin2t "{\f3\fmodern pica;}"; + prin2t "{\f4\fmodern Courier;}"; + prin2t "{\f5\fmodern elite;}"; + prin2t "{\f6\fmodern prestige;}"; + prin2t "{\f7\fmodern lettergothic;}"; + prin2t "{\f8\fmodern gothicPS;}"; + prin2t "{\f9\fmodern cubicPS;}"; + prin2t "{\f10\fmodern lineprinter;}"; + prin2t "{\f11\fswiss Helvetica;}"; + prin2t "{\f12\fmodern avantegarde;}"; + prin2t "{\f13\fmodern spartan;}"; + prin2t "{\f14\fmodern metro;}"; + prin2t "{\f15\fmodern presentation;}"; + prin2t "{\f16\fmodern APL;}"; + prin2t "{\f17\fmodern OCRA;}"; + prin2t "{\f18\fmodern OCRB;}"; + prin2t "{\f19\froman boldPS;}"; + prin2t "{\f20\froman emperorPS;}"; + prin2t "{\f21\froman madaleine;}"; + prin2t "{\f22\froman zapf humanist;}"; + prin2t "{\f23\froman classic;}"; + prin2t "{\f24\froman roman f;}"; + prin2t "{\f25\froman roman g;}"; + prin2t "{\f26\froman roman h;}"; + prin2t "{\f27\froman timesroman;}"; + prin2t "{\f28\froman century;}"; + prin2t "{\f29\froman palantino;}"; + prin2t "{\f30\froman souvenir;}"; + prin2t "{\f31\froman garamond;}"; + prin2t "{\f32\froman caledonia;}"; + prin2t "{\f33\froman bodini;}"; + prin2t "{\f34\froman university;}"; + prin2t "{\f35\fscript Script;}"; + prin2t "{\f36\fscript scriptPS;}"; + prin2t "{\f37\fscript script c;}"; + prin2t "{\f38\fscript script d;}"; + prin2t "{\f39\fscript commercial script;}"; + prin2t "{\f40\fscript park avenue;}"; + prin2t "{\f41\fscript coronet;}"; + prin2t "{\f42\fscript script h;}"; + prin2t "{\f43\fscript greek;}"; + prin2t "{\f44\froman kana;}"; + prin2t "{\f45\froman hebrew;}"; + prin2t "{\f46\froman roman s;}"; + prin2t "{\f47\froman russian;}"; + prin2t "{\f48\froman roman u;}"; + prin2t "{\f49\froman roman v;}"; + prin2t "{\f50\froman roman w;}"; + prin2t "{\f51\fdecor narrator;}"; + prin2t "{\f52\fdecor emphasis;}"; + prin2t "{\f53\fdecor zapf chancery;}"; + prin2t "{\f54\fdecor decor d;}"; + prin2t "{\f55\fdecor old english;}"; + prin2t "{\f56\fdecor decor f;}"; + prin2t "{\f57\fdecor decor g;}"; + prin2t "{\f58\fdecor cooper black;}"; + prin2t "{\f59\fnil linedraw;}"; + prin2t "{\f60\fnil math7;}"; + prin2t "{\f61\fnil math8;}"; + prin2t "{\f62\fnil bar3of9;}"; + prin2t "{\f63\fnil EAN;}"; + prin2t "{\f64\fnil pcline;}"; + prin2t "{\f65\fnil tech h;}"; + prin2t "{\f66\fswiss Helvetica-Narrow;}"; + prin2t "{\f67\fmodern Modern;}"; + prin2t "{\f68\froman Roman;}}"; + terpri(); + princ "{\colortbl;\red0\green0\blue0;\red0\green0\blue255;"; + prin2t "\red0\green255\blue255;\red0\green255\blue0;"; + princ "\red255\green0\blue255;\red255\green0\blue0;"; + prin2t "\red255\green255\blue0;\red255\green255\blue255;}"; + princ "{\stylesheet{\s244 \fs16\up6 \sbasedon0\snext0"; + prin2t " footnote reference;}"; + prin2t "{\s245 \fs20 \sbasedon0\snext245 footnote text;}"; + prin2t "{\s246\li720 \i\fs20 "; + prin2t "\sbasedon0\snext255 heading 9;}"; + prin2t "{\s247\li720 \i\fs20 \sbasedon0\snext255 heading 8;}"; + prin2t "{\s248\li720 \i\fs20 \sbasedon0\snext255 heading 7;}"; + prin2t "{\s249\li720 \fs20\ul \sbasedon0\snext255 heading 6;}"; + prin2t "{\s250\li720 \b\fs20 \sbasedon0\snext255 heading 5;}"; + prin2t "{\s251\li360 "; + prin2t "\ul \sbasedon0\snext255 heading 4;}"; + prin2t "{\s252\li360 \b \sbasedon0\snext255 heading 3;}"; + prin2t "{\s253\sb120 \b\f2 \sbasedon0\snext0 heading 2;}"; + prin2t "{\s254\sb240 \b\f2\ul \sbasedon0\snext0 heading 1;}"; + prin2t "{\s255\li720 \fs20 \sbasedon0\snext255 Normal Indent;}"; + prin2t "{\fs20 "; + prin2t "\snext0 Normal;}"; + prin2t "{\s2\fi-240\li480\sb80\tx480 \f11 \sbasedon0\snext2 nscba;}"; + prin2t "{\s3\fi-240\li240\sa20 \f11 \sbasedon0\snext3 j;}"; + prin2t "{\s4\li480\sa20 \f11 \sbasedon0\snext4 ij;}"; + prin2t "{\s5\sb80\sa20 \f11 \sbasedon0\snext5 btb;}"; + prin2t "{\s6\fi-240\li2400\sb20\sa20 \f11\fs20 "; + prin2t "\sbasedon0\snext6 ctcb;}"; + prin2t "{\s7\fi-240\li480\sa40\tx480 \f11 \sbasedon0\snext7 ns;}"; + prin2t "{\s8\sa120 \f11\fs28 \sbasedon0\snext8 TT;}"; + prin2t "{\s9\fi-240\li2400\sa20 \f11 \sbasedon0\snext9 crtj;}"; + prin2t "{\s10\fi-240\li480\tx480 \f11 \sbasedon0\snext10 nsca;}"; + prin2t "{\s11\sa20 \f11 "; + prin2t "\sbasedon0\snext11 bt;}"; + prin2t "{\s12\li240\sb120\sa40 \f11 \sbasedon0\snext12 Hf;}"; + prin2t "{\s13\li240\sb120\sa40 \f11 \sbasedon0\snext13 Hs;}"; + prin2t "{\s14\li480\sb120\sa40 \f11 \sbasedon0\snext14 RT;}"; + princ "{\s15\fi-2160\li2160\sb240\sa80\tx2160 \f11"; + prin2t " \sbasedon0\snext15 c;}"; + prin2t "{"; + prin2t "\s16\li2160\sa20 \f11 \sbasedon0\snext16 ct;}"; + prin2t "{\s17\li240\sa20 \f11 \sbasedon0\snext17 it;}"; + prin2t "{\s18\li480 \f11\fs20 \sbasedon0\snext18 nsct;}"; + prin2t "{\s19\fi-160\li400\sb80\sa40 \f11 \sbasedon0\snext19 nscb;}"; + prin2t "{\s20\fi-2640\li2880\sb120\sa40\brdrb\brdrs \brdrbtw\brdrs "; + prin2t "\tx2880 \f11 \sbasedon0\snext20 HC2;}"; + princ "{\s21\fi-2640\li2880\sb120\sa20\tx2880 \f11"; + prin2t " \sbasedon0\snext21 C2;}"; + prin2t "{\s22\fi-240\li2400\sa20 \f11\fs20 \sbasedon0\snext22 ctc;}"; + prin2t "{\s23\li2160\sb160 \f11 \sbasedon0\snext23 crt;}"; + prin2t "{\s24\li480\sb20\sa40 \f11 "; + prin2t "\sbasedon0\snext24 or;}}"; + terpri(); + princ "{\info{\author Dan Davids}{\operator Dan Davids}"; + prin2t "{\creatim\yr2137\mo8\dy7}"; + princ "{\revtim\yr1990\mo5\dy9\hr16\min54}{\version3}"; + prin2t "{\edmins3134}{\nofpages0}"; + prin2t "{\nofwords65536}{\nofchars69885}{\vern8310}}"; + terpri(); + prin2t "\ftnbj \sectd \linex576\endnhere "; + prin2t "\pard\plain \sl240 \fs20 "; + terpri(); + terpri(); + terpri(); + wrs o; + end; + +symbolic procedure endoutput (); + begin + scalar o; + o := wrs outfile!*; + prin2t "}"; + wrs o + end; + +symbolic procedure verbatim u; !*verbatim := u; + +symbolic procedure newfont(f); + if currentfont neq f then + <>; + +symbolic procedure fontoff(); + <>; + +symbolic procedure fonton(); + <>; + !*font:=t>>; + +symbolic procedure myprin2 u; + <>; + +symbolic procedure myprin2_protected u; + <>; + +fluid '(!*verbescape); + +symbolic procedure emit_start_verbatim(); nil; +symbolic procedure emit_end_verbatim(); nil; +symbolic procedure verbprin2 u; + if u = '!\ then <> + else + if u=!$eol!$ then <> + else + if (u = '!&) then + <> + else + if u memq '(!{ !}) then + <> + else + <>; + +symbolic procedure myterpri(); + channelterpri outfile!*; + +symbolic procedure number4out n; + % print number with 4 digits. + << if n<10 then textout "0"; + if n<100 then textout "0"; + if n<1000 then textout "0"; + textout n>>; + +% par = t: paragraph has been terminated - no new data so far +% newl = t: last character has been an EOL + +symbolic procedure textout(u); + if par and (u=!$eol!$ or u='! ) then nil else + <> + else + if (u = '!$) then + newfont(if currentfont = helvetica then courier else helvetica) + else + if (u memq '(!{ !})) then <> else + if (u neq '! ) or (outc neq '! ) or !*verbatim + then + <>; + >>; + +% -------- paragraph heading --------------------------- + +symbolic procedure par_heading(type); + <>; + +% -------- directory structure ------------------------- + +symbolic procedure base_new_dir(name); nil; + +symbolic procedure emit_dir_new(); nil; + +symbolic procedure emit_dir_key u; + emit_node_key u; + +symbolic procedure emit_dir_separator(); + emit_node_separator(); + +symbolic procedure emit_dir_label u; + emit_node_label u; + +symbolic procedure emit_dir_title u; + emit_node_title(u,nil,'section); + +symbolic procedure emit_dir_browse(u,n); + emit_node_browse(u,n); + +% ---- node structure + +symbolic procedure emit_node_separator(); + <>; + + +symbolic procedure textout2(l); + if atom l then myprin2 l else + for each x in l do myprin2 + if x='! then '!_ else x; + +symbolic procedure printem(s); + % print italic + begin + myprin2 "{\i "; + mapc(s,'myprin2); + myprin2 "} "; + end; + +symbolic procedure printem(s); + begin + fontoff(); + myprin2 "{\f3 "; + mapc(s,'myprin2_protected); + myprin2 "} "; + end; + +symbolic procedure printref u; + begin scalar r; + r:= get_label u; + if null r then return printem u; + fontoff(); + myterpri(); + myprin2 "{\f2\uldb "; + mapc(u,'myprin2); + myprin2 "}{\v\f2 "; + mapc(r,'myprin2); + myprin2 "}"; myprin2 " "; + myterpri(); + end; + +symbolic procedure printnameref u; + printref u; + +fluid '(key_database); + +symbolic procedure emit_node_keys u; + begin scalar keys; + keys := assoc(u,key_database); + if null keys then return; + keys := cdr keys; + fonton(); + myterpri(); + myprin2 " K{\footnote \pard\plain \sl240 \fs20 K "; + while keys do + <>; + myprin2 "}"; + myterpri(); + end; + +symbolic procedure emit_node_key u; + emit_hidden_node_key u; + +symbolic procedure emit_hidden_node_key u; + if current_node!* then + begin scalar q; + q:= assoc(current_node!*,key_database); + if null q then + key_database := (current_node!* . {u}).key_database + else + if not member(u,cdr q) then cdr q:=u.cdr q; + end; + +symbolic procedure emit_node_label u; + <>; + +symbolic procedure emit_node_title(u,dummy,type); + <>; + +symbolic procedure emit_node_browse(u,n); + <>; + + +symbolic procedure print_bold u; + <>; + +symbolic procedure emit_dir_header(); + <>; + +symbolic procedure emit_dir_entry(name,lab); + begin scalar alias; + fontoff(); + myprin2 "{\f2 \tab}{\f2\uldb "; + mapc(name,'myprin2); + myprin2 "}"; + myterpri(); + myprin2 "{\v\f2 "; + textout2 lab; + myprin2 "}"; + if (alias:=assoc(lab,aliases)) then + <>; + print_newline(); + end; + +symbolic procedure print_newline(); + <>; + !*newline:=t + >>; + +symbolic procedure second_newline(); + <>; + +symbolic procedure print_tab (); + <>; + +%------------------- printstruct ------------------------------- + +symbolic procedure printstruct(); + <>; + +symbolic procedure printstruct1(r,n); + <>; + +end; + +  Index: r36/mkhelp/minitex.red ================================================================== --- r36/mkhelp/minitex.red +++ r36/mkhelp/minitex.red @@ -1,326 +1,326 @@ -module minitex; % support of minimal tex syntax for - % reduce help file compilation. - - % author: Herbert Melenk, ZIB Berlin - -% input: list of single characters in Latex subset syntax -% -% output: list of rows, tagged by line number and max column -% length. -% -% supported syntax elements: -% -% ^ exponent -% _ index -% \frac{ ... }{ ... } -% -% escape sequences \{ \} \_ \^ \\ - -fluid '(ESCAPE RAISE LOWER X0 Y0 CON); - -fluid '(xlo xhi yhi ylo minitex_input minitex_page); - -ESCAPE := '!\; -RAISE := '!^; -LOWER := '!_; - -X0 := 2; -Y0 := 3; -CON := 4; - -symbolic procedure mintex_convert0 s; - if null s then s else - if null cdr s then s else - if car s ='!\ and cadr s = '!\ then !$eol!$ . mintex_convert0 cddr s - else car s . mintex_convert0 cdr s; - -symbolic procedure mintex_convert s; mintex_convert0 s; - -symbolic procedure minitex(string); - begin scalar q,w; integer r,c; - minitex_page := for i:=-20:20 collect {i}; - minitex_input := mintex_convert string; - q := make_chain(0,'hugo); - if null q then return nil; - minitex_collect q; - for each l in minitex_page do - if (l:=cdr l) then - <c then c:=length(l); - w:=l.w; - >>; - return r.c. reverse w; - end; - -symbolic procedure minitex_pop_char(); - if minitex_input then - begin scalar c; - c := car minitex_input; - minitex_input := cdr minitex_input; - return c; - end; - -symbolic procedure minitex_skip(cc); - begin scalar c; - c := nil; - while c neq cc do c:=minitex_pop_char(); - end; - -symbolic procedure minitex_next_char(); - if minitex_input then car minitex_input; - -symbolic procedure struct(type); - {type,0,0,0}; - - -symbolic procedure make_chain(font,term); - begin integer indpos,xact,d,fh, - lxlo, lxhi, lylo,lyhi, - yindhi,yindlo; - scalar c,cc,cell,new,end_code; - - fh:=1; % font height - - end_code := 0; - cell := struct('chain); - - loop: - c := minitex_pop_char(); - cc := minitex_next_char(); - if(c = '!{ and null term) then - <>; - - after_syntax: - if not pairp new then <>; - - nth(cell,CON):=append(nth(cell,CON),{new}); - nth(new,X0) := xact; - xact := xact + xhi; - if(xact>lxhi) then lxhi := xact else xact:=lxhi; - if(ylolyhi) then lyhi:=yhi; - - if(term) then goto loop; - - finish: - ylo := lylo; yhi := lyhi; - xlo := lxlo; xhi := lxhi; - if pairp nth(cell,CON) then return(cell); - end; - -symbolic procedure make_char(font,cs,c); - begin scalar cell; - cell := struct('char); - nth(cell,CON) := c; - ylo := 0; yhi:=1; - xlo := 0; xhi:=1; - return(cell); - end; - -symbolic procedure make_frac(font); - begin scalar cell; - scalar numr,denr,line; - integer nxhi,dxhi,nyhi,dyhi,nylo,dylo; - integer lxhi; - integer yline,ydist; - ydist := 1; - - cell := struct('chain); - while minitex_input and car minitex_input neq '!{ do - minitex_input:=cdr minitex_input; - yline := 0; - numr := make_chain(font,nil); - nxhi := xhi; nyhi := yhi; nylo := ylo; - - while minitex_input and car minitex_input neq '!{ do - minitex_input:=cdr minitex_input; - xhi := 0; xlo := 0; yhi := 0; ylo := 0; - denr := make_chain(font,nil); - dxhi := xhi; dyhi := yhi; dylo := ylo; - - % /* move the shorter one to the middle */ - if(dxhi > nxhi) then - << - lxhi := dxhi; - nth(numr,X0) := (dxhi - nxhi)/2; - >> - else - << - lxhi := nxhi; - nth(denr,X0) := (nxhi - dxhi)/2; - >>; - - % /* make line */ - line := make_line(0,yline,lxhi,yline); - - % /* put num on top */ - nth(numr,Y0) := yline - ydist - (nyhi-1); - - % /* put denr below */ - nth(denr,Y0) := yline + ydist - dylo; - - % /* total frame */ - xlo := 0; xhi := lxhi; - ylo := yline - ydist -(nyhi-nylo); - yhi := yline + ydist +(dyhi-dylo); - - % /* make chain */ - nth(cell,CON) := {line,numr,denr}; - return cell; - end; - -symbolic procedure make_line(x,y,x1,y1); - <> where cell=struct('line); - -symbolic procedure make_multi(font); - begin scalar cell,new; integer base; - minitex_skip('!}); - minitex_skip('!}); - cell := struct('chain); nth(cell,CON) :=nil; - while pairp (new :=make_chain(font,!$eol!$)) do - << nth(cell,CON) := append(nth(cell,CON),{new}); - nth(new,Y0) := base; - base:=base + (yhi-ylo) + 1; - >>; - yhi := base; - return cell; - end; - - -symbolic procedure make_end(font); - <>; - -%---------------------- dispatch ----------------------------------- - -fluid '(nullum); -nullum := struct('chain); -nth(nullum,CON):= nil; - -symbolic procedure make_escape(font,term); - if my_compare('(!f !r !a !c)) then make_frac(font) - else - if my_compare('(!r !f !r !a !c)) then make_frac(font) - else - if my_compare('(!b !e !g !i !n { !m !u !l !t !i )) then make_multi(font) - else - if my_compare('(!e !n !d)) then make_end(font) - else - if my_compare('(!e !m)) then nullum - else - if my_compare('(!n !a !m !e)) then nullum - else - if my_compare('(!i !t)) then nullum - else - <>; - -symbolic procedure my_compare s; - begin scalar i,c; - i := minitex_input; - while s and (c := minitex_pop_char()) and - c=car s do s:= cdr s; - if null s then return t; - minitex_input := i; - return nil; - end; - -%-------------- interprete structure: fill into page --------------- - -symbolic procedure minitex_collect u; - minitex_do(0,0,0,u); - -symbolic procedure minitex_do(x,y,font,box); - <>; - apply(get(car box,'minitex),list(x,y,font,box)); - >>; - -put('chain,'minitex,'minitex_chain); - -symbolic procedure minitex_chain(x,y,font,box); - << x:=x+nth(box,X0); y := y+nth(box,Y0); - for each u in nth(box,CON) do minitex_do(x,y,font,u) - >>; - -put('char,'minitex,'minitex_char); - -symbolic procedure minitex_char(x,y,font,box); - begin - x:=x+nth(box,X0); y := y+nth(box,Y0); - minitex_putchar(x,y,nth(box,CON)); - end; - -put('line,'minitex,'minitex_line); - -symbolic procedure minitex_line(x,y,font,box); - begin - x:=x+nth(box,X0); y := y+nth(box,Y0); - for i:=x:x+nth(box,CON) do - minitex_putchar(i,y,'!-); - end; - -symbolic procedure minitex_putchar(x,y,c); - begin scalar r; - x:=x+2; - r:=assoc(y,minitex_page); - while length rc then c:=length(l); + w:=l.w; + >>; + return r.c. reverse w; + end; + +symbolic procedure minitex_pop_char(); + if minitex_input then + begin scalar c; + c := car minitex_input; + minitex_input := cdr minitex_input; + return c; + end; + +symbolic procedure minitex_skip(cc); + begin scalar c; + c := nil; + while c neq cc do c:=minitex_pop_char(); + end; + +symbolic procedure minitex_next_char(); + if minitex_input then car minitex_input; + +symbolic procedure struct(type); + {type,0,0,0}; + + +symbolic procedure make_chain(font,term); + begin integer indpos,xact,d,fh, + lxlo, lxhi, lylo,lyhi, + yindhi,yindlo; + scalar c,cc,cell,new,end_code; + + fh:=1; % font height + + end_code := 0; + cell := struct('chain); + + loop: + c := minitex_pop_char(); + cc := minitex_next_char(); + if(c = '!{ and null term) then + <>; + + after_syntax: + if not pairp new then <>; + + nth(cell,CON):=append(nth(cell,CON),{new}); + nth(new,X0) := xact; + xact := xact + xhi; + if(xact>lxhi) then lxhi := xact else xact:=lxhi; + if(ylolyhi) then lyhi:=yhi; + + if(term) then goto loop; + + finish: + ylo := lylo; yhi := lyhi; + xlo := lxlo; xhi := lxhi; + if pairp nth(cell,CON) then return(cell); + end; + +symbolic procedure make_char(font,cs,c); + begin scalar cell; + cell := struct('char); + nth(cell,CON) := c; + ylo := 0; yhi:=1; + xlo := 0; xhi:=1; + return(cell); + end; + +symbolic procedure make_frac(font); + begin scalar cell; + scalar numr,denr,line; + integer nxhi,dxhi,nyhi,dyhi,nylo,dylo; + integer lxhi; + integer yline,ydist; + ydist := 1; + + cell := struct('chain); + while minitex_input and car minitex_input neq '!{ do + minitex_input:=cdr minitex_input; + yline := 0; + numr := make_chain(font,nil); + nxhi := xhi; nyhi := yhi; nylo := ylo; + + while minitex_input and car minitex_input neq '!{ do + minitex_input:=cdr minitex_input; + xhi := 0; xlo := 0; yhi := 0; ylo := 0; + denr := make_chain(font,nil); + dxhi := xhi; dyhi := yhi; dylo := ylo; + + % /* move the shorter one to the middle */ + if(dxhi > nxhi) then + << + lxhi := dxhi; + nth(numr,X0) := (dxhi - nxhi)/2; + >> + else + << + lxhi := nxhi; + nth(denr,X0) := (nxhi - dxhi)/2; + >>; + + % /* make line */ + line := make_line(0,yline,lxhi,yline); + + % /* put num on top */ + nth(numr,Y0) := yline - ydist - (nyhi-1); + + % /* put denr below */ + nth(denr,Y0) := yline + ydist - dylo; + + % /* total frame */ + xlo := 0; xhi := lxhi; + ylo := yline - ydist -(nyhi-nylo); + yhi := yline + ydist +(dyhi-dylo); + + % /* make chain */ + nth(cell,CON) := {line,numr,denr}; + return cell; + end; + +symbolic procedure make_line(x,y,x1,y1); + <> where cell=struct('line); + +symbolic procedure make_multi(font); + begin scalar cell,new; integer base; + minitex_skip('!}); + minitex_skip('!}); + cell := struct('chain); nth(cell,CON) :=nil; + while pairp (new :=make_chain(font,!$eol!$)) do + << nth(cell,CON) := append(nth(cell,CON),{new}); + nth(new,Y0) := base; + base:=base + (yhi-ylo) + 1; + >>; + yhi := base; + return cell; + end; + + +symbolic procedure make_end(font); + <>; + +%---------------------- dispatch ----------------------------------- + +fluid '(nullum); +nullum := struct('chain); +nth(nullum,CON):= nil; + +symbolic procedure make_escape(font,term); + if my_compare('(!f !r !a !c)) then make_frac(font) + else + if my_compare('(!r !f !r !a !c)) then make_frac(font) + else + if my_compare('(!b !e !g !i !n { !m !u !l !t !i )) then make_multi(font) + else + if my_compare('(!e !n !d)) then make_end(font) + else + if my_compare('(!e !m)) then nullum + else + if my_compare('(!n !a !m !e)) then nullum + else + if my_compare('(!i !t)) then nullum + else + <>; + +symbolic procedure my_compare s; + begin scalar i,c; + i := minitex_input; + while s and (c := minitex_pop_char()) and + c=car s do s:= cdr s; + if null s then return t; + minitex_input := i; + return nil; + end; + +%-------------- interprete structure: fill into page --------------- + +symbolic procedure minitex_collect u; + minitex_do(0,0,0,u); + +symbolic procedure minitex_do(x,y,font,box); + <>; + apply(get(car box,'minitex),list(x,y,font,box)); + >>; + +put('chain,'minitex,'minitex_chain); + +symbolic procedure minitex_chain(x,y,font,box); + << x:=x+nth(box,X0); y := y+nth(box,Y0); + for each u in nth(box,CON) do minitex_do(x,y,font,u) + >>; + +put('char,'minitex,'minitex_char); + +symbolic procedure minitex_char(x,y,font,box); + begin + x:=x+nth(box,X0); y := y+nth(box,Y0); + minitex_putchar(x,y,nth(box,CON)); + end; + +put('line,'minitex,'minitex_line); + +symbolic procedure minitex_line(x,y,font,box); + begin + x:=x+nth(box,X0); y := y+nth(box,Y0); + for i:=x:x+nth(box,CON) do + minitex_putchar(i,y,'!-); + end; + +symbolic procedure minitex_putchar(x,y,c); + begin scalar r; + x:=x+2; + r:=assoc(y,minitex_page); + while length r -To: shar-list@rand.org -Subject: Shar File - - -# This is a shell archive. Remove anything before this line, then -# unpack it by saving it in a file and typing "sh file". (Files -# unpacked will be owned by you and have default permissions.) -# -# This archive contains: -# plot/plot.red - -echo x - plot/plot.red -if [ -f plot/plot.red ] - then - mv plot/plot.red \ - plot/plot.red.old - else - echo "*** New file plot/plot.red created" -fi -cat > "plot/plot.red" \ - << '//E*O*F plot/plot.red//' -module plot; % device and driver independent plot services. - -% Author: Herbert Melenk. - -% Minor corrections by Winfried Neun (October 1995) - -create!-package('(plot),nil); - -global '( - - plotdriver!* % modulename of the actual driver. - - plotmax!* % maximal floating point number which - % gnuplot supports on the machine - % (mostly IEEE double or single precision). - - plotmin!* % lower bound (=1/plotmax!*) - - variation!* % defintion of y-bigstep for smooth - - plotoptions!* % list for collecting the options. - -); - -fluid '( - - plotderiv!* % derivative for 2d plot - -); - -!#if(or (errorp (errorset '!*writingfaslfile nil nil)) - (not !*writingfaslfile) - (errorp (errorset '(load fcomp) nil nil))) - prin2t "no support for fast float!"; - eval'(dm fdeclare (x) nil); - eval'(dm thefloat (x)(cadr x)); -!#endif - -endmodule; - -module plotsynt; % Support for the syntax of the plot command. - -% Author: Herbert Melenk. - -% Create .. as the infix operator if not yet done. - -!*msg := nil; % prevent message ".. redefined" during load - -newtok '( (!. !.) !*interval!*); - -if not(gettype '!*interval!* = 'operator) then -<< - precedence .., or; - algebraic operator ..; - put('!*interval!*,'PRTCH,'! !.!.! ); ->>; - -mkop 'point; - -!*msg := t; - -fluid '(plot!-points!* plot!-refine!* plot!-contour!*); - -global '(plot_xrange plot_yrange plot_zrange); -share plot_xmesh,plot_ymesh,plot_xrange,plot_yrange,plot_zrange; - -fluid '(plotprecision!*); - -plotprecision!* := 0.9995; - -fluid '(!*show_grid test_plot); - -switch show_grid; -switch test_plot; % for test printouts - -if null plotmax!* then -<< - load!-package 'arith; - if not !!plumax then roundconstants(); - plotmax!* := !!plumax; % IEEE double precision ->>; - -plotmin!*:= 1.0/plotmax!*; - - -fluid '(plotranges!* plotfunctions!* plotstyle!* !*plotoverflow - !*roundbf); - -put('plot,'psopfn,'ploteval); - -% I need the following definition only at compile time. -macro procedure plotdriver u; - {'apply,{'get,'plotdriver!*,mkquote cadr u},'list.cddr u}; - -symbolic procedure ploteval u; - begin scalar m,!*exp; - if null plotdriver!* then - rederr "no active device driver for PLOT"; - m:=plotrounded(nil); - plot!-points!* := {20}; - plot!-refine!* := 8; - !*plotoverflow := nil; - plotranges!* := plotfunctions!* := nil; - plotstyle!* := 'lines; - plotdriver(init); - for each option in u do ploteval1 plot!-reval option; - errorset('(ploteval2),t,nil); - plotrounded(m); - end; - -symbolic procedure plot!-reval u; - % Protected call reval: simplify u, but don't call any - % algebraic procedure. - begin scalar w; - w:={nil}; - u:=plot!-reval1(u,w); - return car w and u or reval u; - end; - -symbolic procedure plot!-reval1(u,w); - if idp u then reval u else - if atom u or eqcar(u,'!:dn!:) or get(car u,'dname) then u else %WN - if eq(car u,'!*sq) then plot!-reval1 (reval u,w) else %WN - <> else - << if flagp(car u,'opfn) then car w:=t; - car u . for each q in cdr u collect plot!-reval1(q,w) >> >>; - -symbolic procedure ploteval1 option; - begin scalar x,do; - do := get(plotdriver!*,'do); - if pairp option and (x:=get(car option,do)) - then apply(x,list option) else - if pairp option and (x:=get(car option,'plot!-do)) - then apply(x,list option) else - if eqcar(option,'equal) and (x:=get(cadr option,do)) - then apply(x,list caddr option) else - if eqcar(option,'equal) and (x:=get(cadr option,'plot!-do)) - then apply(x,list caddr option) - else ploteval0 option; - end; - -symbolic procedure ploteval0 option; - begin scalar l,r,opt,w; - opt:=get(plotdriver!*,'option); - if flagp(option,opt) then - <>; - if eqcar(option,'list) then - <