WarpPI/core/src/main/java/it/cavallium/warppi/math/functions/Expression.java

627 lines
28 KiB
Java
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

package it.cavallium.warppi.math.functions;
import it.cavallium.warppi.gui.expression.blocks.Block;
import it.cavallium.warppi.gui.expression.blocks.BlockContainer;
import it.cavallium.warppi.gui.expression.blocks.BlockParenthesis;
import it.cavallium.warppi.math.Function;
import it.cavallium.warppi.math.FunctionSingle;
import it.cavallium.warppi.math.MathContext;
import it.cavallium.warppi.math.functions.trigonometry.ArcCosine;
import it.cavallium.warppi.math.functions.trigonometry.ArcSine;
import it.cavallium.warppi.math.functions.trigonometry.ArcTangent;
import it.cavallium.warppi.math.functions.trigonometry.Cosine;
import it.cavallium.warppi.math.functions.trigonometry.Sine;
import it.cavallium.warppi.math.functions.trigonometry.Tangent;
import it.cavallium.warppi.util.Error;
import it.unimi.dsi.fastutil.objects.ObjectArrayList;
public class Expression extends FunctionSingle {
public Expression(final MathContext root) {
super(root);
}
public Expression(final MathContext root, final Function value) {
super(root, value);
}
private final boolean initialParenthesis = false;
@Deprecated
public Expression(final MathContext root, final String string) throws Error {
this(root, string, "", true);
}
@Deprecated
public Expression(final MathContext root, final String string, final String debugSpaces, final boolean initialParenthesis) throws Error {
super(root);
/*
super(root);
this.initialParenthesis = initialParenthesis;
boolean isNumber = false;
// Determine if the expression is already a number:
// Determina se l'espressione è già un numero:
try {
new Number(root, string);
isNumber = true;
} catch (final NumberFormatException ex) {
isNumber = false;
}
String processExpression = string;
Utils.debug.println(debugSpaces + "•Analyzing expression:" + processExpression);
isNumber = false; //TODO: rimuovere isNumber, alcune semplificazione come la divisione per zero altrimenti verrebbero saltate.
if (isNumber) {
// If the expression is already a number:
// Se l'espressione è già un numero:
final Number t = new Number(root, string);
parameter = t;
Utils.debug.println(debugSpaces + "•Result:" + t.toString());
} else {
// Else prepare the expression:
// Altrimenti prepara l'espressione:
debugSpaces += " ";
// IF the expression is not a number:
// Se l'espressione non è già un numero:
// Check if there are more than one equal symbol (=)
// Controlla se ci sono più di un uguale (=)
int equationsFound = 0;
int systemsFound = 0;
for (final char c : processExpression.toCharArray()) {
if (("" + c).equals(MathematicalSymbols.EQUATION)) {
equationsFound += 1;
}
if (("" + c).equals(MathematicalSymbols.SYSTEM)) {
equationsFound += 1;
}
}
if (equationsFound == 1 && systemsFound == 0) {
processExpression = MathematicalSymbols.SYSTEM + processExpression;
systemsFound += 1;
}
if (equationsFound != systemsFound) {
throw new Error(Errors.SYNTAX_ERROR);
}
//Solve the exceeding symbols ++ and --
// Correggi i segni ++ e -- in eccesso
Pattern pattern = Pattern.compile("\\+\\++?|\\-\\-+?");
Matcher matcher = pattern.matcher(processExpression);
boolean symbolsChanged = false;
while (matcher.find()) {
symbolsChanged = true;
final String correzione = "+";
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
matcher = pattern.matcher(processExpression);
}
// Correct the exceeding symbols +- and -+
// Correggi i segni +- e -+ in eccesso
pattern = Pattern.compile("\\+\\-|\\-\\+");
matcher = pattern.matcher(processExpression);
while (matcher.find()) {
symbolsChanged = true;
final String correzione = "-";
processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
matcher = pattern.matcher(processExpression);
}
// Rimuovi i segni appena dopo le parentesi
if (processExpression.contains("(+")) {
symbolsChanged = true;
processExpression = processExpression.replace("(+", "(");
}
// // Cambia i segni appena prima le parentesi
// if (processExpression.contains("-(")) {
// symbolsChanged = true;
// processExpression = processExpression.replace("-(", "-1*(");
// }
// Rimuovi i segni appena dopo l'inizio
if (processExpression.startsWith("+")) {
symbolsChanged = true;
processExpression = processExpression.substring(1, processExpression.length());
}
// Rimuovi i + in eccesso
pattern = Pattern.compile("[" + ArrayToRegex(Utils.add(concat(MathematicalSymbols.signums(true), MathematicalSymbols.functions), '(')) + "]\\+[^" + ArrayToRegex(concat(concat(MathematicalSymbols.signums(true), MathematicalSymbols.functions), new char[] { '(', ')' })) + "]+?[" + ArrayToRegex(concat(MathematicalSymbols.signums(true), MathematicalSymbols.functions)) + "]|[" + ArrayToRegex(concat(MathematicalSymbols.signums(true), MathematicalSymbols.functions)) + "]+?\\+[^" + ArrayToRegex(concat(concat(MathematicalSymbols.signums(true), MathematicalSymbols.functions), new char[] { '(', ')' })) + "]");
matcher = pattern.matcher(processExpression);
symbolsChanged = false;
while (matcher.find()) {
symbolsChanged = true;
final String correzione = matcher.group(0).replaceFirst(Matcher.quoteReplacement("+"), "");
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
matcher = pattern.matcher(processExpression);
}
// Correggi i segni - in
processExpression = processExpression.replace('-', MathematicalSymbols.SUBTRACTION);
// Correggi i segni dopo di espressioni o funzioni SN in -
pattern = Pattern.compile("[" + Utils.ArrayToRegex(concat(concat(MathematicalSymbols.functions, new char[] { MathematicalSymbols.PARENTHESIS_OPEN }), MathematicalSymbols.signums(true))) + "]" + MathematicalSymbols.SUBTRACTION);
matcher = pattern.matcher(processExpression);
while (matcher.find()) {
symbolsChanged = true;
final char correzione = MathematicalSymbols.MINUS;
processExpression = processExpression.substring(0, matcher.start(0) + 1) + correzione + processExpression.substring(matcher.start(0) + 2, processExpression.length());
matcher = pattern.matcher(processExpression);
}
// Cambia il segno iniziale in -
if (processExpression.startsWith("")) {
symbolsChanged = true;
processExpression = "-" + processExpression.substring(1, processExpression.length());
}
if (symbolsChanged) {
Utils.debug.println(debugSpaces + "•Resolved signs:" + processExpression);
}
// // Aggiungi le parentesi implicite per le potenze con una incognita
// pattern = Pattern.compile("(?<!(?:\\(|^))(["+Utils.ArrayToRegex(MathematicalSymbols.variables())+"]+"+MathematicalSymbols.POWER+"[^" + Utils.ArrayToRegex(Utils.add(concat(MathematicalSymbols.functionsNSN(), concat(MathematicalSymbols.signums(true), MathematicalSymbols.genericSyntax())), ")")) + "])(?!\\))");
// matcher = pattern.matcher(processExpression);
// symbolsChanged = false;
// while (matcher.find()) {
// symbolsChanged = true;
// String correzione = matcher.group().replace(MathematicalSymbols.POWER, "⑴");
// processExpression = processExpression.substring(0, matcher.start(0)) + correzione + processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
// matcher = pattern.matcher(processExpression);
// }
//
// processExpression = processExpression.replace("⑴", MathematicalSymbols.POWER);
// Aggiungi i segni * accanto alle parentesi
pattern = Pattern.compile("\\([^\\(]+?\\)");
matcher = pattern.matcher(processExpression);
while (matcher.find()) {
symbolsChanged = true;
// sistema i segni * impliciti prima e dopo l'espressione.
String beforeexp = processExpression.substring(0, matcher.start(0));
final String newexp = matcher.group(0).substring(1, matcher.group(0).length() - 1);
String afterexp = processExpression.substring(matcher.start(0) + matcher.group(0).length(), processExpression.length());
if (Pattern.compile("[^\\-" + Utils.ArrayToRegex(Utils.add(concat(MathematicalSymbols.functions, concat(MathematicalSymbols.signums(true), MathematicalSymbols.genericSyntax)), '(')) + "]$").matcher(beforeexp).find()) {
// Se la stringa precedente finisce con un numero
beforeexp += MathematicalSymbols.MULTIPLICATION;
}
if (Pattern.compile("^[^\\-" + Utils.ArrayToRegex(Utils.add(concat(MathematicalSymbols.functions, concat(MathematicalSymbols.signums(true), MathematicalSymbols.genericSyntax)), ')')) + "]").matcher(afterexp).find()) {
// Se la stringa successiva inizia con un numero
afterexp = MathematicalSymbols.MULTIPLICATION + afterexp;
}
processExpression = beforeexp + "⑴" + newexp + "⑵" + afterexp;
matcher = pattern.matcher(processExpression);
}
processExpression = processExpression.replace("⑴", "(").replace("⑵", ")");
if (symbolsChanged) {
Utils.debug.println(debugSpaces + "•Added implicit multiplications:" + processExpression);
}
Utils.debug.println(debugSpaces + "•Subdivision in classes:");
debugSpaces += " ";
// Convert the expression to a list of objects
Expression imputRawParenthesis = new Expression(root);
imputRawParenthesis = (Expression) imputRawParenthesis.setParameter(null);
String tmp = "";
final char[] functions = concat(concat(concat(concat(MathematicalSymbols.functions, MathematicalSymbols.parentheses), MathematicalSymbols.signums(true)), MathematicalSymbols.variables), MathematicalSymbols.genericSyntax);
for (int i = 0; i < processExpression.length(); i++) {
// Per ogni carattere cerca se è un numero o una funzione:
final char charI = processExpression.charAt(i);
if (Utils.isInArray(charI, functions)) {
// Finds the type of function fron the following list
// Cerca il tipo di funzione tra le esistenti
Function f = null;
switch (charI) {
case MathematicalSymbols.SUM:
f = new Sum(root, null, null);
break;
case MathematicalSymbols.SUM_SUBTRACTION:
f = new SumSubtraction(root, null, null);
break;
case MathematicalSymbols.SUBTRACTION:
f = new Subtraction(root, null, null);
break;
case MathematicalSymbols.MINUS:
f = new Negative(root, null);
break;
case MathematicalSymbols.MULTIPLICATION:
f = new Multiplication(root, null, null);
break;
case MathematicalSymbols.DIVISION:
f = new Division(root, null, null);
break;
case MathematicalSymbols.NTH_ROOT:
f = new Root(root, null, null);
break;
case MathematicalSymbols.SQUARE_ROOT:
f = new RootSquare(root, null);
break;
case MathematicalSymbols.POWER:
f = new Power(root, null, null);
break;
case MathematicalSymbols.SINE:
f = new Sine(root, null);
break;
case MathematicalSymbols.COSINE:
f = new Cosine(root, null);
break;
case MathematicalSymbols.TANGENT:
f = new Tangent(root, null);
break;
case MathematicalSymbols.ARC_SINE:
f = new ArcSine(root, null);
break;
case MathematicalSymbols.ARC_COSINE:
f = new ArcCosine(root, null);
break;
case MathematicalSymbols.ARC_TANGENT:
f = new ArcTangent(root, null);
break;
case MathematicalSymbols.PARENTHESIS_OPEN:
// Find the last closed parenthesis
// cerca l'ultima parentesi chiusa
int startIndex = i;
int endIndex = -1;
int jumps = -1;
for (int i2 = startIndex; i2 < processExpression.length(); i2++) {
if ((processExpression.charAt(i2) + "").equals(MathematicalSymbols.PARENTHESIS_CLOSE)) {
if (jumps == 0) {
endIndex = i2;
break;
} else if (jumps > 0) {
jumps -= 1;
} else if (jumps < 0) {
throw new Error(Errors.UNBALANCED_STACK);
}
} else if ((processExpression.charAt(i2) + "").equals(MathematicalSymbols.PARENTHESIS_OPEN)) {
jumps += 1;
}
}
if (endIndex == -1 || endIndex < startIndex) {
throw new Error(Errors.UNBALANCED_STACK);
}
startIndex += 1;
i = startIndex;
String tmpExpr = "";
while (i < endIndex) {
tmpExpr += processExpression.charAt(i);
i++;
}
f = new Expression(root, tmpExpr, debugSpaces, false);
break;
default:
if (Utils.isInArray(charI, MathematicalSymbols.variables)) {
f = new Variable(root, charI, Variable.V_TYPE.UNKNOWN);
} else {
if (charI == '(' || charI == ')') {
throw new Error(Errors.UNBALANCED_STACK);
} else {
System.err.println("Unexpected character while parsing expression: " + charI);
throw new Error(Errors.SYNTAX_ERROR);
}
// throw new java.lang.RuntimeException("Il carattere " + charI + " non è tra le funzioni designate!\nAggiungerlo ad esse o rimuovere il carattere dall'espressione!");
}
}
if (f instanceof Expression) {
tmp = "";
} else if (f instanceof Variable) {
if (imputRawParenthesis.getParametersLength() == 0) {
if (tmp.length() > 0) {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Number(root, tmp));
Utils.debug.println(debugSpaces + "•Added number to expression:" + tmp);
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Multiplication(root, null, null));
Utils.debug.println(debugSpaces + "•Added multiplication to expression:" + new Multiplication(root, null, null).getClass().getSimpleName());
}
} else {
final Function precedentFunction = imputRawParenthesis.getParameter(imputRawParenthesis.getParametersLength() - 1);
if (tmp.length() > 0) {
if (precedentFunction instanceof Number || precedentFunction instanceof Variable) {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Multiplication(root, null, null));
Utils.debug.println(debugSpaces + "•Added multiplication to expression:" + new Multiplication(root, null, null).getClass().getSimpleName());
}
if (tmp.equals("-")) {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Subtraction(root, null, null));
} else {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Number(root, tmp));
Utils.debug.println(debugSpaces + "•Added number to expression:" + tmp);
}
}
if (tmp.length() > 0 || (precedentFunction instanceof Number || precedentFunction instanceof Variable)) {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Multiplication(root, null, null));
Utils.debug.println(debugSpaces + "•Added multiplication to expression:" + new Multiplication(root, null, null).getClass().getSimpleName());
}
}
} else {
if (tmp.length() != 0) {
if (tmp.equals("-")) {
if (tmp.equals("-")) {
tmp = "-1";
}
}
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Number(root, tmp));
Utils.debug.println(debugSpaces + "•Added number to expression:" + tmp);
}
}
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(f);
Utils.debug.println(debugSpaces + "•Added variable to expression:" + f.getClass().getSimpleName() + (f instanceof Number ? " (number)" : " (variable)"));
tmp = "";
} else {
try {
if (charI != '-' && charI != '.') {
new BigDecimal(tmp + charI);
}
// Se il carattere è un numero intero, un segno
// negativo, o un punto
tmp += charI;
} catch (final Exception exc) {
throw new java.lang.RuntimeException("Il carattere " + tmp + charI + " non è nè un numero nè un espressione presente nella lista completa!\nAggiungerlo ad essa o rimuovere il carattere dall'espressione!");
}
}
}
if (tmp.length() > 0) {
Utils.debug.println(debugSpaces + "•Added variable to expression:" + tmp);
try {
imputRawParenthesis = (Expression) imputRawParenthesis.appendParameter(new Number(root, tmp));
} catch (final NumberFormatException ex) {
throw new Error(Errors.SYNTAX_ERROR);
}
tmp = "";
}
int dsl = debugSpaces.length();
debugSpaces = "";
for (int i = 0; i < dsl - 2; i++) {
debugSpaces += " ";
}
Utils.debug.println(debugSpaces + "•Finished the subdivision in classes.");
// Fine suddivisione di insieme
Utils.debug.println(debugSpaces + "•Removing useless parentheses");
for (int i = 0; i < imputRawParenthesis.getParametersLength(); i++) {
if (imputRawParenthesis.getParameter(i) instanceof Expression) {
final Expression par = (Expression) imputRawParenthesis.getParameter(i);
if (par.getParametersLength() == 1) {
final Function subFunz = par.getParameter(0);
if (subFunz instanceof Expression || subFunz instanceof Number || subFunz instanceof Variable) {
imputRawParenthesis = (Expression) imputRawParenthesis.setParameter(i, subFunz);
Utils.debug.println(debugSpaces + " •Useless parentheses removed");
}
}
}
}
// Inizia l'affinazione dell'espressione
Utils.debug.println(debugSpaces + "•Pushing classes...");
final Function[] oldFunctionsArray = imputRawParenthesis.getParameters();
final ObjectArrayList<Function> oldFunctionsList = new ObjectArrayList<>();
for (int i = 0; i < oldFunctionsArray.length; i++) {
Function funzione = oldFunctionsArray[i];
if (funzione != null) {
//Affinazione
if (funzione instanceof Root) {
if ((i - 1) >= 0 && oldFunctionsArray[i - 1] instanceof Number && ((Number) oldFunctionsArray[i - 1]).getTerm().compareTo(new BigDecimal(2)) == 0) {
oldFunctionsArray[i] = null;
oldFunctionsArray[i - 1] = null;
oldFunctionsList.remove(oldFunctionsList.size() - 1);
i -= 1;
funzione = new RootSquare(root, null);
}
}
//Aggiunta della funzione alla lista grezza
oldFunctionsList.add(funzione);
}
}
if (oldFunctionsList.size() > 1) {
Utils.debug.println(debugSpaces + " •Correcting classes:");
int before = 0;
String step = "SN Functions";
int n = 0;
do {
before = oldFunctionsList.size();
int i = 0;
boolean change = false;
if (Utils.areThereOnlyEmptySNFunctions(oldFunctionsList)) {
step = "SN Functions"; // SECONDA FASE
} else if (Utils.areThereOnlyEmptyNSNFunctions(oldFunctionsList)) {
step = "NSN Functions"; // TERZA FASE
} else if (Utils.areThereEmptyMultiplications(oldFunctionsList)) {
step = "multiplications"; // QUARTA FASE
} else if (Utils.areThereEmptySums(oldFunctionsList)) {
step = "sums"; // QUINTA FASE
} else {
// fase = "errore";
System.out.println("WARN: ---> POSSIBILE ERRORE????? <---");// BOH
// throw new Errore(Errori.SYNTAX_ERROR);
while (oldFunctionsList.size() > 1) {
oldFunctionsList.set(0, new Multiplication(root, oldFunctionsList.get(0), oldFunctionsList.remove(1)));
}
}
Utils.debug.println(debugSpaces + " •Phase: " + step);
while (i < oldFunctionsList.size() && change == false && oldFunctionsList.size() > 1) {
Function funzioneTMP = oldFunctionsList.get(i);
if (funzioneTMP instanceof FunctionOperator) {
if (step != "SN Functions") {
if ((step == "sums" && (funzioneTMP instanceof Sum || funzioneTMP instanceof SumSubtraction || funzioneTMP instanceof Subtraction) == true && ((funzioneTMP instanceof FunctionSingle && ((FunctionSingle) funzioneTMP).getParameter() == null) || (funzioneTMP instanceof FunctionOperator && ((FunctionOperator) funzioneTMP).getParameter1() == null && ((FunctionOperator) funzioneTMP).getParameter2() == null) || (!(funzioneTMP instanceof FunctionSingle) && !(funzioneTMP instanceof FunctionOperator)))) || (step.equals("multiplications") && ((funzioneTMP instanceof Multiplication) || (funzioneTMP instanceof Division)) && ((FunctionOperator) funzioneTMP).getParameter1() == null && ((FunctionOperator) funzioneTMP).getParameter2() == null) || (step == "NSN Functions" && (funzioneTMP instanceof Sum) == false && (funzioneTMP instanceof SumSubtraction) == false && (funzioneTMP instanceof Subtraction) == false && (funzioneTMP instanceof Multiplication) == false && (funzioneTMP instanceof Division) == false && ((funzioneTMP instanceof FunctionSingle && ((FunctionSingle) funzioneTMP).getParameter() == null) || (funzioneTMP instanceof FunctionOperator && ((FunctionOperator) funzioneTMP).getParameter1() == null && ((FunctionOperator) funzioneTMP).getParameter2() == null) || (!(funzioneTMP instanceof FunctionSingle) && !(funzioneTMP instanceof FunctionOperator))))) {
change = true;
if (i + 1 < oldFunctionsList.size() && i - 1 >= 0) {
funzioneTMP = ((FunctionOperator) funzioneTMP).setParameter1(oldFunctionsList.get(i - 1));
funzioneTMP = ((FunctionOperator) funzioneTMP).setParameter2(oldFunctionsList.get(i + 1));
oldFunctionsList.set(i, funzioneTMP);
// è importante togliere prima gli elementi
// in fondo e poi quelli davanti, perché gli
// indici scalano da destra a sinistra.
oldFunctionsList.remove(i + 1);
oldFunctionsList.remove(i - 1);
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getClass().getSimpleName());
try {
Utils.debug.println(debugSpaces + " " + "var1=" + ((FunctionOperator) funzioneTMP).getParameter1().toString());
} catch (final NullPointerException ex2) {}
try {
Utils.debug.println(debugSpaces + " " + "var2=" + ((FunctionOperator) funzioneTMP).getParameter2().toString());
} catch (final NullPointerException ex2) {}
try {
Utils.debug.println(debugSpaces + " " + "(result)=" + ((FunctionOperator) funzioneTMP).toString());
} catch (final NullPointerException ex2) {}
} else {
throw new Error(Errors.SYNTAX_ERROR);
}
}
}
} else if (funzioneTMP instanceof FunctionSingle) {
if ((step == "SN Functions" && ((FunctionSingle) funzioneTMP).getParameter() == null)) {
if (i + 1 < oldFunctionsList.size()) {
final Function nextFunc = oldFunctionsList.get(i + 1);
if (nextFunc instanceof FunctionSingle && ((FunctionSingle) nextFunc).getParameter() == null) {
} else {
change = true;
funzioneTMP = ((FunctionSingle) funzioneTMP).setParameter(nextFunc);
oldFunctionsList.set(i, funzioneTMP);
// è importante togliere prima gli elementi in
// fondo e poi quelli davanti, perché gli indici
// scalano da destra a sinistra.
oldFunctionsList.remove(i + 1);
Utils.debug.println(debugSpaces + " •Set variable to expression:" + funzioneTMP.getClass().getSimpleName());
final Function var = ((FunctionSingle) funzioneTMP).getParameter();
if (var == null) {
Utils.debug.println(debugSpaces + " " + "var=null");
} else {
Utils.debug.println(debugSpaces + " " + "var=" + var.toString());
}
}
} else {
throw new Error(Errors.SYNTAX_ERROR);
}
}
} else if (funzioneTMP instanceof Number || funzioneTMP instanceof Variable || funzioneTMP instanceof Expression) {
if (n < 300) {
// Utils.debug.println(debugSpaces+" •Set variable
// to number:"+funzioneTMP.calcola());
}
} else {
throw new java.lang.RuntimeException("Tipo sconosciuto");
}
i++;
n++;
}
} while (((oldFunctionsList.size() != before || step != "sums") && oldFunctionsList.size() > 1));
}
if (oldFunctionsList.isEmpty()) {
super.functions = new Function[] { new Number(root, 0) };
} else {
super.functions = oldFunctionsList.toArray(new Function[oldFunctionsList.size()]);
}
dsl = debugSpaces.length();
debugSpaces = "";
for (int i = 0; i < dsl - 2; i++) {
debugSpaces += " ";
}
Utils.debug.println(debugSpaces + "•Finished correcting classes.");
final String result = toString();
Utils.debug.println(debugSpaces + "•Result:" + result);
}
*/
}
public boolean parenthesisNeeded() {
boolean parenthesisneeded = true;
if (initialParenthesis) {
parenthesisneeded = false;
} else {
final Function f = getParameter(0);
if (f instanceof Number || f instanceof Variable || f instanceof Expression || f instanceof Division || f instanceof Joke || f instanceof Undefined || f instanceof Power || f instanceof Sine || f instanceof Cosine || f instanceof Tangent || f instanceof ArcSine || f instanceof ArcCosine || f instanceof ArcTangent || f instanceof RootSquare) {
parenthesisneeded = false;
}
if (f instanceof Multiplication) {
if (((Multiplication) f).getParameter1() instanceof Number) {
parenthesisneeded = !(((Multiplication) f).getParameter2() instanceof Variable);
} else if (((Multiplication) f).getParameter2() instanceof Number) {
parenthesisneeded = !(((Multiplication) f).getParameter1() instanceof Variable);
} else if (((Multiplication) f).getParameter1() instanceof Variable || ((Multiplication) f).getParameter2() instanceof Variable) {
parenthesisneeded = false;
}
}
}
return parenthesisneeded;
}
@Override
public ObjectArrayList<Block> toBlock(final MathContext context) throws Error {
final ObjectArrayList<Block> result = new ObjectArrayList<>();
final ObjectArrayList<Block> sub = getParameter(0).toBlock(context);
final BlockParenthesis bp = new BlockParenthesis();
final BlockContainer bpc = bp.getNumberContainer();
for (final Block b : sub) {
bpc.appendBlockUnsafe(b);
}
bpc.recomputeDimensions();
bp.recomputeDimensions();
result.add(bp);
return result;
}
@Override
public <Argument, Result> Result accept(final Function.Visitor<Argument, Result> visitor, final Argument argument) {
return visitor.visit(this, argument);
}
@Override
public String toString() {
String s = "(";
if (parameter == null) {
s += "null";
} else {
s += parameter.toString();
}
s += ")";
return s;
}
@Override
public boolean equals(final Object o) {
if (parameter == null | o == null) {
return parameter == o;
} else {
final Function f = (Function) o;
if (f instanceof Expression) {
return getParameter(0).equals(((Expression) f).getParameter(0));
} else {
return getParameter(0).equals(f);
}
}
}
@Override
public Expression clone() {
return new Expression(mathContext, parameter == null ? null : parameter.clone());
}
@Override
public Expression clone(MathContext newContext) {
return new Expression(newContext, parameter == null ? null : parameter.clone(newContext));
}
}