");
/*
blanks ( ) [ ] , are seperators (not allowed in names of symbols)
Arguments may be separated by spaces or single commas.
Parenthesis must be balanced.
Symbols are either terminal (arity==0) or prefix or infix (unary infix defaults to postfix)
expr ::= terminal | prefix expr1 ... exprN | prefix(expr1, ... , exprN) |
expr infix | expr1 infix exprN | (expr) | [expr]
Expressions are read from left to right, choosing the longest initial substring
that matches the name of a symbol. Symbol priority is taken into account.
*/
function str2expr(str,pri) { //builds expr and returns [expr,substring]
// If returned substring starts with "Error: ..." it contains information about a parsing error
var arg=[];
var token="";
var symbol;
var nextsymbol;
var expr;
var estr;
var more;
str=removeCharsAndBlanks(str,0);
symbol=getSymbol(str); //either a symbol or a bracket or empty
//document.writeln("@@",str,"#",symbol," "+temp[1]+" ");
else if (temp[1].slice(0,5)!="") {
alert("Parse Leftover: >>>"+temp[1]+"<<<");
} //arities of expressions are not checked
return temp[0];
}
currentDefs = [];
newSymbol("Defn","");
newSymbol("Axiom","");
mathdelimit="`";
function p(str) {
var arr=str.split(mathdelimit); // string to delimit math expressions
var expr=false;
document.writeln("
");
if (symbol==null||symbol==rightBracket)
return [null,"Error, '(' or symbol expected: "+str];
str=removeCharsAndBlanks(str,symbol.name.length);
if (symbol==leftBracket) { //read (expr)
estr=str2expr(str,0);expr=estr[0];str=estr[1];
if (str.slice(0,5)=="Error") return [null,str];
expr.priority = maxPriority;
symbol=getSymbol(str);
if (symbol==null) return [null,"Error, unknown symbol: "+str];
str=removeCharsAndBlanks(str,symbol.name.length);
if (symbol!=rightBracket) return [null,"Error, ')' expected : "+str];
} else if (symbol.arity==0 || symbol.infix && symbol!=minus) {//read terminal
expr=new Expr(symbol,[], maxPriority);
} else { //read prefix expr1 ... exprN or prefix(...)
nextsymbol = getSymbol(str);
var commas=false;
if (nextsymbol==leftBracket && symbol.paren) {
str = removeCharsAndBlanks(str,nextsymbol.name.length);
nextsymbol = getSymbol(str);
commas=true;
}
more = nextsymbol!=null &&
(commas || !nextsymbol.infix && !nextsymbol.endSymb) && //nextsymbol!=norm) &&
nextsymbol!=rightBracket && nextsymbol!=comma;
while (str!="" && more && (symbol.endName==null||
symbol.endName!=str.slice(0,symbol.endName.length))) {
nextsymbol = getSymbol(str);
//document.write(symbol.name,nextsymbol.name,"@",str,"
");
if (nextsymbol==null) return [null,"Error, incorrect symbol: "+str];
if (commas)
estr=str2expr(str,-1);
else estr=str2expr(str,symbol.priority);
expr=estr[0];str=estr[1];
if (str.slice(0,5)=="Error") return [null,str];
add(arg,expr);
nextsymbol = getSymbol(str);
more = nextsymbol != null &&
(commas || !nextsymbol.infix && nextsymbol!=norm) &&
nextsymbol!=rightBracket;
if (commas)
if (str=="") return [null,"Error, ')' expected: "+str];
else if (str.charAt(0)==",") str=removeCharsAndBlanks(str,1);
else if (str.charAt(0)==")") {
more = false;
str=removeCharsAndBlanks(str,1);
}
}
expr=new Expr(symbol, arg, maxPriority);
if (symbol.endName!=null) {
//document.write(symbol.name,"#",str,"
");
if (symbol.endName!=str.slice(0,symbol.endName.length))
return [null,"Error, "+symbol.endName+" expected: "+str];
str=removeCharsAndBlanks(str,symbol.endName.length);
}
}
//parse right argument of infix operation
symbol = getSymbol(str);// infix op symb
var insert=null;
if (symbol==null || !symbol.infix || symbol.priority