Memory improvements
This commit is contained in:
parent
c000a525db
commit
bd91238b14
@ -352,4 +352,15 @@ public final class App {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static String find(@Nonnull List<String> tokens, @Nonnull String text, int position) {
|
||||
for (int i = 0; i < tokens.size(); i++) {
|
||||
final String token = tokens.get(i);
|
||||
if (text.startsWith(token, position)) {
|
||||
return token;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
@ -176,7 +176,7 @@ public class FunctionsRegistry extends BaseEntitiesRegistry<Function, OldFunctio
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void save() {
|
||||
public void save() {
|
||||
handler.removeCallbacks(writeTask);
|
||||
handler.postDelayed(writeTask, 500);
|
||||
}
|
||||
|
@ -33,6 +33,9 @@ import javax.inject.Singleton;
|
||||
@Singleton
|
||||
public class Keyboard {
|
||||
|
||||
@Nonnull
|
||||
private final MathType.Result mathType = new MathType.Result();
|
||||
|
||||
@Inject
|
||||
Editor editor;
|
||||
|
||||
@ -61,7 +64,7 @@ public class Keyboard {
|
||||
int cursorPositionOffset = 0;
|
||||
final StringBuilder textToBeInserted = new StringBuilder(text);
|
||||
|
||||
final MathType.Result mathType = MathType.getType(text, 0, false);
|
||||
MathType.getType(text, 0, false, mathType);
|
||||
switch (mathType.type) {
|
||||
case function:
|
||||
textToBeInserted.append("()");
|
||||
|
@ -26,34 +26,17 @@ import android.support.annotation.StringRes;
|
||||
import jscl.math.operator.*;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import java.util.Arrays;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
public enum OperatorCategory implements Category {
|
||||
|
||||
derivatives(100, R.string.derivatives) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
return operator instanceof Derivative || operator instanceof Integral || operator instanceof IndefiniteIntegral;
|
||||
}
|
||||
},
|
||||
|
||||
other(200, R.string.other) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
return operator instanceof Sum || operator instanceof Product;
|
||||
}
|
||||
},
|
||||
|
||||
my(0, R.string.c_fun_category_my) {
|
||||
my(R.string.c_fun_category_my) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
return !operator.isSystem();
|
||||
}
|
||||
},
|
||||
|
||||
common(50, R.string.c_fun_category_common) {
|
||||
common(R.string.c_fun_category_common) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
for (OperatorCategory category : values()) {
|
||||
@ -66,36 +49,29 @@ public enum OperatorCategory implements Category {
|
||||
|
||||
return true;
|
||||
}
|
||||
},
|
||||
|
||||
derivatives(R.string.derivatives) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
return operator instanceof Derivative || operator instanceof Integral || operator instanceof IndefiniteIntegral;
|
||||
}
|
||||
},
|
||||
|
||||
other(R.string.other) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull Operator operator) {
|
||||
return operator instanceof Sum || operator instanceof Product;
|
||||
}
|
||||
};
|
||||
|
||||
private final int tabOrder;
|
||||
@StringRes
|
||||
private final int title;
|
||||
|
||||
OperatorCategory(int tabOrder, @StringRes int title) {
|
||||
this.tabOrder = tabOrder;
|
||||
OperatorCategory(@StringRes int title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static List<OperatorCategory> getCategoriesByTabOrder() {
|
||||
final List<OperatorCategory> result = Arrays.asList(OperatorCategory.values());
|
||||
|
||||
java.util.Collections.sort(result, new Comparator<OperatorCategory>() {
|
||||
@Override
|
||||
public int compare(OperatorCategory category, OperatorCategory category1) {
|
||||
return category.tabOrder - category1.tabOrder;
|
||||
}
|
||||
});
|
||||
|
||||
// todo serso: current solution (as creating operators is not implemented yet)
|
||||
result.remove(my);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
|
||||
public abstract boolean isInCategory(@Nonnull Operator operator);
|
||||
|
||||
@Override
|
||||
|
@ -26,7 +26,6 @@ import jscl.math.function.Function;
|
||||
import jscl.math.function.IConstant;
|
||||
import org.solovyev.android.calculator.math.MathType;
|
||||
import org.solovyev.android.calculator.text.TextProcessor;
|
||||
import org.solovyev.common.collections.Collections;
|
||||
import org.solovyev.common.msg.MessageType;
|
||||
import org.solovyev.common.search.StartsWithFinder;
|
||||
|
||||
@ -56,20 +55,19 @@ public class ToJsclTextProcessor implements TextProcessor<PreparedExpression, St
|
||||
|
||||
@Nonnull
|
||||
private static StringBuilder processExpression(@Nonnull String s) throws ParseException {
|
||||
final StartsWithFinder startsWithFinder = StartsWithFinder.newInstance(s);
|
||||
final StringBuilder result = new StringBuilder();
|
||||
final MathType.Results results = new MathType.Results();
|
||||
|
||||
MathType.Result mathTypeResult = null;
|
||||
MathType.Result mathTypeBefore;
|
||||
MathType.Result mathTypeBefore = null;
|
||||
|
||||
final LiteNumberBuilder nb = new LiteNumberBuilder(Locator.getInstance().getEngine());
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
if (s.charAt(i) == ' ') continue;
|
||||
startsWithFinder.setI(i);
|
||||
|
||||
results.release(mathTypeBefore);
|
||||
mathTypeBefore = mathTypeResult == null ? null : mathTypeResult;
|
||||
|
||||
mathTypeResult = MathType.getType(s, i, nb.isHexMode());
|
||||
mathTypeResult = MathType.getType(s, i, nb.isHexMode(), results.obtain());
|
||||
|
||||
nb.process(mathTypeResult);
|
||||
|
||||
@ -84,7 +82,7 @@ public class ToJsclTextProcessor implements TextProcessor<PreparedExpression, St
|
||||
|
||||
if (mathTypeBefore != null &&
|
||||
(mathTypeBefore.type == MathType.function || mathTypeBefore.type == MathType.operator) &&
|
||||
App.find(MathType.groupSymbols, startsWithFinder) != null) {
|
||||
App.find(MathType.groupSymbols, s, i) != null) {
|
||||
final String functionName = mathTypeBefore.match;
|
||||
final Function function = Locator.getInstance().getEngine().getFunctionsRegistry().get(functionName);
|
||||
if (function == null || function.getMinParameters() > 0) {
|
||||
|
@ -26,49 +26,30 @@ import android.support.annotation.StringRes;
|
||||
import jscl.math.function.IConstant;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import java.util.Arrays;
|
||||
import java.util.Comparator;
|
||||
import java.util.List;
|
||||
|
||||
public enum VarCategory implements Category {
|
||||
|
||||
system(100, R.string.c_var_system) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull IConstant var) {
|
||||
return var.isSystem();
|
||||
}
|
||||
},
|
||||
|
||||
my(0, R.string.c_var_my) {
|
||||
my(R.string.c_var_my) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull IConstant var) {
|
||||
return !var.isSystem();
|
||||
}
|
||||
},
|
||||
|
||||
system(R.string.c_var_system) {
|
||||
@Override
|
||||
public boolean isInCategory(@Nonnull IConstant var) {
|
||||
return var.isSystem();
|
||||
}
|
||||
};
|
||||
|
||||
private final int tabOrder;
|
||||
@StringRes
|
||||
private final int title;
|
||||
|
||||
VarCategory(int tabOrder, @StringRes int title) {
|
||||
this.tabOrder = tabOrder;
|
||||
VarCategory(@StringRes int title) {
|
||||
this.title = title;
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static List<VarCategory> getCategoriesByTabOrder() {
|
||||
final List<VarCategory> result = Arrays.asList(VarCategory.values());
|
||||
|
||||
java.util.Collections.sort(result, new Comparator<VarCategory>() {
|
||||
@Override
|
||||
public int compare(VarCategory category, VarCategory category1) {
|
||||
return category.tabOrder - category1.tabOrder;
|
||||
}
|
||||
});
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public abstract boolean isInCategory(@Nonnull IConstant var);
|
||||
|
||||
|
||||
|
@ -242,7 +242,7 @@ public class History {
|
||||
|
||||
private void onRecentChanged(@Nonnull Object event) {
|
||||
handler.removeCallbacks(writeRecent);
|
||||
handler.postDelayed(writeRecent, 500);
|
||||
handler.postDelayed(writeRecent, 5000);
|
||||
bus.post(event);
|
||||
}
|
||||
|
||||
|
@ -25,9 +25,9 @@ package org.solovyev.android.calculator.math;
|
||||
import jscl.JsclMathEngine;
|
||||
import jscl.NumeralBase;
|
||||
import jscl.math.function.Constants;
|
||||
import org.solovyev.android.calculator.App;
|
||||
import org.solovyev.android.calculator.Locator;
|
||||
import org.solovyev.android.calculator.ParseException;
|
||||
import org.solovyev.common.JPredicate;
|
||||
|
||||
import javax.annotation.Nonnull;
|
||||
import javax.annotation.Nullable;
|
||||
@ -259,55 +259,48 @@ public enum MathType {
|
||||
*/
|
||||
@Nonnull
|
||||
public static Result getType(@Nonnull String text, int i, boolean hexMode) {
|
||||
return getType(text, i, hexMode, new Result());
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
public static Result getType(@Nonnull String text, int i, boolean hexMode, @Nonnull Result result) {
|
||||
if (i < 0) {
|
||||
throw new IllegalArgumentException("I must be more or equals to 0.");
|
||||
} else if (i >= text.length() && i != 0) {
|
||||
throw new IllegalArgumentException("I must be less than size of text.");
|
||||
} else if (i == 0 && text.length() == 0) {
|
||||
return new Result(MathType.text, text);
|
||||
return result.set(MathType.text, text);
|
||||
}
|
||||
|
||||
final StartsWithFinder startsWithFinder = new StartsWithFinder(text, i);
|
||||
|
||||
for (MathType mathType : getMathTypesByPriority()) {
|
||||
final String s = find(mathType.getTokens(), startsWithFinder);
|
||||
final List<MathType> mathTypes = getMathTypesByPriority();
|
||||
for (int j = 0; j < mathTypes.size(); j++) {
|
||||
final MathType mathType = mathTypes.get(j);
|
||||
final String s = App.find(mathType.getTokens(), text, i);
|
||||
if (s == null) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (s.length() > 1) {
|
||||
return new Result(mathType, s);
|
||||
return result.set(mathType, s);
|
||||
}
|
||||
|
||||
if (hexMode || JsclMathEngine.getInstance().getNumeralBase() == NumeralBase.hex) {
|
||||
final Character ch = s.charAt(0);
|
||||
if (NumeralBase.hex.getAcceptableCharacters().contains(ch)) {
|
||||
return new Result(MathType.digit, s);
|
||||
return result.set(MathType.digit, s);
|
||||
}
|
||||
}
|
||||
|
||||
if (mathType == MathType.grouping_separator) {
|
||||
if (i + 1 < text.length() && getType(text, i + 1, hexMode).type == MathType.digit) {
|
||||
return new Result(mathType, s);
|
||||
if (i + 1 < text.length() && getType(text, i + 1, hexMode, result).type == MathType.digit) {
|
||||
return result.set(mathType, s);
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
return new Result(mathType, s);
|
||||
return result.set(mathType, s);
|
||||
}
|
||||
|
||||
return new Result(MathType.text, text.substring(i));
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private static String find(@Nonnull List<String> list, @Nonnull JPredicate<String> predicate) {
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
final String token = list.get(i);
|
||||
if(predicate.apply(token)) {
|
||||
return token;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
return result.set(MathType.text, text.substring(i));
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
@ -388,15 +381,23 @@ public enum MathType {
|
||||
public static class Result {
|
||||
|
||||
@Nonnull
|
||||
public final MathType type;
|
||||
public MathType type;
|
||||
|
||||
@Nonnull
|
||||
public final String match;
|
||||
public String match;
|
||||
|
||||
public Result(@Nonnull MathType type, @Nonnull String match) {
|
||||
this.type = type;
|
||||
set(type, match);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
Result set(@Nonnull MathType type, @Nonnull String match) {
|
||||
this.type = type;
|
||||
this.match = match;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Result() {
|
||||
}
|
||||
|
||||
public int processToJscl(@Nonnull StringBuilder result, int i) throws ParseException {
|
||||
@ -404,24 +405,23 @@ public enum MathType {
|
||||
}
|
||||
}
|
||||
|
||||
private static class StartsWithFinder implements JPredicate<String> {
|
||||
public static class Results {
|
||||
@Nonnull
|
||||
private final List<Result> list = new ArrayList<>();
|
||||
|
||||
@Nonnull
|
||||
private final String targetString;
|
||||
private int i;
|
||||
|
||||
public StartsWithFinder(@Nonnull String targetString, int i) {
|
||||
this.targetString = targetString;
|
||||
this.i = i;
|
||||
public Result obtain() {
|
||||
if (list.isEmpty()) {
|
||||
return new Result();
|
||||
}
|
||||
return list.remove(list.size() - 1);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(@Nullable String s) {
|
||||
return s != null && targetString.startsWith(s, i);
|
||||
}
|
||||
|
||||
public void setI(int i) {
|
||||
this.i = i;
|
||||
public void release(@Nullable Result result) {
|
||||
if (result == null) {
|
||||
return;
|
||||
}
|
||||
list.add(result);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -57,7 +57,7 @@ public class CalculatorVarsActivity extends BaseActivity implements CalculatorEv
|
||||
|
||||
final CalculatorFragmentType fragmentType = CalculatorFragmentType.variables;
|
||||
|
||||
for (VarCategory category : VarCategory.getCategoriesByTabOrder()) {
|
||||
for (VarCategory category : VarCategory.values()) {
|
||||
|
||||
final Bundle fragmentParameters;
|
||||
|
||||
|
@ -47,7 +47,7 @@ public class OperatorsActivity extends BaseActivity implements CalculatorEventLi
|
||||
|
||||
final CalculatorFragmentType fragmentType = CalculatorFragmentType.operators;
|
||||
|
||||
for (OperatorCategory category : OperatorCategory.getCategoriesByTabOrder()) {
|
||||
for (OperatorCategory category : OperatorCategory.values()) {
|
||||
ui.addTab(this, fragmentType.createSubFragmentTag(category.name()), fragmentType.getFragmentClass(), BaseEntitiesFragment.createBundleFor(category.name()), category.title(), R.id.main_layout);
|
||||
}
|
||||
}
|
||||
|
@ -42,25 +42,28 @@ public class FromJsclSimplifyTextProcessor implements TextProcessor<String, Gene
|
||||
@Nonnull
|
||||
@Override
|
||||
public String process(@Nonnull Generic from) {
|
||||
return removeMultiplicationSigns(from.toString());
|
||||
return fixMultiplicationSigns(from.toString());
|
||||
}
|
||||
|
||||
public String process(@Nonnull String s) {
|
||||
return removeMultiplicationSigns(s);
|
||||
return fixMultiplicationSigns(s);
|
||||
}
|
||||
|
||||
@Nonnull
|
||||
private String removeMultiplicationSigns(String s) {
|
||||
private String fixMultiplicationSigns(String s) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
final MathType.Results results = new MathType.Results();
|
||||
|
||||
MathType.Result mathTypeBefore;
|
||||
MathType.Result mathTypeBefore = null;
|
||||
MathType.Result mathType = null;
|
||||
MathType.Result mathTypeAfter = null;
|
||||
|
||||
for (int i = 0; i < s.length(); i++) {
|
||||
results.release(mathTypeBefore);
|
||||
mathTypeBefore = mathType;
|
||||
|
||||
if (mathTypeAfter == null) {
|
||||
mathType = MathType.getType(s, i, false);
|
||||
mathType = MathType.getType(s, i, false, results.obtain());
|
||||
} else {
|
||||
mathType = mathTypeAfter;
|
||||
}
|
||||
@ -68,7 +71,7 @@ public class FromJsclSimplifyTextProcessor implements TextProcessor<String, Gene
|
||||
char ch = s.charAt(i);
|
||||
if (ch == '*') {
|
||||
if (i + 1 < s.length()) {
|
||||
mathTypeAfter = MathType.getType(s, i + 1, false);
|
||||
mathTypeAfter = MathType.getType(s, i + 1, false, results.obtain());
|
||||
} else {
|
||||
mathTypeAfter = null;
|
||||
}
|
||||
@ -105,5 +108,4 @@ public class FromJsclSimplifyTextProcessor implements TextProcessor<String, Gene
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -80,13 +80,14 @@ public class TextHighlighter implements TextProcessor<TextProcessorEditorResult,
|
||||
final Engine engine = Locator.getInstance().getEngine();
|
||||
final SpannableStringBuilder sb = new SpannableStringBuilder();
|
||||
final BaseNumberBuilder nb = !formatNumber ? new LiteNumberBuilder(engine) : new NumberBuilder(engine);
|
||||
final MathType.Result result = new MathType.Result();
|
||||
|
||||
int offset = 0;
|
||||
int groupsCount = 0;
|
||||
int openGroupsCount = 0;
|
||||
|
||||
for (int i = 0; i < text.length(); i++) {
|
||||
final MathType.Result result = MathType.getType(text, i, nb.isHexMode());
|
||||
MathType.getType(text, i, nb.isHexMode(), result);
|
||||
|
||||
offset += nb.process(sb, result);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user