version 2.19

PIEvaluator setVariable by index bug fix
This commit is contained in:
2021-04-01 19:14:54 +03:00
parent 6e4b808a66
commit 58bdcd65a3
3 changed files with 127 additions and 44 deletions

View File

@@ -76,8 +76,9 @@ namespace PIEvaluatorTypes {
short arguments;
};
struct PIP_EXPORT Variable {
Variable() {value = 0.;}
Variable(const PIString & var_name, complexd val) {name = var_name; value = val;}
Variable() {value = 0.; index = -1;}
Variable(const PIString & var_name, complexd val, int ind = -1) {name = var_name; value = val; index = ind;}
int index;
PIString name;
complexd value;
};
@@ -99,29 +100,30 @@ public:
PIEvaluatorContent();
~PIEvaluatorContent() {;}
void addFunction(const PIString & name, int args = 1) {functions.push_back(PIEvaluatorTypes::Function(name, args, getBaseFunction(name)));}
void addVariable(const PIString & name, const complexd & val = 0.) {variables.push_back(PIEvaluatorTypes::Variable(name, val)); sortVariables();}
void addCustomFunction(const PIString & name, int args_count, FuncFunc func) {functions << PIEvaluatorTypes::Function(name, args_count, func);}
void addFunction(const PIString & name, int args = 1);
int addVariable(const PIString & name, const complexd & val = 0.);
void addCustomFunction(const PIString & name, int args_count, FuncFunc func);
int functionsCount() const {return functions.size();}
int variablesCount() const {return variables.size();}
int customVariablesCount() const {return variables.size() - cv_count;}
int findFunction(const PIString & name) const {for (uint i = 0; i < functions.size(); i++) if (functions[i].identifier == name) return i; return -1;}
int findVariable(const PIString & var_name) const {for (uint i = 0; i < variables.size(); i++) if (variables[i].name == var_name) return i; return -1;}
PIEvaluatorTypes::Function function(int index) {if (index < 0 || index >= functions.size_s()) return PIEvaluatorTypes::Function(); return functions[index];}
PIEvaluatorTypes::Variable variable(int index) {if (index < 0 || index >= variables.size_s()) return PIEvaluatorTypes::Variable(); return variables[index];}
int customVariablesCount() const;
int findFunction(const PIString & name) const;
int findVariable(const PIString & var_name) const;
PIEvaluatorTypes::Function function(int index);
PIEvaluatorTypes::Variable variable(int index);
PIEvaluatorTypes::Function function(const PIString & name) {return function(findFunction(name));}
PIEvaluatorTypes::Variable variable(const PIString & name) {return variable(findVariable(name));}
PIEvaluatorTypes::Variable customVariable(int index) {if (index < cv_count || index >= variables.size_s() + cv_count) return PIEvaluatorTypes::Variable(); return variables[index + cv_count];}
PIEvaluatorTypes::Variable customVariable(int index);
bool setVariableValue(int index, complexd new_value);
bool setVariableName(int index, const PIString & new_name);
bool setVariableValue(const PIString & var_name, const complexd & new_value) {return setVariableValue(findVariable(var_name), new_value);}
bool setVariableName(int index, const PIString & new_name);
bool setVariableName(const PIString & var_name, const PIString & new_name) {return setVariableName(findVariable(var_name), new_name);}
void removeVariable(int index) {variables.remove(index);}
void removeVariable(int index);
void removeVariable(const PIString & var_name) {removeVariable(findVariable(var_name));}
void clearCustomVariables();
void sortVariables();
PIEvaluatorTypes::BaseFunctions getBaseFunction(const PIString & name);
void dump();
private:
PIVector<PIEvaluatorTypes::Function> functions;
PIVector<PIEvaluatorTypes::Variable> variables;
@@ -154,12 +156,10 @@ public:
bool isCorrect() const {return correct;}
//! Set variable value with name "name" to value "value". Add variable if it doesn`t exists
int setVariable(const PIString & name, complexd value = 0.) {if (content.findVariable(name) < 0) content.addVariable(name, value); else content.setVariableValue(name, value); return content.findVariable(name);}
int setVariable(const PIString & name, complexd value = complexd(0.));
//! Set variable value with index "index" to value "value". Don`t add variable if it doesn`t exists
void setVariable(int index, complexd value = 0.) {if (index >= 0 && index < content.variablesCount()) content.setVariableValue(index, value);}
void setCustomVariableValue(int index, complexd value = 0.) {content.variables[index + content.cv_count].value = value;}
void setVariable(int index, complexd value = 0.);
//! Evaluate last successfully checked with function \a check() expression and returns result
complexd evaluate();
@@ -194,8 +194,6 @@ public:
//! Restore from %PIByteArray evaluator state (expression, variables, errors, compiled instructions)
void load(PIByteArray ba);
PIEvaluatorContent content;
private:
const PIString & prepare(const PIString & string);
PIString preprocess(const PIString & string);
@@ -216,12 +214,13 @@ private:
PIString inBrackets(const PIString & string);
PIString operationChar(const PIEvaluatorTypes::Operation & operation);
void operationsByPriority(int p, PIVector<PIEvaluatorTypes::Operation> & ret);
complexd value(const int & index) {if (index < 0) return tmpvars[-index - 1].value; else return kvars->at(index).value;}
complexd value(const int & index) {if (index < 0) return tmpvars[-index - 1].value; else return content.variables[index].value;}
inline complexd residue(const complexd & f, const complexd & s);
inline void execFunction(const PIEvaluatorTypes::Instruction & ci);
PIEvaluatorContent content;
PIDeque<PIEvaluatorTypes::Element> elements;
PIVector<PIEvaluatorTypes::Variable> currentVariables, variables, tmpvars, * kvars;
PIVector<PIEvaluatorTypes::Variable> currentVariables, variables, tmpvars;
PIVector<PIEvaluatorTypes::Instruction> instructions;
PIStringList unknownVars, usedVars;
PIString currentString, lastError;
@@ -232,6 +231,8 @@ private:
inline bool operator ==(PIEvaluatorTypes::Element e1, PIEvaluatorTypes::Element e2) {return (e1.type == e2.type && e1.num == e2.num);}
inline bool operator !=(PIEvaluatorTypes::Element e1, PIEvaluatorTypes::Element e2) {return (e1.type != e2.type || e1.num != e2.num);}
inline bool operator < (PIEvaluatorTypes::Variable e1, PIEvaluatorTypes::Variable e2) {return e1.name > e2.name;}
inline bool operator ==(PIEvaluatorTypes::Variable e1, PIEvaluatorTypes::Variable e2) {return e1.name == e2.name;}
inline PIByteArray & operator <<(PIByteArray & s, const PIEvaluatorTypes::Instruction & v) {
s << PIByteArray::RawData(&v, sizeof(v) - sizeof(v.operators)) << v.operators;