android_calculator-15: Add numeral systems
This commit is contained in:
parent
4bcd26faec
commit
9384cd1784
@ -14,6 +14,7 @@ import jscl.math.Generic;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.solovyev.android.calculator.jscl.JsclOperation;
|
||||
import org.solovyev.android.calculator.model.CalculatorEngine;
|
||||
import org.solovyev.android.calculator.model.ParseException;
|
||||
import org.solovyev.android.calculator.model.TextProcessor;
|
||||
import org.solovyev.android.view.AutoResizeTextView;
|
||||
@ -34,7 +35,7 @@ public class CalculatorDisplay extends AutoResizeTextView {
|
||||
private JsclOperation jsclOperation = JsclOperation.numeric;
|
||||
|
||||
@NotNull
|
||||
private final static TextProcessor<TextHighlighter.Result> textHighlighter = new TextHighlighter(Color.WHITE, true);
|
||||
private final static TextProcessor<TextHighlighter.Result> textHighlighter = new TextHighlighter(Color.WHITE, true, CalculatorEngine.instance.getEngine());
|
||||
|
||||
@Nullable
|
||||
private Generic genericResult;
|
||||
|
@ -7,15 +7,16 @@ package org.solovyev.android.calculator;
|
||||
|
||||
import android.content.Context;
|
||||
import android.graphics.Color;
|
||||
import android.os.Build;
|
||||
import android.text.Html;
|
||||
import android.util.AttributeSet;
|
||||
import android.util.Log;
|
||||
import android.view.ContextMenu;
|
||||
import android.widget.EditText;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.solovyev.android.calculator.model.CalculatorEngine;
|
||||
import org.solovyev.android.calculator.model.ParseException;
|
||||
import org.solovyev.android.calculator.model.TextProcessor;
|
||||
import org.solovyev.common.math.calculators.Calculator;
|
||||
|
||||
/**
|
||||
* User: serso
|
||||
@ -27,7 +28,7 @@ public class CalculatorEditor extends EditText {
|
||||
private boolean highlightText = true;
|
||||
|
||||
@NotNull
|
||||
private final static TextProcessor<TextHighlighter.Result> textHighlighter = new TextHighlighter(Color.WHITE, false);
|
||||
private final static TextProcessor<TextHighlighter.Result> textHighlighter = new TextHighlighter(Color.WHITE, false, CalculatorEngine.instance.getEngine());
|
||||
|
||||
public CalculatorEditor(Context context) {
|
||||
super(context);
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
package org.solovyev.android.calculator;
|
||||
|
||||
import jscl.MathContext;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.solovyev.android.calculator.math.MathType;
|
||||
import org.solovyev.android.calculator.model.NumberBuilder;
|
||||
@ -20,6 +21,9 @@ import org.solovyev.common.utils.MutableObject;
|
||||
*/
|
||||
public class TextHighlighter implements TextProcessor<TextHighlighter.Result> {
|
||||
|
||||
@NotNull
|
||||
public final MathContext mathContext;
|
||||
|
||||
public static class Result implements CharSequence {
|
||||
|
||||
@NotNull
|
||||
@ -63,9 +67,10 @@ public class TextHighlighter implements TextProcessor<TextHighlighter.Result> {
|
||||
private final int colorBlue;
|
||||
private final boolean simpleFormat;
|
||||
|
||||
public TextHighlighter(int baseColor, boolean simpleFormat) {
|
||||
public TextHighlighter(int baseColor, boolean simpleFormat, @NotNull MathContext mathContext) {
|
||||
this.color = baseColor;
|
||||
this.simpleFormat = simpleFormat;
|
||||
this.mathContext = mathContext;
|
||||
//this.colorRed = Color.red(baseColor);
|
||||
this.colorRed = (baseColor >> 16) & 0xFF;
|
||||
//this.colorGreen = Color.green(baseColor);
|
||||
@ -86,7 +91,7 @@ public class TextHighlighter implements TextProcessor<TextHighlighter.Result> {
|
||||
|
||||
int numberOffset = 0;
|
||||
|
||||
final NumberBuilder numberBuilder = new NumberBuilder(simpleFormat);
|
||||
final NumberBuilder numberBuilder = new NumberBuilder(simpleFormat, mathContext.getNumeralBase());
|
||||
for (int i = 0; i < text.length(); i++) {
|
||||
MathType.Result mathType = MathType.getType(text, i);
|
||||
|
||||
|
@ -16,7 +16,7 @@ import org.solovyev.android.calculator.model.TextProcessor;
|
||||
|
||||
public enum JsclOperation {
|
||||
|
||||
simplify(new FromJsclSimplifyTextProcessor()) {
|
||||
simplify(new FromJsclSimplifyTextProcessor(CalculatorEngine.instance.getEngine())) {
|
||||
@NotNull
|
||||
@Override
|
||||
public String evaluate(@NotNull String expression) throws ParseException {
|
||||
|
@ -20,7 +20,7 @@ import java.util.*;
|
||||
|
||||
public enum MathType {
|
||||
|
||||
/* numeral_base(50, true, false) {
|
||||
numeral_base(50, true, false) {
|
||||
|
||||
private final List<String> tokens = new ArrayList<String>(10);
|
||||
{
|
||||
@ -37,7 +37,7 @@ public enum MathType {
|
||||
public List<String> getTokens() {
|
||||
return tokens;
|
||||
}
|
||||
},*/
|
||||
},
|
||||
|
||||
dot(200, true, true, ".") {
|
||||
@Override
|
||||
|
@ -338,7 +338,7 @@ public enum CalculatorEngine {
|
||||
}
|
||||
|
||||
public void setDefaultAngleUnits(@NotNull AngleUnit angleUnits) {
|
||||
getEngine().setDefaultAngleUnit(angleUnits);
|
||||
getEngine().setAngleUnits(angleUnits);
|
||||
}
|
||||
|
||||
// for tests only
|
||||
|
@ -1,5 +1,7 @@
|
||||
package org.solovyev.android.calculator.model;
|
||||
|
||||
import jscl.MathContext;
|
||||
import jscl.MathEngine;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.solovyev.android.calculator.math.MathType;
|
||||
@ -14,12 +16,19 @@ import java.util.List;
|
||||
*/
|
||||
public class FromJsclSimplifyTextProcessor implements TextProcessor<String> {
|
||||
|
||||
@NotNull
|
||||
private final MathContext mathContext;
|
||||
|
||||
public FromJsclSimplifyTextProcessor(@NotNull MathContext mathContext) {
|
||||
this.mathContext = mathContext;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public String process(@NotNull String s) throws ParseException {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
final NumberBuilder numberBuilder = new NumberBuilder(true);
|
||||
final NumberBuilder numberBuilder = new NumberBuilder(true, mathContext.getNumeralBase());
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
final MathType.Result mathTypeResult = MathType.getType(s, i);
|
||||
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
package org.solovyev.android.calculator.model;
|
||||
|
||||
import jscl.NumeralBase;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
import org.solovyev.android.calculator.math.MathType;
|
||||
@ -30,11 +31,16 @@ public class NumberBuilder {
|
||||
|
||||
private final boolean simpleFormat;
|
||||
|
||||
/*@Nullable
|
||||
@NotNull
|
||||
private final NumeralBase defaultNumeralBase;
|
||||
|
||||
@Nullable
|
||||
private NumeralBase nb;
|
||||
*/
|
||||
public NumberBuilder(boolean simpleFormat) {
|
||||
|
||||
public NumberBuilder(boolean simpleFormat, @NotNull NumeralBase defaultNumeralBase) {
|
||||
this.simpleFormat = simpleFormat;
|
||||
this.defaultNumeralBase = defaultNumeralBase;
|
||||
this.nb = defaultNumeralBase;
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@ -42,17 +48,17 @@ public class NumberBuilder {
|
||||
number = null;
|
||||
|
||||
final MathType.Result possibleResult;
|
||||
if ((CollectionsUtils.contains(mathTypeResult.getMathType(), MathType.digit, /*MathType.numeral_base,*/ MathType.dot, MathType.grouping_separator, MathType.power_10) ||
|
||||
if ((CollectionsUtils.contains(mathTypeResult.getMathType(), MathType.digit, MathType.numeral_base, MathType.dot, MathType.grouping_separator, MathType.power_10) ||
|
||||
isSignAfterE(mathTypeResult)) && numeralBaseCheck(mathTypeResult)) {
|
||||
if (numberBuilder == null) {
|
||||
numberBuilder = new StringBuilder();
|
||||
}
|
||||
|
||||
/*if (mathTypeResult.getMathType() != MathType.numeral_base) {*/
|
||||
if (mathTypeResult.getMathType() != MathType.numeral_base) {
|
||||
numberBuilder.append(mathTypeResult.getMatch());
|
||||
/*} else {
|
||||
} else {
|
||||
nb = NumeralBase.getByPrefix(mathTypeResult.getMatch());
|
||||
}*/
|
||||
}
|
||||
|
||||
possibleResult = null;
|
||||
} else {
|
||||
@ -63,7 +69,7 @@ public class NumberBuilder {
|
||||
}
|
||||
|
||||
private boolean numeralBaseCheck( @NotNull MathType.Result mathType ) {
|
||||
/*if ( mathType.getMathType() == MathType.digit ) {
|
||||
if ( mathType.getMathType() == MathType.digit ) {
|
||||
final Character ch = mathType.getMatch().charAt(0);
|
||||
if ( NumeralBase.hex.getAcceptableCharacters().contains(ch) && !NumeralBase.dec.getAcceptableCharacters().contains(ch) ) {
|
||||
if ( nb == NumeralBase.hex ) {
|
||||
@ -76,8 +82,7 @@ public class NumberBuilder {
|
||||
}
|
||||
} else {
|
||||
return true;
|
||||
}*/
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private boolean isSignAfterE(@NotNull MathType.Result mathTypeResult) {
|
||||
@ -113,7 +118,7 @@ public class NumberBuilder {
|
||||
}
|
||||
|
||||
numberBuilder = null;
|
||||
/*nb = null;*/
|
||||
nb = defaultNumeralBase;
|
||||
} else {
|
||||
number = null;
|
||||
}
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
package org.solovyev.android.calculator;
|
||||
|
||||
import jscl.JsclMathEngine;
|
||||
import junit.framework.Assert;
|
||||
import org.junit.Test;
|
||||
import org.solovyev.android.calculator.model.TextProcessor;
|
||||
@ -22,7 +23,7 @@ public class TextHighlighterTest {
|
||||
|
||||
@Test
|
||||
public void testProcess() throws Exception {
|
||||
TextProcessor textHighlighter = new TextHighlighter(0, true);
|
||||
TextProcessor textHighlighter = new TextHighlighter(0, true, JsclMathEngine.instance);
|
||||
|
||||
final Random random = new Random(new Date().getTime());
|
||||
for (int i = 0; i < 1000; i++) {
|
||||
@ -44,14 +45,14 @@ public class TextHighlighterTest {
|
||||
Assert.assertEquals("1 000 000", textHighlighter.process("1000000").toString());
|
||||
Assert.assertEquals("1 000 000", textHighlighter.process("1000000").toString());
|
||||
|
||||
textHighlighter = new TextHighlighter(0, false);
|
||||
textHighlighter = new TextHighlighter(0, false, JsclMathEngine.instance);
|
||||
Assert.assertEquals("0.1E3", textHighlighter.process("0.1E3").toString());
|
||||
Assert.assertEquals("1E3", textHighlighter.process("1E3").toString());
|
||||
Assert.assertEquals("1 000 000E3", textHighlighter.process("1000000E3").toString());
|
||||
Assert.assertEquals("-1 000 000E3", textHighlighter.process("-1000000E3").toString());
|
||||
Assert.assertEquals("-1 000 000E-3", textHighlighter.process("-1000000E-3").toString());
|
||||
Assert.assertEquals("-1 000 000E-30000", textHighlighter.process("-1000000E-30000").toString());
|
||||
textHighlighter = new TextHighlighter(0, true);
|
||||
textHighlighter = new TextHighlighter(0, true, JsclMathEngine.instance);
|
||||
|
||||
textHighlighter.process("cannot calculate 3^10^10 !!!\n" +
|
||||
" unable to enter 0. FIXED\n" +
|
||||
|
@ -94,27 +94,27 @@ public class CalculatorEngineTest {
|
||||
Assert.assertEquals("1", cm.evaluate(JsclOperation.simplify, "eq( 1, 1)").getResult());
|
||||
Assert.assertEquals("1", cm.evaluate(JsclOperation.numeric, "lg(10)").getResult());
|
||||
Assert.assertEquals("4", cm.evaluate(JsclOperation.numeric, "2+2").getResult());
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getDefaultAngleUnit();
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getAngleUnits();
|
||||
try {
|
||||
cm.getEngine().setDefaultAngleUnit(AngleUnit.rad);
|
||||
cm.getEngine().setAngleUnits(AngleUnit.rad);
|
||||
Assert.assertEquals("-0.757", cm.evaluate(JsclOperation.numeric, "sin(4)").getResult());
|
||||
Assert.assertEquals("0.524", cm.evaluate(JsclOperation.numeric, "asin(0.5)").getResult());
|
||||
Assert.assertEquals("-0.396", cm.evaluate(JsclOperation.numeric, "sin(4)asin(0.5)").getResult());
|
||||
Assert.assertEquals("-0.56", cm.evaluate(JsclOperation.numeric, "sin(4)asin(0.5)√(2)").getResult());
|
||||
Assert.assertEquals("-0.56", cm.evaluate(JsclOperation.numeric, "sin(4)asin(0.5)√(2)").getResult());
|
||||
} finally {
|
||||
cm.getEngine().setDefaultAngleUnit(defaultAngleUnit);
|
||||
cm.getEngine().setAngleUnits(defaultAngleUnit);
|
||||
}
|
||||
Assert.assertEquals("7.389", cm.evaluate(JsclOperation.numeric, "e^2").getResult());
|
||||
Assert.assertEquals("7.389", cm.evaluate(JsclOperation.numeric, "exp(1)^2").getResult());
|
||||
Assert.assertEquals("7.389", cm.evaluate(JsclOperation.numeric, "exp(2)").getResult());
|
||||
Assert.assertEquals("2+i", cm.evaluate(JsclOperation.numeric, "2*1+√(-1)").getResult());
|
||||
try {
|
||||
cm.getEngine().setDefaultAngleUnit(AngleUnit.rad);
|
||||
cm.getEngine().setAngleUnits(AngleUnit.rad);
|
||||
Assert.assertEquals("0.921+3.142i", cm.evaluate(JsclOperation.numeric, "ln(5cosh(38π√(2cos(2))))").getResult());
|
||||
Assert.assertEquals("-3.41+3.41i", cm.evaluate(JsclOperation.numeric, "(5tan(2i)+2i)/(1-i)").getResult());
|
||||
} finally {
|
||||
cm.getEngine().setDefaultAngleUnit(defaultAngleUnit);
|
||||
cm.getEngine().setAngleUnits(defaultAngleUnit);
|
||||
}
|
||||
Assert.assertEquals("7.389i", cm.evaluate(JsclOperation.numeric, "iexp(2)").getResult());
|
||||
Assert.assertEquals("2+7.389i", cm.evaluate(JsclOperation.numeric, "2+iexp(2)").getResult());
|
||||
@ -152,7 +152,7 @@ public class CalculatorEngineTest {
|
||||
CalculatorEngine.instance.getVarsRegister().add(new Var.Builder("si", 5d));
|
||||
|
||||
try {
|
||||
cm.getEngine().setDefaultAngleUnit(AngleUnit.rad);
|
||||
cm.getEngine().setAngleUnits(AngleUnit.rad);
|
||||
Assert.assertEquals("0.451", cm.evaluate(JsclOperation.numeric, "acos(0.8999999999999811)").getResult());
|
||||
Assert.assertEquals("-0.959", cm.evaluate(JsclOperation.numeric, "sin(5)").getResult());
|
||||
Assert.assertEquals("-4.795", cm.evaluate(JsclOperation.numeric, "sin(5)si").getResult());
|
||||
@ -160,7 +160,7 @@ public class CalculatorEngineTest {
|
||||
Assert.assertEquals("-23.973", cm.evaluate(JsclOperation.numeric, "si*sin(5)si").getResult());
|
||||
Assert.assertEquals("-3.309", cm.evaluate(JsclOperation.numeric, "sisin(5si)si").getResult());
|
||||
} finally {
|
||||
cm.getEngine().setDefaultAngleUnit(defaultAngleUnit);
|
||||
cm.getEngine().setAngleUnits(defaultAngleUnit);
|
||||
}
|
||||
|
||||
CalculatorEngine.instance.getVarsRegister().add(new Var.Builder("s", 1d));
|
||||
@ -252,12 +252,12 @@ public class CalculatorEngineTest {
|
||||
} catch (ParseException e) {
|
||||
}
|
||||
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getDefaultAngleUnit();
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getAngleUnits();
|
||||
try {
|
||||
cm.getEngine().setDefaultAngleUnit(AngleUnit.rad);
|
||||
cm.getEngine().setAngleUnits(AngleUnit.rad);
|
||||
Assert.assertEquals("0.739", cm.evaluate(JsclOperation.numeric, "cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(cos(1))))))))))))))))))))))))))))))))))))").getResult());
|
||||
} finally {
|
||||
cm.getEngine().setDefaultAngleUnit(defaultAngleUnit);
|
||||
cm.getEngine().setAngleUnits(defaultAngleUnit);
|
||||
}
|
||||
|
||||
CalculatorEngine.instance.getVarsRegister().add(new Var.Builder("si", 5d));
|
||||
@ -327,9 +327,9 @@ public class CalculatorEngineTest {
|
||||
public void testDegrees() throws Exception {
|
||||
final CalculatorEngine cm = CalculatorEngine.instance;
|
||||
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getDefaultAngleUnit();
|
||||
final AngleUnit defaultAngleUnit = cm.getEngine().getAngleUnits();
|
||||
try {
|
||||
cm.getEngine().setDefaultAngleUnit(AngleUnit.rad);
|
||||
cm.getEngine().setAngleUnits(AngleUnit.rad);
|
||||
cm.setPrecision(3);
|
||||
try {
|
||||
Assert.assertEquals("0.017", cm.evaluate(JsclOperation.numeric, "°"));
|
||||
@ -350,7 +350,7 @@ public class CalculatorEngineTest {
|
||||
|
||||
Assert.assertEquals("∂(cos(t), t, t,1°)", cm.evaluate(JsclOperation.simplify, "∂(cos(t),t,t,1°)").getResult());
|
||||
} finally {
|
||||
cm.getEngine().setDefaultAngleUnit(defaultAngleUnit);
|
||||
cm.getEngine().setAngleUnits(defaultAngleUnit);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,5 +1,6 @@
|
||||
package org.solovyev.android.calculator.model;
|
||||
|
||||
import jscl.JsclMathEngine;
|
||||
import org.junit.Assert;
|
||||
import org.junit.BeforeClass;
|
||||
import org.junit.Test;
|
||||
@ -20,7 +21,7 @@ public class FromJsclSimplifyTextProcessorTest {
|
||||
|
||||
@Test
|
||||
public void testProcess() throws Exception {
|
||||
FromJsclSimplifyTextProcessor tp = new FromJsclSimplifyTextProcessor();
|
||||
FromJsclSimplifyTextProcessor tp = new FromJsclSimplifyTextProcessor(JsclMathEngine.instance);
|
||||
Assert.assertEquals("(e)", tp.process("(2.718281828459045)"));
|
||||
Assert.assertEquals("ee", tp.process("2.718281828459045*2.718281828459045"));
|
||||
Assert.assertEquals("((e)(e))", tp.process("((2.718281828459045)*(2.718281828459045))"));
|
||||
|
Loading…
Reference in New Issue
Block a user