MathExprImpl.mesa
Carl Waldspurger, August 14, 1986 6:35:22 pm PDT
Mathematics Expressions Module
DIRECTORY
MathRules USING [AtomBoxProc, AtomPaintProc, CompoundBoxProc, CompositionProc, AtomToRopeProc, Size],
MathBox,
MathTypes USING [Style, AtomValue, AtomValueRep, FormatClass],
MathDB USING [LookupAtomClass, LookupCompoundClass, notFound],
ImagerFont USING [Extents],
Vector USING [VEC],
Rope USING [ROPE],
MathExpr;
MathExprImpl: CEDAR PROGRAM
IMPORTS MathDB
EXPORTS MathExpr ~
BEGIN
Abbreviations from Imported Interfaces
ROPE: TYPE ~ Rope.ROPE;
VEC: TYPE ~ Vector.VEC;
BOX: TYPE ~ MathBox.BOX;
Style: TYPE ~ MathTypes.Style;
AtomValue: TYPE ~ MathTypes.AtomValue;
AtomValueRep: TYPE ~ MathTypes.AtomValueRep;
AtomBoxProc: TYPE ~ MathRules.AtomBoxProc;
AtomPaintProc: TYPE ~ MathRules.AtomPaintProc;
CompoundBoxProc: TYPE ~ MathRules.CompoundBoxProc;
CompositionProc: TYPE ~ MathRules.CompositionProc;
AtomToRopeProc: TYPE ~ MathRules.AtomToRopeProc;
Size: TYPE ~ MathRules.Size;
TaggedMathExpr: TYPE ~ MathExpr.TaggedMathExpr;
ExprFlavors: TYPE ~ MathExpr.ExprFlavors;
AtomClass: TYPE ~ MathExpr.AtomClass;
AtomClassRep: TYPE ~ MathExpr.AtomClassRep;
AtomFlavor: TYPE ~ MathExpr.AtomFlavor;
CompoundClass: TYPE ~ MathExpr.CompoundClass;
CompoundClassRep: TYPE ~ MathExpr.CompoundClassRep;
FormatClass: TYPE ~ MathTypes.FormatClass;
Argument: TYPE ~ MathExpr.Argument;
Symbol: TYPE ~ MathExpr.Symbol;
MatrixFlavor: TYPE ~ MathExpr.MatrixFlavor;
Private Type Rep
A Math Expression is either an atomic expression or a compound expression
MathExprRep: PUBLIC TYPE ~
RECORD [
SELECT type:* FROM
atom => [
class: AtomClass, -- atomic data type
value: AtomValue -- atomic value, e.g. integer as rope
],
compound => [
class: CompoundClass, -- compound operation class, e.g. summation or product
subExprs: LIST OF TaggedMathExpr ← NIL -- class operation arguments
],
matrix => [
flavor: MatrixFlavor, -- type of matrix op, e.g. determinant or matrix, etc.
nRows, nCols: INT, -- matrix size as rows x cols
elements: LIST OF TaggedMathExpr ← NIL, -- matrix elements
openSym, closeSym: EXPR, -- left and right brackets or parentheses
space: EXPR -- space to use between elements
],
ENDCASE
];
AtomExprRep: PUBLIC TYPE ~ atom MathExprRep;
CompoundExprRep: PUBLIC TYPE ~ compound MathExprRep;
MatrixExprRep: PUBLIC TYPE ~ matrix MathExprRep;
privately (n.b. not public) redefine opaque types in terms of concrete rep
EXPR: TYPE ~ REF MathExprRep;
AtomEXPR: TYPE ~ REF AtomExprRep;
CompoundEXPR: TYPE ~ REF CompoundExprRep;
MatrixEXPR: TYPE ~ REF MatrixExprRep;
Constructors
Primitive Constructors
MakeArgument: PUBLIC PROC[name: ATOM, aliases: LIST OF ATOM, size: Size] RETURNS[Argument] ~ {
effects: constructs and returns an argument object
RETURN[[name: name, aliases: aliases, size: size]];
};
MakeSymbol: PUBLIC PROC[name: ATOM, aliases: LIST OF ATOM, size: Size, value: EXPR] RETURNS[Symbol] ~ {
effects: constructs and returns a symbol object
RETURN[[name: name, aliases: aliases, size: size, value: value]];
};
MakeAtomClass: PUBLIC PROC[name: ATOM, formatClass: FormatClass, flavor: AtomFlavor, style: Style, boxRule: AtomBoxProc, paintRule: AtomPaintProc, cvtRope: AtomToRopeProc] RETURNS[AtomClass] ~ {
effects: constructs and returns a new atom class object
RETURN[NEW[AtomClassRep ← [name: name, formatClass: formatClass, flavor: flavor, style: style, boxRule: boxRule, paintRule: paintRule, cvtRope: cvtRope]]];
};
MakeCompoundClass: PUBLIC PROC[name: ATOM, formatClass: FormatClass, description: ROPE, args: LIST OF Argument, syms: LIST OF Symbol, boxRule: CompoundBoxProc, compBox: CompositionProc, cvtAS: ROPENIL] RETURNS[CompoundClass] ~ {
effects: constructs and returns a new compound class object
RETURN[NEW[CompoundClassRep ← [name: name, formatClass: formatClass, description: description, arguments: args, symbols: syms, boxRule: boxRule, compBox: compBox, cvtAS: cvtAS]]];
};
MakeAtomChar: PUBLIC PROC[c: CHAR] RETURNS[AtomValue] ~ {
effects: Constructs and returns a new atom value of type char
RETURN[NEW[char AtomValueRep ← [char[char: [0, ORD[c]]]]]];
};
MakeAtomRope: PUBLIC PROC[r: ROPE] RETURNS[AtomValue] ~ {
effects: Constructs and returns a new atom value of type rope
RETURN[NEW[rope AtomValueRep ← [rope[rope: r]]]];
};
MakeAtomBox: PUBLIC PROC[b: ImagerFont.Extents] RETURNS[AtomValue] ~ {
effects: Constructs and returns a new atom value of type box.
RETURN[NEW[box AtomValueRep ← [box[box: b]]]];
};
MakeAtomOther: PUBLIC PROC[other: REF ANY] RETURNS[AtomValue] ~ {
effects: COnstructs and returns a new atom value of type other
RETURN[NEW[other AtomValueRep ← [other[other: other]]]];
};
Math Expression Constructors
MakeAtomicExpr: PUBLIC PROC[class: ATOM, value: AtomValue] RETURNS[EXPR] ~ {
effects: constructs and returns a new atomic expression object
SIGNALS badAtomClass if class is unrecognized
lookup class in database, complain if not found
atomClass: AtomClass ← MathDB.LookupAtomClass[class ! MathDB.notFound => {ERROR badAtomClass}];
RETURN[NEW[atom MathExprRep ← [atom[class: atomClass, value: value]]]];
};
MakeCompoundExpr: PUBLIC PROC[class: ATOM, args: LIST OF TaggedMathExpr] RETURNS[EXPR] ~ {
effects: constructs and returns a new compound expression object
SIGNALS badCompoundClass if class is unrecognized
SIGNALS badExprs if exprs has the wrong number or wrong type of elements
local declarations
validExprs: LIST OF TaggedMathExpr ← NIL;
lookup class in database, complain if not found
compClass: CompoundClass ← MathDB.LookupCompoundClass[class ! MathDB.notFound => {ERROR badCompoundClass}];
check validity of subexpressions (by tagged id)
grab each argument and symbol as needed and stuff into validExprs (cons up list)
FOR l: LIST OF Argument ← compClass.arguments, l.rest UNTIL l = NIL DO
validExprs ← CONS[GetTaggedExpr[l.first.name, args ! exprNotFound => {ERROR badExprs[l.first.name]}], validExprs];
ENDLOOP;
FOR l: LIST OF Symbol ← compClass.symbols, l.rest UNTIL l = NIL DO
validExprs ← CONS[[l.first.name, l.first.value], validExprs];
ENDLOOP;
finally construct and return verified EXPR object
RETURN[NEW[compound MathExprRep ← [compound[class: compClass, subExprs: validExprs]]]];
};
MakeMatrixExpr: PUBLIC PROC[flavor: MatrixFlavor, nRows, nCols: NAT, elements: LIST OF TaggedMathExpr, openSym, closeSym, space: EXPR] RETURNS[EXPR] ~ {
effects: constructs and returns a new matrix expression object
SIGNALS badMatrixSize if nRows or nCols is invalid
SIGNALS badMatrix if rows has the wrong number or wrong type of elements
no error checking for now... (development)
RETURN[NEW[matrix MathExprRep ← [matrix[flavor: flavor, nRows: nRows, nCols: nCols, elements: elements, openSym: openSym, closeSym: closeSym, space: space]]]];
};
Selectors
GetType: PUBLIC PROC[expr: EXPR] RETURNS[ExprFlavors] ~ {
effect: Returns atom if expr is an AtomEXPR,
Returns compound if expr is a CompoundEXPR
WITH expr SELECT FROM
a: AtomEXPR => RETURN[atom];
c: CompoundEXPR => RETURN[compound];
m: MatrixEXPR => RETURN[matrix];
ENDCASE => ERROR;
};
GetAtomClass: PUBLIC PROC[expr: AtomEXPR] RETURNS[AtomClass] ~ {
effects: Returns the class of atomic expression expr.
RETURN[expr.class];
};
GetAtomExpr: PUBLIC PROC[expr: EXPR] RETURNS[AtomEXPR] ~ {
effects: If expr.Type = atom, returns atomic expression.
Otherwise SIGNALS wrongExprType
WITH expr SELECT FROM
a: AtomEXPR => RETURN[a];
c: CompoundEXPR => ERROR wrongExprType;
m: MatrixEXPR => ERROR wrongExprType;
ENDCASE => ERROR;
};
GetValue: PUBLIC PROC[expr: AtomEXPR] RETURNS[AtomValue] ~ {
effects: Returns the value of atomic expression expr.
RETURN[expr.value];
};
GetCompoundClass: PUBLIC PROC[expr: CompoundEXPR] RETURNS[CompoundClass] ~ {
effects: Returns the class of compound expression expr.
RETURN[expr.class];
};
GetCompoundExpr: PUBLIC PROC[expr: EXPR] RETURNS[CompoundEXPR] ~ {
effects: If expr.Type[] = compound, returns compound expression.
Otherwise SIGNALS wrongExprType
WITH expr SELECT FROM
a: AtomEXPR => ERROR wrongExprType;
c: CompoundEXPR => RETURN[c];
m: MatrixEXPR => ERROR wrongExprType;
ENDCASE => ERROR;
};
GetMatrixExpr: PUBLIC PROC[expr: EXPR] RETURNS[MatrixEXPR] ~ {
effects: IF expr.Type[] = matrix, returns matrix expression
Otherwise SIGNALS wrongExprType
WITH expr SELECT FROM
a: AtomEXPR => ERROR wrongExprType;
c: CompoundEXPR => ERROR wrongExprType;
m: MatrixEXPR => RETURN[m];
ENDCASE => ERROR;
};
GetSubExprs: PUBLIC PROC[expr: CompoundEXPR] RETURNS[LIST OF TaggedMathExpr] ~ {
effects: Returns the subexpressions for compound expression expr.
RETURN[expr.subExprs];
};
GetMatrixElements: PUBLIC PROC[expr: MatrixEXPR]
RETURNS[LIST OF TaggedMathExpr] ~ {
effects: Returns the rows of expression for matrix expression expr.
RETURN[expr.elements];
};
GetMatrixSize: PUBLIC PROC[expr: MatrixEXPR] RETURNS[NAT, NAT] ~ {
effects: Returns the size (dimensions) of expr as [nRows, nCols]
RETURN[expr.nRows, expr.nCols];
};
GetMatrixFlavor: PUBLIC PROC[expr: MatrixEXPR] RETURNS[MatrixFlavor] ~ {
effects: Returns the flavor of expr.
RETURN[expr.flavor];
};
GetMatrixOpenSym: PUBLIC PROC[expr: MatrixEXPR] RETURNS[EXPR] ~ {
effects: Returns open symbol expression of expr
RETURN[expr.openSym];
};
GetMatrixCloseSym: PUBLIC PROC[expr: MatrixEXPR] RETURNS[EXPR] ~ {
effects: Returns close symbol expression of expr
RETURN[expr.closeSym];
};
GetMatrixSpace: PUBLIC PROC[expr: MatrixEXPR] RETURNS[EXPR] ~ {
effects: Returns space expression of expr
RETURN[expr.space];
};
List Selectors
GetTaggedExpr: PUBLIC PROC[tag: ATOM, exprs: LIST OF TaggedMathExpr] RETURNS[TaggedMathExpr] ~ {
effects: Returns the TaggedMathExpr in exprs associated with tag.
SIGNALS exprNotFound if no association exists.
cdr down list looking for tag
FOR l: LIST OF TaggedMathExpr ← exprs, l.rest UNTIL l = NIL DO
IF l.first.id = tag THEN RETURN[l.first];
ENDLOOP;
not found, so complain
ERROR exprNotFound;
};
Signals & Errors
badAtomClass: PUBLIC ERROR = CODE;
badCompoundClass: PUBLIC ERROR = CODE;
badExprs: PUBLIC ERROR[reason: ATOM] = CODE;
exprNotFound: PUBLIC ERROR = CODE;
wrongExprType: PUBLIC ERROR = CODE;
invalidReplacement: PUBLIC ERROR = CODE;
END.