[poincare] Restructuration of poincare (no duplication of children

storage)

Change-Id: Ia10c3cc83e10d238750c6954b7c093d26b762c94
This commit is contained in:
Émilie Feral
2017-09-21 10:33:58 +02:00
parent d3a2109b5f
commit 23629b0939
146 changed files with 1938 additions and 1889 deletions

View File

@@ -36,7 +36,7 @@ AppsContainer::AppsContainer() :
Poincare::Expression::setCircuitBreaker(AppsContainer::poincareCircuitBreaker);
}
bool AppsContainer::poincareCircuitBreaker(const Poincare::Expression * e) {
bool AppsContainer::poincareCircuitBreaker() {
Ion::Keyboard::State state = Ion::Keyboard::scan();
return state.keyDown(Ion::Keyboard::Key::A6);
}

View File

@@ -32,7 +32,7 @@
class AppsContainer : public Container {
public:
AppsContainer();
static bool poincareCircuitBreaker(const Poincare::Expression * e);
static bool poincareCircuitBreaker();
int numberOfApps();
App::Snapshot * appSnapshotAtIndex(int index);
App::Snapshot * hardwareTestAppSnapshot();

View File

@@ -19,8 +19,7 @@ void CartesianFunction::setDisplayDerivative(bool display) {
double CartesianFunction::approximateDerivative(double x, Poincare::Context * context) const {
Poincare::Complex<double> abscissa = Poincare::Complex<double>::Float(x);
Poincare::Expression * args[2] = {expression(), &abscissa};
Poincare::Derivative derivative;
derivative.setArgument(args, 2, true);
Poincare::Derivative derivative(args, true);
return derivative.approximate<double>(*context);
}

View File

@@ -286,7 +286,7 @@ T Sequence::templatedEvaluateAtAbscissa(T x, Poincare::Context * context) const
return bufferValue<T>(0);
}
LocalContext<T> subContext = LocalContext<T>(context);
Poincare::Symbol nSymbol = Poincare::Symbol(symbol());
Poincare::Symbol nSymbol(symbol());
int start = indexBuffer<T>(0) < 0 || indexBuffer<T>(0) > n ? 0 : indexBuffer<T>(0);
T un = indexBuffer<T>(0) < 0 || indexBuffer<T>(0) > n ? firstInitialConditionExpression()->approximate<T>(*context) : bufferValue<T>(0);
for (int i = start; i < n; i++) {
@@ -315,7 +315,7 @@ T Sequence::templatedEvaluateAtAbscissa(T x, Poincare::Context * context) const
return bufferValue<T>(1);
}
LocalContext<T> subContext = LocalContext<T>(context);
Poincare::Symbol nSymbol = Poincare::Symbol(symbol());
Poincare::Symbol nSymbol(symbol());
int start = indexBuffer<T>(0) >= 0 && indexBuffer<T>(0) < n && indexBuffer<T>(1) > 0 && indexBuffer<T>(1) <= n && indexBuffer<T>(0) + 1 == indexBuffer<T>(1) ? indexBuffer<T>(0) : 0;
T un = indexBuffer<T>(0) >= 0 && indexBuffer<T>(0) < n && indexBuffer<T>(1) > 0 && indexBuffer<T>(1) <= n && indexBuffer<T>(0) + 1 == indexBuffer<T>(1) ? bufferValue<T>(0) : firstInitialConditionExpression()->approximate<T>(*context);
T un1 = indexBuffer<T>(0) >= 0 && indexBuffer<T>(0) < n && indexBuffer<T>(1) > 0 && indexBuffer<T>(1) <= n && indexBuffer<T>(0) + 1 == indexBuffer<T>(1) ? bufferValue<T>(1) : secondInitialConditionExpression()->approximate<T>(*context);

View File

@@ -102,7 +102,7 @@ bool Function::isEmpty() {
template<typename T>
T Function::templatedEvaluateAtAbscissa(T x, Poincare::Context * context) const {
Poincare::VariableContext<T> variableContext = Poincare::VariableContext<T>(symbol(), context);
Poincare::Symbol xSymbol = Poincare::Symbol(symbol());
Poincare::Symbol xSymbol(symbol());
Poincare::Complex<T> e = Poincare::Complex<T>::Float(x);
variableContext.setExpressionForSymbolName(&e, &xSymbol);
return expression()->approximate<T>(variableContext);

View File

@@ -77,7 +77,7 @@ bool VariableBoxController::ContentViewController::handleEvent(Ion::Events::Even
}
if (event == Ion::Events::Backspace && m_currentPage != Page::RootMenu) {
if (m_currentPage == Page::Scalar) {
const Symbol symbol = Symbol('A'+selectedRow());
const Symbol symbol('A'+selectedRow());
m_context->setExpressionForSymbolName(nullptr, &symbol);
}
if (m_currentPage == Page::Matrix) {

View File

@@ -9,8 +9,8 @@ objs += $(addprefix poincare/src/,\
arc_sine.o\
arc_tangent.o\
binomial_coefficient.o\
bounded_static_hierarchy.o\
ceiling.o\
commutative_operation.o\
complex.o\
complex_argument.o\
complex_matrix.o\
@@ -21,7 +21,9 @@ objs += $(addprefix poincare/src/,\
determinant.o\
division_quotient.o\
division_remainder.o\
dynamic_hierarchy.o\
evaluation.o\
evaluation_engine.o\
expression.o\
expression_lexer.o\
expression_parser.o\
@@ -29,10 +31,10 @@ objs += $(addprefix poincare/src/,\
floor.o\
frac_part.o\
fraction.o\
function.o\
expression_matrix.o\
global_context.o\
great_common_divisor.o\
hierarchy.o\
hyperbolic_arc_cosine.o\
hyperbolic_arc_sine.o\
hyperbolic_arc_tangent.o\
@@ -42,8 +44,8 @@ objs += $(addprefix poincare/src/,\
imaginary_part.o\
integer.o\
integral.o\
layout_engine.o\
list_data.o\
leaf_expression.o\
least_common_multiple.o\
logarithm.o\
matrix.o\
@@ -53,7 +55,6 @@ objs += $(addprefix poincare/src/,\
matrix_trace.o\
matrix_transpose.o\
multiplication.o\
n_ary_operation.o\
naperian_logarithm.o\
nth_root.o\
opposite.o\
@@ -68,6 +69,7 @@ objs += $(addprefix poincare/src/,\
sequence.o\
sine.o\
square_root.o\
static_hierarchy.o\
store.o\
subtraction.o\
sum.o\
@@ -75,6 +77,7 @@ objs += $(addprefix poincare/src/,\
tangent.o\
variable_context.o\
)
objs += $(addprefix poincare/src/layout/,\
absolute_value_layout.o\
baseline_relative_layout.o\
@@ -112,22 +115,6 @@ tests += $(addprefix poincare/test/,\
# simplify_utils.cpp\
# identity.cpp\
# tests += $(addprefix poincare/test/,\
addition.cpp\
float.cpp\
fraction.cpp\
identity.cpp\
integer.cpp\
matrix.cpp\
product.cpp\
power.cpp\
simplify_utils.cpp\
simplify_addition.cpp\
simplify_product.cpp\
subtraction.cpp\
trigo.cpp\
)
ifdef POINCARE_TESTS_PRINT_EXPRESSIONS
tests += poincare/src/expression_debug.o
SFLAGS += -DPOINCARE_TESTS_PRINT_EXPRESSIONS=1

View File

@@ -1,24 +1,25 @@
#ifndef POINCARE_ABSOLUTE_VALUE_H
#define POINCARE_ABSOLUTE_VALUE_H
#include <poincare/function.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class AbsoluteValue : public Function {
class AbsoluteValue : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
AbsoluteValue();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};

View File

@@ -1,27 +1,39 @@
#ifndef POINCARE_ADDITION_H
#define POINCARE_ADDITION_H
#include <poincare/commutative_operation.h>
#include <poincare/dynamic_hierarchy.h>
#include <poincare/layout_engine.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Addition : public CommutativeOperation {
using CommutativeOperation::CommutativeOperation;
class Addition : public DynamicHierarchy {
using DynamicHierarchy::DynamicHierarchy;
public:
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n);
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * m);
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n) {
return EvaluationEngine::elementWiseOnComplexMatrices(m, n, compute<T>);
}
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * m) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
private:
Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const override {
return compute(c, d);
template<typename T> static Evaluation<T> * computeOnMatrixAndComplex(Evaluation<T> * m, const Complex<T> * c) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const override {
return compute(c, d);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<float>(this, context, angleUnit, compute<float>, computeOnComplexAndMatrix<float>, computeOnMatrixAndComplex<float>, computeOnMatrices<float>);
}
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<double>(this, context, angleUnit, compute<double>, computeOnComplexAndMatrix<double>, computeOnMatrixAndComplex<double>, computeOnMatrices<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createInfixLayout(this, floatDisplayMode, complexFormat, "+");
}
char operatorChar() const override;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_ARC_COSINE_H
#define POINCARE_ARC_COSINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ArcCosine : public Function {
class ArcCosine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ArcCosine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "acos");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_ARC_SINE_H
#define POINCARE_ARC_SINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ArcSine : public Function {
class ArcSine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ArcSine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "asin");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_ARC_TANGENT_H
#define POINCARE_ARC_TANGENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ArcTangent: public Function {
class ArcTangent : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ArcTangent();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "atan");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const;
};
}

View File

@@ -1,20 +1,21 @@
#ifndef POINCARE_BINOMIAL_COEFFICIENT_H
#define POINCARE_BINOMIAL_COEFFICIENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class BinomialCoefficient : public Function {
class BinomialCoefficient : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
BinomialCoefficient();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};

View File

@@ -0,0 +1,18 @@
#ifndef POINCARE_BOUNDED_STATIC_HIERARCHY_H
#define POINCARE_BOUNDED_STATIC_HIERARCHY_H
#include <poincare/static_hierarchy.h>
namespace Poincare {
template<int T>
class BoundedStaticHierarchy : public StaticHierarchy<T> {
public:
BoundedStaticHierarchy();
BoundedStaticHierarchy(Expression * const * operands, int numberOfOperands, bool cloneOperands = true);
bool hasValidNumberOfArguments() const override;
};
}
#endif

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_CEILING_H
#define POINCARE_CEILING_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Ceiling : public Function {
class Ceiling : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Ceiling();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit, computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "ceil");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,16 +0,0 @@
#ifndef POINCARE_COMMUTATIVE_OPERATION_H
#define POINCARE_COMMUTATIVE_OPERATION_H
#include <poincare/n_ary_operation.h>
namespace Poincare {
class CommutativeOperation : public NAryOperation {
using NAryOperation::NAryOperation;
public:
void sort() override;
};
}
#endif

View File

@@ -31,16 +31,23 @@ public:
Complex(const char * integralPart, int integralPartLength, bool integralNegative,
const char * fractionalPart, int fractionalPartLength,
const char * exponent, int exponentLength, bool exponentNegative);
T toScalar() const override;
const Complex<T> * operand(int i) const override {
return complexOperand(i);
}
int numberOfRows() const override;
int numberOfColumns() const override;
T a() const;
T b() const;
T r() const;
T th() const;
Complex<T> conjugate() const;
/* Expression */
Expression::Type type() const override;
Complex<T> * clone() const override;
Evaluation<T> * cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
bool isCommutative() const override;
bool hasValidNumberOfArguments() const override;
/* Evaluation */
T toScalar() const override;
int numberOfRows() const override;
int numberOfColumns() const override;
int writeTextInBuffer(char * buffer, int bufferSize) const override;
Evaluation<T> * createDeterminant() const override {
return clone();
@@ -49,11 +56,6 @@ public:
Evaluation<T> * createTrace() const override {
return clone();
}
T a() const;
T b() const;
T r() const;
T th() const;
Complex<T> conjugate() const;
/* The parameter 'DisplayMode' refers to the way to display float 'scientific'
* or 'auto'. The scientific mode returns float with style -1.2E2 whereas
* the auto mode tries to return 'natural' float like (0.021) and switches

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_COMPLEX_ARGUMENT_H
#define POINCARE_COMPLEX_ARGUMENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ComplexArgument : public Function {
class ComplexArgument : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ComplexArgument();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "arg");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -6,7 +6,7 @@
namespace Poincare {
template<typename T>
class ComplexMatrix : public Evaluation<T> {
class ComplexMatrix : public Evaluation<T> {
public:
ComplexMatrix(const Complex<T> * complexes, int numberOfRows, int numberOfColumns);
~ComplexMatrix();
@@ -14,14 +14,21 @@ public:
ComplexMatrix(ComplexMatrix&& other) = delete;
ComplexMatrix& operator=(const ComplexMatrix& other) = delete;
ComplexMatrix& operator=(ComplexMatrix&& other) = delete;
/* Expression */
Expression::Type type() const override;
ComplexMatrix<T> * clone() const override;
bool isCommutative() const override;
/* Evaluation */
T toScalar() const override;
const Complex<T> * complexOperand(int i) const override;
int numberOfRows() const override;
int numberOfColumns() const override;
ComplexMatrix<T> * clone() const override;
ComplexMatrix<T> * cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
const Complex<T> * complexOperand(int i) const override;
/* If the buffer is too small, the function fills the buffer until reaching
* buffer size */
int writeTextInBuffer(char * buffer, int bufferSize) const override;
static Evaluation<T> * createIdentity(int dim);
private:
Evaluation<float> * privateEvaluate(Expression::SinglePrecision p, Context& context, Expression::AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_CONFIDENCE_INTERVAL_H
#define POINCARE_CONFIDENCE_INTERVAL_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class ConfidenceInterval : public Function {
class ConfidenceInterval : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
ConfidenceInterval();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "confidence");
}
};
}

View File

@@ -1,24 +1,25 @@
#ifndef POINCARE_CONJUGATE_H
#define POINCARE_CONJUGATE_H
#include <poincare/function.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Conjugate : public Function {
class Conjugate : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Conjugate();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};

View File

@@ -1,23 +1,28 @@
#ifndef POINCARE_COSINE_H
#define POINCARE_COSINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Cosine : public Function {
class Cosine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Cosine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c, AngleUnit angleUnit = AngleUnit::Radian);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit = AngleUnit::Radian);
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return compute(c, angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return compute(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "cos");
}
};

View File

@@ -1,23 +1,27 @@
#ifndef POINCARE_DERIVATIVE_H
#define POINCARE_DERIVATIVE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/variable_context.h>
namespace Poincare {
class Derivative : public Function {
class Derivative : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
Derivative();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
template<typename T> T growthRateAroundAbscissa(T x, T h, VariableContext<T> variableContext, AngleUnit angleUnit) const;
template<typename T> T approximateDerivate2(T x, T h, VariableContext<T> xContext, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "diff");
}
// TODO: Change coefficients?
constexpr static double k_maxErrorRateOnApproximation = 0.001;
constexpr static double k_minInitialRate = 0.01;

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_DETERMINANT_H
#define POINCARE_DETERMINANT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class Determinant : public Function {
class Determinant : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Determinant();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "det");
}
};
}

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_DIVISION_QUOTIENT_H
#define POINCARE_DIVISION_QUOTIENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class DivisionQuotient : public Function {
class DivisionQuotient : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
DivisionQuotient();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "quo");
}
};
}

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_DIVISION_REMAINDER_H
#define POINCARE_DIVISION_REMAINDER_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class DivisionRemainder : public Function {
class DivisionRemainder : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
DivisionRemainder();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "rem");
}
};
}

View File

@@ -0,0 +1,26 @@
#ifndef POINCARE_DYNAMIC_HIERARCHY_H
#define POINCARE_DYNAMIC_HIERARCHY_H
#include <poincare/hierarchy.h>
namespace Poincare {
class DynamicHierarchy : public Hierarchy {
public:
DynamicHierarchy();
DynamicHierarchy(Expression ** operands, int numberOfOperands, bool cloneOperands = true);
~DynamicHierarchy();
DynamicHierarchy(const DynamicHierarchy& other) = delete;
DynamicHierarchy(DynamicHierarchy&& other) = delete;
DynamicHierarchy& operator=(const DynamicHierarchy& other) = delete;
DynamicHierarchy& operator=(DynamicHierarchy&& other) = delete;
int numberOfOperands() const override;
const Expression * operand(int i) const override;
protected:
Expression ** operands() override;
Expression ** m_operands;
};
}
#endif

View File

@@ -12,7 +12,7 @@ template<typename T>
class Evaluation : public Matrix {
public:
virtual T toScalar() const = 0;
bool hasValidNumberOfArguments() const override;
virtual int writeTextInBuffer(char * buffer, int bufferSize) const = 0;
virtual const Expression * operand(int i) const override;
virtual const Complex<T> * complexOperand(int i) const = 0;
virtual Evaluation<T> * clone() const override = 0;

View File

@@ -0,0 +1,28 @@
#ifndef POINCARE_EVALUATION_ENGINE_H
#define POINCARE_EVALUATION_ENGINE_H
#include <poincare/expression.h>
#include <poincare/evaluation.h>
#include <poincare/complex.h>
namespace Poincare {
class EvaluationEngine {
public:
template <typename T> using ExpressionToComplexMap = Complex<T>(*)(const Complex<T>, Expression::AngleUnit angleUnit);
template<typename T> static Evaluation<T> * map(const Expression * expression, Context& context, Expression::AngleUnit angleUnit, ExpressionToComplexMap<T> compute);
template <typename T> using ComplexAndComplexReduction = Complex<T>(*)(const Complex<T>, const Complex<T>);
template <typename T> using ComplexAndMatrixReduction = Evaluation<T> * (*)(const Complex<T> * c, Evaluation<T> * m);
template <typename T> using MatrixAndComplexReduction = Evaluation<T> * (*)(Evaluation<T> * m, const Complex<T> * c);
template <typename T> using MatrixAndMatrixReduction = Evaluation<T> * (*)(Evaluation<T> * m, Evaluation<T> * n);
template<typename T> static Evaluation<T> * mapReduce(const Expression * expression, Context& context, Expression::AngleUnit angleUnit, ComplexAndComplexReduction<T> computeOnComplexes, ComplexAndMatrixReduction<T> computeOnComplexAndMatrix, MatrixAndComplexReduction<T> computeOnMatrixAndComplex, MatrixAndMatrixReduction<T> computeOnMatrices);
template<typename T> static Evaluation<T> * elementWiseOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * n, ComplexAndComplexReduction<T> computeOnComplexes);
template<typename T> static Evaluation<T> * elementWiseOnComplexMatrices(Evaluation<T> * m, Evaluation<T> * n, ComplexAndComplexReduction<T> computeOnComplexes);
};
}
#endif

View File

@@ -2,7 +2,6 @@
#define POINCARE_EXPRESSION_H
#include <poincare/expression_layout.h>
#include <kandinsky.h>
namespace Poincare {
@@ -70,11 +69,6 @@ public:
Determinant,
Store,
};
enum class AngleUnit {
Degree = 0,
Radian = 1,
Default = 2
};
enum class FloatDisplayMode {
Decimal = 0,
Scientific = 1,
@@ -85,52 +79,64 @@ public:
Polar = 1,
Default = 2
};
enum class AngleUnit {
Degree = 0,
Radian = 1,
Default = 2
};
/* Constructor & Destructor */
static Expression * parse(char const * string);
virtual ~Expression() = default;
virtual bool hasValidNumberOfArguments() const = 0;
ExpressionLayout * createLayout(FloatDisplayMode floatDisplayMode = FloatDisplayMode::Default, ComplexFormat complexFormat = ComplexFormat::Default) const; // Returned object must be deleted
/* Poor man's RTTI */
virtual Type type() const = 0;
/* Circuit breaker */
typedef bool (*CircuitBreaker)();
static void setCircuitBreaker(CircuitBreaker cb);
static bool shouldStopProcessing();
/* Hierarchy */
virtual bool hasValidNumberOfArguments() const;
virtual const Expression * operand(int i) const = 0;
virtual int numberOfOperands() const = 0;
virtual Expression * clone() const = 0;
virtual Expression * cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands = true) const = 0;
// TODO: Consider std::unique_ptr - see https://google-styleguide.googlecode.com/svn/trunk/cppguide.html#Ownership_and_Smart_Pointers
/* Layout Engine */
ExpressionLayout * createLayout(FloatDisplayMode floatDisplayMode = FloatDisplayMode::Default, ComplexFormat complexFormat = ComplexFormat::Default) const; // Returned object must be deleted
/* This tests whether two expressions are the same, it heavily relies on the
/* Commutative rule */
virtual bool isCommutative() const = 0;
virtual void sort();
/* This tests whether two expressions are the =, <, >, it heavily relies on the
* fact that operands are sorted.
*/
bool isIdenticalTo(const Expression * e) const;
bool isGreaterThan(const Expression * e) const;
int comparesTo(const Expression * e) const;
//Expression * simplify() const;
virtual void sort();
virtual Type type() const = 0;
typedef bool (*CircuitBreaker)(const Expression * e);
static void setCircuitBreaker(CircuitBreaker cb);
bool shouldStopProcessing() const;
/* The function evaluate creates a new expression and thus mallocs memory.
/* Evaluation Engine
* The function evaluate creates a new expression and thus mallocs memory.
* Do not forget to delete the new expression to avoid leaking. */
template<typename T> Evaluation<T> * evaluate(Context& context, AngleUnit angleUnit = AngleUnit::Default) const;
template<typename T> T approximate(Context& context, AngleUnit angleUnit = AngleUnit::Default) const;
template<typename T> static T approximate(const char * text, Context& context, AngleUnit angleUnit = AngleUnit::Default);
virtual int writeTextInBuffer(char * buffer, int bufferSize) const;
protected:
/* Evaluation Engine */
typedef float SinglePrecision;
typedef double DoublePrecision;
template<typename T> static T epsilon();
/* Compare (== and >) the type of the root node of 2 expressions.
/* Compare (== < and >) the type of the root node of 2 expressions.
* This behavior makes sense for value-less nodes (addition, product, fraction
* power, etc… For nodes with a value (Integer, Complex), this must be over-
* -riden. */
virtual bool nodeEquals(const Expression * e) const;
virtual bool nodeGreaterThan(const Expression * e) const;
virtual int nodeComparesTo(const Expression * e) const;
private:
/* Layout Engine */
virtual ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const = 0;
/* Evaluation Engine */
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const = 0;
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const = 0;
};
}

View File

@@ -14,14 +14,16 @@ public:
ExpressionMatrix(Matrix&& other) = delete;
ExpressionMatrix& operator=(const ExpressionMatrix& other) = delete;
ExpressionMatrix& operator=(ExpressionMatrix&& other) = delete;
bool hasValidNumberOfArguments() const override;
/* Expression */
Type type() const override;
Expression * clone() const override;
bool isCommutative() const override;
/* Evaluation */
int numberOfRows() const override;
int numberOfColumns() const override;
const Expression * operand(int i) const override;
Expression * clone() const override;
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }

View File

@@ -1,24 +1,25 @@
#ifndef POINCARE_FACTORIAL_H
#define POINCARE_FACTORIAL_H
#include <poincare/function.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Factorial : public Function {
class Factorial : public StaticHierarchy<1> {
public:
Factorial(Expression * argument, bool clone = true);
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_FLOOR_H
#define POINCARE_FLOOR_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Floor : public Function {
class Floor : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Floor();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit, computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "floor");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_FRAC_PART_H
#define POINCARE_FRAC_PART_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class FracPart : public Function {
class FracPart : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
FracPart();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit, computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "Frac");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,42 +1,33 @@
#ifndef POINCARE_FRACTION_H
#define POINCARE_FRACTION_H
#include <poincare/n_ary_operation.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Fraction : public NAryOperation {
using NAryOperation::NAryOperation;
class Fraction : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
private:
template<typename T> static Evaluation<T> * computeOnMatrixAndComplex(Evaluation<T> * m, const Complex<T> * c) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * n);
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<float>(this, context, angleUnit, compute<float>, computeOnComplexAndMatrix<float>, computeOnMatrixAndComplex<float>, computeOnMatrices<float>);
}
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<double>(this, context, angleUnit, compute<double>, computeOnComplexAndMatrix<double>, computeOnMatrixAndComplex<double>, computeOnMatrices<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Evaluation<float> * computeOnComplexAndComplexMatrix(const Complex<float> * c, Evaluation<float> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
Evaluation<double> * computeOnComplexAndComplexMatrix(const Complex<double> * c, Evaluation<double> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * n) const;
Evaluation<float> * computeOnComplexMatrices(Evaluation<float> * m, Evaluation<float> * n) const override {
return templatedComputeOnComplexMatrices(m, n);
}
Evaluation<double> * computeOnComplexMatrices(Evaluation<double> * m, Evaluation<double> * n) const override {
return templatedComputeOnComplexMatrices(m, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexMatrices(Evaluation<T> * m, Evaluation<T> * n) const;
Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const override {
return compute(c, d);
}
Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const override {
return compute(c, d);
}
};
}

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_GREAT_COMMON_DIVISOR_H
#define POINCARE_GREAT_COMMON_DIVISOR_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class GreatCommonDivisor : public Function {
class GreatCommonDivisor : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
GreatCommonDivisor();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "gcd");
}
};
}

View File

@@ -0,0 +1,21 @@
#ifndef POINCARE_HIERARCHY_H
#define POINCARE_HIERARCHY_H
#include <poincare/expression.h>
namespace Poincare {
class Hierarchy : public Expression {
public:
Hierarchy(int numberOfOperands);
void swapOperands(int i, int j);
void sort() override;
protected:
int m_numberOfOperands;
private:
virtual Expression ** operands() = 0;
};
}
#endif

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_HYPERBOLIC_ARC_COSINE_H
#define POINCARE_HYPERBOLIC_ARC_COSINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicArcCosine : public Function {
class HyperbolicArcCosine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicArcCosine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "acosh");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_HYPERBOLIC_ARC_SINE_H
#define POINCARE_HYPERBOLIC_ARC_SINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicArcSine : public Function {
class HyperbolicArcSine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicArcSine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "asinh");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_HYPERBOLIC_ARC_TANGENT_H
#define POINCARE_HYPERBOLIC_ARC_TANGENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicArcTangent : public Function {
class HyperbolicArcTangent : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicArcTangent();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "atanh");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,23 +1,28 @@
#ifndef POINCARE_HYPERBOLIC_COSINE_H
#define POINCARE_HYPERBOLIC_COSINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicCosine : public Function {
class HyperbolicCosine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicCosine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "cosh");
}
};

View File

@@ -1,23 +1,28 @@
#ifndef POINCARE_HYPERBOLIC_SINE_H
#define POINCARE_HYPERBOLIC_SINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicSine : public Function {
class HyperbolicSine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicSine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "sinh");
}
};

View File

@@ -1,23 +1,28 @@
#ifndef POINCARE_HYPERBOLIC_TANGENT_H
#define POINCARE_HYPERBOLIC_TANGENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class HyperbolicTangent : public Function {
class HyperbolicTangent : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
HyperbolicTangent();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return compute(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "tanh");
}
};

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_IMAGINARY_PART_H
#define POINCARE_IMAGINARY_PART_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ImaginaryPart : public Function {
class ImaginaryPart : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ImaginaryPart();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "im");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,7 +1,7 @@
#ifndef POINCARE_INTEGER_H
#define POINCARE_INTEGER_H
#include <poincare/leaf_expression.h>
#include <poincare/static_hierarchy.h>
#include <stdint.h>
typedef int32_t native_int_t;
@@ -10,11 +10,10 @@ typedef uint64_t double_native_uint_t;
namespace Poincare {
class Integer : public LeafExpression {
class Integer : public StaticHierarchy<0> {
public:
Integer(native_int_t i);
Integer(const char * digits, bool negative = false); // Digits are NOT NULL-terminated
Type type() const override;
~Integer();
Integer(Integer&& other); // C++11 move constructor
@@ -31,10 +30,12 @@ public:
bool operator<(const Integer &other) const;
bool operator==(const Integer &other) const;
/* Expression */
Type type() const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
bool valueEquals(const Expression * e) const override;
bool valueGreaterThan(const Expression * e) const override;
int nodeComparesTo(const Expression * e) const override;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override;
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override;

View File

@@ -1,17 +1,17 @@
#ifndef POINCARE_INTEGRAL_H
#define POINCARE_INTEGRAL_H
#include <poincare/function.h>
#include <poincare/static_hierarchy.h>
#include <poincare/variable_context.h>
namespace Poincare {
class Integral : public Function {
class Integral : public StaticHierarchy<3> {
using StaticHierarchy<3>::StaticHierarchy;
public:
Integral();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }

View File

@@ -0,0 +1,16 @@
#ifndef POINCARE_LAYOUT_ENGINE_H
#define POINCARE_LAYOUT_ENGINE_H
#include <poincare/expression.h>
namespace Poincare {
class LayoutEngine {
public:
static ExpressionLayout * createInfixLayout(const Expression * expression, Expression::FloatDisplayMode floatDisplayMode, Expression::ComplexFormat complexFormat, const char * operatorName);
static ExpressionLayout * createPrefixLayout(const Expression * expression, Expression::FloatDisplayMode floatDisplayMode, Expression::ComplexFormat complexFormat, const char * operatorName);
};
}
#endif

View File

@@ -1,25 +0,0 @@
#ifndef POINCARE_LEAF_EXPRESSION_H
#define POINCARE_LEAF_EXPRESSION_H
#include <poincare/expression.h>
namespace Poincare {
class LeafExpression : public Expression {
public:
bool hasValidNumberOfArguments() const override;
const Expression * operand(int i) const override;
int numberOfOperands() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
void sort() override;
private:
bool nodeEquals(const Expression * e) const override;
virtual bool valueEquals(const Expression * e) const = 0;
bool nodeGreaterThan(const Expression * e) const override;
virtual bool valueGreaterThan(const Expression * e) const = 0;
};
}
#endif

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_LEAST_COMMON_MULTIPLE_H
#define POINCARE_LEAST_COMMON_MULTIPLE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class LeastCommonMultiple : public Function {
class LeastCommonMultiple : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
LeastCommonMultiple();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "lcm");
}
};
}

View File

@@ -1,29 +1,25 @@
#ifndef POINCARE_LOGARITHM_H
#define POINCARE_LOGARITHM_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/bounded_static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Logarithm : public Function {
class Logarithm : public BoundedStaticHierarchy<2> {
using BoundedStaticHierarchy<2>::BoundedStaticHierarchy;
public:
Logarithm();
bool hasValidNumberOfArguments() const override;
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,20 +1,15 @@
#ifndef POINCARE_MATRIX_H
#define POINCARE_MATRIX_H
#include <poincare/expression.h>
#include <poincare/matrix_data.h>
namespace Poincare {
class Matrix : public Expression {
public:
virtual const Expression * operand(int i) const override = 0;
int numberOfOperands() const override;
virtual int numberOfRows() const = 0;
virtual int numberOfColumns() const = 0;
/* If the buffer is too small, the function fills the buffer until reaching
* buffer size */
int writeTextInBuffer(char * buffer, int bufferSize) const override;
private:
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};

View File

@@ -1,20 +1,26 @@
#ifndef POINCARE_MATRIX_DIMENSION_H
#define POINCARE_MATRIX_DIMENSION_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class MatrixDimension : public Function {
class MatrixDimension : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
MatrixDimension();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "dimension");
}
};
}

View File

@@ -1,20 +1,26 @@
#ifndef POINCARE_MATRIX_INVERSE_H
#define POINCARE_MATRIX_INVERSE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class MatrixInverse : public Function {
class MatrixInverse : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
MatrixInverse();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "inverse");
}
};
}

View File

@@ -1,20 +1,26 @@
#ifndef POINCARE_MATRIX_TRACE_H
#define POINCARE_MATRIX_TRACE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class MatrixTrace : public Function {
class MatrixTrace : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
MatrixTrace();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "trace");
}
};
}

View File

@@ -1,20 +1,26 @@
#ifndef POINCARE_MATRIX_TRANSPOSE_H
#define POINCARE_MATRIX_TRANSPOSE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class MatrixTranspose : public Function {
class MatrixTranspose : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
MatrixTranspose();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "transpose");
}
};
}

View File

@@ -1,34 +1,35 @@
#ifndef POINCARE_MULTIPLICATION_H
#define POINCARE_MULTIPLICATION_H
#include <poincare/commutative_operation.h>
#include <poincare/dynamic_hierarchy.h>
#include <poincare/layout_engine.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Multiplication : public CommutativeOperation {
using CommutativeOperation::CommutativeOperation;
class Multiplication : public DynamicHierarchy {
using DynamicHierarchy::DynamicHierarchy;
public:
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n);
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * m);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * m) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n);
private:
char operatorChar() const override;
Evaluation<float> * computeOnComplexMatrices(Evaluation<float> * m, Evaluation<float> * n) const override {
return computeOnMatrices(m, n);
template<typename T> static Evaluation<T> * computeOnMatrixAndComplex(Evaluation<T> * m, const Complex<T> * c) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
Evaluation<double> * computeOnComplexMatrices(Evaluation<double> * m, Evaluation<double> * n) const override {
return computeOnMatrices(m, n);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<float>(this, context, angleUnit, compute<float>, computeOnComplexAndMatrix<float>, computeOnMatrixAndComplex<float>, computeOnMatrices<float>);
}
Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const override {
return compute(c, d);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<double>(this, context, angleUnit, compute<double>, computeOnComplexAndMatrix<double>, computeOnMatrixAndComplex<double>, computeOnMatrices<double>);
}
Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const override {
return compute(c, d);
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createInfixLayout(this, floatDisplayMode, complexFormat, "*");
}
};

View File

@@ -1,64 +0,0 @@
#ifndef POINCARE_N_ARY_OPERATION_H
#define POINCARE_N_ARY_OPERATION_H
#include <poincare/expression.h>
#include <poincare/matrix.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class NAryOperation : public Expression {
public:
NAryOperation();
NAryOperation(Expression ** operands, int numberOfOperands, bool cloneOperands = true);
~NAryOperation();
NAryOperation(const NAryOperation& other) = delete;
NAryOperation(NAryOperation&& other) = delete;
NAryOperation& operator=(const NAryOperation& other) = delete;
NAryOperation& operator=(NAryOperation&& other) = delete;
bool hasValidNumberOfArguments() const override;
const Expression * operand(int i) const override;
int numberOfOperands() const override;
Expression * clone() const override;
protected:
Expression ** m_operands;
int m_numberOfOperands;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
virtual Evaluation<float> * computeOnComplexAndComplexMatrix(const Complex<float> * c, Evaluation<float> * n) const {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
virtual Evaluation<double> * computeOnComplexAndComplexMatrix(const Complex<double> * c, Evaluation<double> * n) const {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * n) const;
virtual Evaluation<float> * computeOnComplexMatrixAndComplex(Evaluation<float> * m, const Complex<float> * d) const {
return templatedComputeOnComplexMatrixAndComplex(m, d);
}
virtual Evaluation<double> * computeOnComplexMatrixAndComplex(Evaluation<double> * m, const Complex<double> * d) const {
return templatedComputeOnComplexMatrixAndComplex(m, d);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexMatrixAndComplex(Evaluation<T> * m, const Complex<T> * d) const;
virtual Evaluation<float> * computeOnComplexMatrices(Evaluation<float> * m, Evaluation<float> * n) const {
return templatedComputeOnComplexMatrices(m, n);
}
virtual Evaluation<double> * computeOnComplexMatrices(Evaluation<double> * m, Evaluation<double> * n) const {
return templatedComputeOnComplexMatrices(m, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexMatrices(Evaluation<T> * m, Evaluation<T> * n) const;
virtual Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const = 0;
virtual Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const = 0;
private:
virtual char operatorChar() const;
};
}
#endif

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_NAPERIAN_LOGARITHM_H
#define POINCARE_NAPERIAN_LOGARITHM_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class NaperianLogarithm : public Function {
class NaperianLogarithm : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
NaperianLogarithm();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "ln");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,22 +1,23 @@
#ifndef POINCARE_NTH_ROOT_H
#define POINCARE_NTH_ROOT_H
#include <poincare/function.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
namespace Poincare {
class NthRoot : public Function {
class NthRoot : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
NthRoot();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
template<typename T> Complex<T> compute(const Complex<T> c, const Complex<T> d) const;
};
}

View File

@@ -1,34 +1,27 @@
#ifndef POINCARE_OPPOSITE_H
#define POINCARE_OPPOSITE_H
#include <poincare/expression.h>
#include <poincare/matrix.h>
#include <poincare/static_hierarchy.h>
#include <poincare/layout_engine.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Opposite : public Expression {
class Opposite : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Opposite(Expression * operand, bool cloneOperands = true);
~Opposite();
Opposite(const Opposite& other) = delete;
Opposite(Opposite&& other) = delete;
Opposite& operator=(const Opposite& other) = delete;
Opposite& operator=(Opposite&& other) = delete;
bool hasValidNumberOfArguments() const override;
const Expression * operand(int i) const override;
int numberOfOperands() const override;
Expression * clone() const override;
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c);
template<typename T> static Evaluation<T> * computeOnMatrix(Evaluation<T> * m);
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, AngleUnit angleUnit);
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit, compute<float>);
}
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, compute<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Expression * m_operand;
};
}

View File

@@ -1,25 +1,17 @@
#ifndef POINCARE_PARENTHESIS_H
#define POINCARE_PARENTHESIS_H
#include <poincare/expression.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class Parenthesis : public Expression {
class Parenthesis : public StaticHierarchy<1> {
public:
using StaticHierarchy<1>::StaticHierarchy;
public:
Parenthesis(Expression * operand, bool cloneOperands = true);
~Parenthesis();
Parenthesis(const Parenthesis& other) = delete;
Parenthesis(Parenthesis&& other) = delete;
Parenthesis& operator=(const Parenthesis& other) = delete;
Parenthesis& operator=(Parenthesis&& other) = delete;
bool hasValidNumberOfArguments() const override;
const Expression * operand(int i) const override;
int numberOfOperands() const override;
Expression * clone() const override;
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
bool isCommutative() const override;
private:
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_PERMUTE_COEFFICIENT_H
#define POINCARE_PERMUTE_COEFFICIENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class PermuteCoefficient : public Function {
class PermuteCoefficient : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
PermuteCoefficient();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "permute");
}
};
}

View File

@@ -1,49 +1,32 @@
#ifndef POINCARE_POWER_H
#define POINCARE_POWER_H
#include <poincare/n_ary_operation.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Power : public NAryOperation {
using NAryOperation::NAryOperation;
class Power : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
private:
constexpr static float k_maxNumberOfSteps = 10000.0f;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const override {
return compute(c, d);
}
Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const override {
return compute(c, d);
}
Evaluation<float> * computeOnComplexAndComplexMatrix(const Complex<float> * c, Evaluation<float> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
Evaluation<double> * computeOnComplexAndComplexMatrix(const Complex<double> * c, Evaluation<double> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * n) const;
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * n);
template<typename T> static Evaluation<T> * computeOnMatrixAndComplex(Evaluation<T> * m, const Complex<T> * d);
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n);
Evaluation<float> * computeOnComplexMatrixAndComplex(Evaluation<float> * m, const Complex<float> * d) const override {
return templatedComputeOnComplexMatrixAndComplex(m, d);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<float>(this, context, angleUnit, compute<float>, computeOnComplexAndMatrix<float>, computeOnMatrixAndComplex<float>, computeOnMatrices<float>);
}
Evaluation<double> * computeOnComplexMatrixAndComplex(Evaluation<double> * m, const Complex<double> * d) const override {
return templatedComputeOnComplexMatrixAndComplex(m, d);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<double>(this, context, angleUnit, compute<double>, computeOnComplexAndMatrix<double>, computeOnMatrixAndComplex<double>, computeOnMatrices<double>);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexMatrixAndComplex(Evaluation<T> * m, const Complex<T> * d) const;
Evaluation<float> * computeOnComplexMatrices(Evaluation<float> * m, Evaluation<float> * n) const override {
return templatedComputeOnComplexMatrices(m, n);
}
Evaluation<double> * computeOnComplexMatrices(Evaluation<double> * m, Evaluation<double> * n) const override {
return templatedComputeOnComplexMatrices(m, n);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexMatrices(Evaluation<T> * m, Evaluation<T> * n) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
};
}

View File

@@ -1,20 +1,24 @@
#ifndef POINCARE_PREDICTION_INTERVAL_H
#define POINCARE_PREDICTION_INTERVAL_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class PredictionInterval : public Function {
class PredictionInterval : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
PredictionInterval();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "prediction95");
}
};
}

View File

@@ -6,11 +6,11 @@
namespace Poincare {
class Product : public Sequence {
using Sequence::Sequence;
public:
Product();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
int emptySequenceValue() const override;
ExpressionLayout * createSequenceLayoutWithArgumentLayouts(ExpressionLayout * subscriptLayout, ExpressionLayout * superscriptLayout, ExpressionLayout * argumentLayout) const override;

View File

@@ -1,24 +1,29 @@
#ifndef POINCARE_REEL_PART_H
#define POINCARE_REEL_PART_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class ReelPart : public Function {
class ReelPart : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
ReelPart();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "re");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -1,20 +1,26 @@
#ifndef POINCARE_ROUND_H
#define POINCARE_ROUND_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/complex.h>
#include <poincare/complex_matrix.h>
namespace Poincare {
class Round : public Function {
class Round : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
Round();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "round");
}
};
}

View File

@@ -1,13 +1,14 @@
#ifndef POINCARE_SEQUENCE_H
#define POINCARE_SEQUENCE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Sequence : public Function {
public:
Sequence(const char * name);
class Sequence : public StaticHierarchy<3> {
using StaticHierarchy<3>::StaticHierarchy;
private:
constexpr static float k_maxNumberOfSteps = 10000.0f;
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;

View File

@@ -1,23 +1,28 @@
#ifndef POINCARE_SINE_H
#define POINCARE_SINE_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Sine : public Function {
class Sine : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Sine();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
template<typename T> static Complex<T> compute(const Complex<T> c, AngleUnit angleUnit = AngleUnit::Radian);
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit = AngleUnit::Radian);
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return compute(c, angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return compute(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "sin");
}
};

View File

@@ -1,25 +1,27 @@
#ifndef POINCARE_SQUARE_ROOT_H
#define POINCARE_SQUARE_ROOT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class SquareRoot : public Function {
class SquareRoot : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
SquareRoot();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c);
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c) const;
};
}

View File

@@ -0,0 +1,31 @@
#ifndef POINCARE_STATIC_HIERARCHY_H
#define POINCARE_STATIC_HIERARCHY_H
#include <poincare/hierarchy.h>
#include <poincare/list_data.h>
namespace Poincare {
template<int T>
class StaticHierarchy : public Hierarchy {
public:
StaticHierarchy();
StaticHierarchy(Expression * const * operands, bool cloneOperands = true);
~StaticHierarchy();
StaticHierarchy(const StaticHierarchy& other) = delete;
StaticHierarchy(StaticHierarchy&& other) = delete;
StaticHierarchy& operator=(const StaticHierarchy& other) = delete;
StaticHierarchy& operator=(StaticHierarchy&& other) = delete;
virtual void setArgument(ListData * listData, int numberOfEntries, bool clone);
int numberOfOperands() const override;
const Expression * operand(int i) const override;
bool hasValidNumberOfArguments() const override;
protected:
void build(Expression * const * operands, int numberOfOperands, bool cloneOperands);
Expression ** operands() override;
Expression * m_operands[T];
};
}
#endif

View File

@@ -14,13 +14,11 @@ public:
Store(Store&& other) = delete;
Store& operator=(const Store& other) = delete;
Store& operator=(Store&& other) = delete;
bool hasValidNumberOfArguments() const override;
Type type() const override;
Expression * clone() const override;
bool isCommutative() const override;
const Expression * operand(int i) const override;
int numberOfOperands() const override;
Expression * clone() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
private:
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override;
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }

View File

@@ -1,33 +1,37 @@
#ifndef POINCARE_SUBSTRACTION_H
#define POINCARE_SUBSTRACTION_H
#include <poincare/n_ary_operation.h>
#include <poincare/static_hierarchy.h>
#include <poincare/layout_engine.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Subtraction : public NAryOperation {
using NAryOperation::NAryOperation;
class Subtraction : public StaticHierarchy<2> {
using StaticHierarchy<2>::StaticHierarchy;
public:
Type type() const override;
Expression * cloneWithDifferentOperands(Expression** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
template<typename T> static Complex<T> compute(const Complex<T> c, const Complex<T> d);
private:
char operatorChar() const override;
template<typename T> static Evaluation<T> * computeOnMatrixAndComplex(Evaluation<T> * m, const Complex<T> * c) {
return EvaluationEngine::elementWiseOnComplexAndComplexMatrix(c, m, compute<T>);
}
template<typename T> static Evaluation<T> * computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * n);
template<typename T> static Evaluation<T> * computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n) {
return EvaluationEngine::elementWiseOnComplexMatrices(m, n, compute<T>);
}
Evaluation<float> * computeOnComplexAndComplexMatrix(const Complex<float> * c, Evaluation<float> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<float>(this, context, angleUnit, compute<float>, computeOnComplexAndMatrix<float>, computeOnMatrixAndComplex<float>, computeOnMatrices<float>);
}
Evaluation<double> * computeOnComplexAndComplexMatrix(const Complex<double> * c, Evaluation<double> * n) const override {
return templatedComputeOnComplexAndComplexMatrix(c, n);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::mapReduce<double>(this, context, angleUnit, compute<double>, computeOnComplexAndMatrix<double>, computeOnMatrixAndComplex<double>, computeOnMatrices<double>);
}
template<typename T> Evaluation<T> * templatedComputeOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * n) const;
Complex<float> privateCompute(const Complex<float> c, const Complex<float> d) const override {
return compute(c, d);
}
Complex<double> privateCompute(const Complex<double> c, const Complex<double> d) const override {
return compute(c, d);
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createInfixLayout(this, floatDisplayMode, complexFormat, "-");
}
};

View File

@@ -6,11 +6,11 @@
namespace Poincare {
class Sum : public Sequence {
using Sequence::Sequence;
public:
Sum();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numberOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
int emptySequenceValue() const override;
ExpressionLayout * createSequenceLayoutWithArgumentLayouts(ExpressionLayout * subscriptLayout, ExpressionLayout * superscriptLayout, ExpressionLayout * argumentLayout) const override;

View File

@@ -1,11 +1,11 @@
#ifndef POINCARE_SYMBOL_H
#define POINCARE_SYMBOL_H
#include <poincare/leaf_expression.h>
#include <poincare/static_hierarchy.h>
namespace Poincare {
class Symbol : public LeafExpression {
class Symbol : public StaticHierarchy<0> {
public:
enum SpecialSymbols : char {
/* We can use characters from 1 to 31 as they do not correspond to usual
@@ -30,13 +30,14 @@ public:
};
static SpecialSymbols matrixSymbol(char index);
Symbol(char name);
Type type() const override;
Symbol(Symbol&& other); // C++11 move constructor
char name() const;
Type type() const override;
Expression * clone() const override;
bool isMatrixSymbol() const;
bool isCommutative() const override;
private:
bool valueEquals(const Expression * e) const override;
bool valueGreaterThan(const Expression * e) const override;
int nodeComparesTo(const Expression * e) const override;
Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<float>(context, angleUnit); }
Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override { return templatedEvaluate<double>(context, angleUnit); }
template<typename T> Evaluation<T> * templatedEvaluate(Context& context, AngleUnit angleUnit) const;

View File

@@ -1,24 +1,30 @@
#ifndef POINCARE_TANGENT_H
#define POINCARE_TANGENT_H
#include <poincare/function.h>
#include <poincare/layout_engine.h>
#include <poincare/static_hierarchy.h>
#include <poincare/evaluation_engine.h>
namespace Poincare {
class Tangent : public Function {
class Tangent : public StaticHierarchy<1> {
using StaticHierarchy<1>::StaticHierarchy;
public:
Tangent();
Type type() const override;
Expression * cloneWithDifferentOperands(Expression ** newOperands,
int numnerOfOperands, bool cloneOperands = true) const override;
Expression * clone() const override;
bool isCommutative() const override;
private:
Complex<float> computeComplex(const Complex<float> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
template<typename T> static Complex<T> computeOnComplex(const Complex<T> c, AngleUnit angleUnit = AngleUnit::Radian);
virtual Evaluation<float> * privateEvaluate(SinglePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<float>(this, context, angleUnit,computeOnComplex<float>);
}
Complex<double> computeComplex(const Complex<double> c, AngleUnit angleUnit) const override {
return templatedComputeComplex(c, angleUnit);
virtual Evaluation<double> * privateEvaluate(DoublePrecision p, Context& context, AngleUnit angleUnit) const override {
return EvaluationEngine::map<double>(this, context, angleUnit, computeOnComplex<double>);
}
ExpressionLayout * privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const override {
return LayoutEngine::createPrefixLayout(this, floatDisplayMode, complexFormat, "tan");
}
template<typename T> Complex<T> templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const;
};
}

View File

@@ -9,32 +9,28 @@ extern "C" {
namespace Poincare {
AbsoluteValue::AbsoluteValue() :
Function("abs")
{
}
Expression::Type AbsoluteValue::type() const {
return Type::AbsoluteValue;
}
Expression * AbsoluteValue::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
AbsoluteValue * a = new AbsoluteValue();
a->setArgument(newOperands, numberOfOperands, cloneOperands);
Expression * AbsoluteValue::clone() const {
AbsoluteValue * a = new AbsoluteValue(m_operands, true);
return a;
}
bool AbsoluteValue::isCommutative() const {
return false;
}
template<typename T>
Complex<T> AbsoluteValue::templatedComputeComplex(const Complex<T> c) const {
Complex<T> AbsoluteValue::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
return Complex<T>::Float(c.r());
}
ExpressionLayout * AbsoluteValue::privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const {
assert(floatDisplayMode != FloatDisplayMode::Default);
assert(complexFormat != ComplexFormat::Default);
return new AbsoluteValueLayout(m_args[0]->createLayout(floatDisplayMode, complexFormat));
return new AbsoluteValueLayout(operand(0)->createLayout(floatDisplayMode, complexFormat));
}
}

View File

@@ -4,9 +4,6 @@ extern "C" {
#include <assert.h>
#include <stdlib.h>
}
#include "layout/horizontal_layout.h"
#include "layout/string_layout.h"
#include "layout/parenthesis_layout.h"
namespace Poincare {
@@ -14,32 +11,19 @@ Expression::Type Addition::type() const {
return Type::Addition;
}
Expression * Addition::clone() const {
return new Addition(m_operands, m_numberOfOperands, true);
}
bool Addition::isCommutative() const {
return true;
}
template<typename T>
Complex<T> Addition::compute(const Complex<T> c, const Complex<T> d) {
return Complex<T>::Cartesian(c.a()+d.a(), c.b()+d.b());
}
template<typename T>
Evaluation<T> * Addition::computeOnMatrices(Evaluation<T> * m, Evaluation<T> * n) {
Addition a;
return a.computeOnComplexMatrices(m,n);
}
template<typename T>
Evaluation<T> * Addition::computeOnComplexAndMatrix(const Complex<T> * c, Evaluation<T> * m) {
Addition a;
return a.computeOnComplexAndComplexMatrix(c,m);
}
Expression * Addition::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
return new Addition(newOperands, numberOfOperands, cloneOperands);
}
char Addition::operatorChar() const {
return '+';
}
template Poincare::Complex<float> Poincare::Addition::compute<float>(Poincare::Complex<float>, Poincare::Complex<float>);
template Poincare::Complex<double> Poincare::Addition::compute<double>(Poincare::Complex<double>, Poincare::Complex<double>);

View File

@@ -6,25 +6,21 @@ extern "C" {
namespace Poincare {
ArcCosine::ArcCosine() :
Function("acos")
{
}
Expression::Type ArcCosine::type() const {
return Type::ArcCosine;
}
Expression * ArcCosine::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
ArcCosine * c = new ArcCosine();
c->setArgument(newOperands, numberOfOperands, cloneOperands);
return c;
Expression * ArcCosine::clone() const {
ArcCosine * a = new ArcCosine(m_operands, true);
return a;
}
bool ArcCosine::isCommutative() const {
return false;
}
template<typename T>
Complex<T> ArcCosine::templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const {
Complex<T> ArcCosine::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
assert(angleUnit != AngleUnit::Default);
if (c.b() != 0) {
return Complex<T>::Float(NAN);

View File

@@ -6,25 +6,21 @@ extern "C" {
namespace Poincare {
ArcSine::ArcSine() :
Function("asin")
{
}
Expression::Type ArcSine::type() const {
return Type::ArcSine;
}
Expression * ArcSine::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
ArcSine * s = new ArcSine();
s->setArgument(newOperands, numberOfOperands, cloneOperands);
return s;
Expression * ArcSine::clone() const {
ArcSine * a = new ArcSine(m_operands, true);
return a;
}
bool ArcSine::isCommutative() const {
return false;
}
template<typename T>
Complex<T> ArcSine::templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const {
Complex<T> ArcSine::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
assert(angleUnit != AngleUnit::Default);
if (c.b() != 0) {
return Complex<T>::Float(NAN);

View File

@@ -6,25 +6,21 @@ extern "C" {
namespace Poincare {
ArcTangent::ArcTangent() :
Function("atan")
{
}
Expression::Type ArcTangent::type() const {
return Type::ArcTangent;
}
Expression * ArcTangent::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
ArcTangent * t = new ArcTangent();
t->setArgument(newOperands, numberOfOperands, cloneOperands);
return t;
Expression * ArcTangent::clone() const {
ArcTangent * a = new ArcTangent(m_operands, true);
return a;
}
bool ArcTangent::isCommutative() const {
return false;
}
template<typename T>
Complex<T> ArcTangent::templatedComputeComplex(const Complex<T> c, AngleUnit angleUnit) const {
Complex<T> ArcTangent::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
assert(angleUnit != AngleUnit::Default);
if (c.b() != 0) {
return Complex<T>::Float(NAN);

View File

@@ -12,27 +12,23 @@ extern "C" {
namespace Poincare {
BinomialCoefficient::BinomialCoefficient() :
Function("binomial", 2)
{
}
Expression::Type BinomialCoefficient::type() const {
return Type::BinomialCoefficient;
}
Expression * BinomialCoefficient::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
BinomialCoefficient * bc = new BinomialCoefficient();
bc->setArgument(newOperands, numberOfOperands, cloneOperands);
return bc;
Expression * BinomialCoefficient::clone() const {
BinomialCoefficient * b = new BinomialCoefficient(m_operands, true);
return b;
}
bool BinomialCoefficient::isCommutative() const {
return false;
}
template<typename T>
Evaluation<T> * BinomialCoefficient::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Evaluation<T> * nInput = m_args[0]->evaluate<T>(context, angleUnit);
Evaluation<T> * kInput = m_args[1]->evaluate<T>(context, angleUnit);
Evaluation<T> * nInput = operand(0)->evaluate<T>(context, angleUnit);
Evaluation<T> * kInput = operand(1)->evaluate<T>(context, angleUnit);
T n = nInput->toScalar();
T k = kInput->toScalar();
delete nInput;
@@ -51,8 +47,8 @@ ExpressionLayout * BinomialCoefficient::privateCreateLayout(FloatDisplayMode flo
assert(floatDisplayMode != FloatDisplayMode::Default);
assert(complexFormat != ComplexFormat::Default);
ExpressionLayout * childrenLayouts[2];
childrenLayouts[0] = m_args[0]->createLayout(floatDisplayMode, complexFormat);
childrenLayouts[1] = m_args[1]->createLayout(floatDisplayMode, complexFormat);
childrenLayouts[0] = operand(0)->createLayout(floatDisplayMode, complexFormat);
childrenLayouts[1] = operand(1)->createLayout(floatDisplayMode, complexFormat);
return new ParenthesisLayout(new GridLayout(childrenLayouts, 2, 1));
}

View File

@@ -0,0 +1,31 @@
#include <poincare/bounded_static_hierarchy.h>
extern "C" {
#include <assert.h>
}
namespace Poincare {
template<int T>
BoundedStaticHierarchy<T>::BoundedStaticHierarchy() :
StaticHierarchy<T>()
{
}
template<int T>
BoundedStaticHierarchy<T>::BoundedStaticHierarchy(Expression * const * operands, int numberOfOperands, bool cloneOperands)
{
StaticHierarchy<T>::m_numberOfOperands = numberOfOperands;
StaticHierarchy<T>::build(operands, numberOfOperands, cloneOperands);
}
template<int T>
bool BoundedStaticHierarchy<T>::hasValidNumberOfArguments() const {
if (StaticHierarchy<T>::m_numberOfOperands <= 0 || StaticHierarchy<T>::m_numberOfOperands > T) {
return false;
}
return Hierarchy::hasValidNumberOfArguments();
}
template class Poincare::BoundedStaticHierarchy<2>;
}

View File

@@ -7,25 +7,21 @@ extern "C" {
namespace Poincare {
Ceiling::Ceiling() :
Function("ceil")
{
}
Expression::Type Ceiling::type() const {
return Type::Ceiling;
}
Expression * Ceiling::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
Ceiling * c = new Ceiling();
c->setArgument(newOperands, numberOfOperands, cloneOperands);
Expression * Ceiling::clone() const {
Ceiling * c = new Ceiling(m_operands, true);
return c;
}
bool Ceiling::isCommutative() const {
return false;
}
template<typename T>
Complex<T> Ceiling::templatedComputeComplex(const Complex<T> c) const {
Complex<T> Ceiling::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
if (c.b() != 0) {
return Complex<T>::Float(NAN);
}

View File

@@ -1,28 +0,0 @@
#include <poincare/commutative_operation.h>
namespace Poincare {
void CommutativeOperation::sort() {
// First, sort every child
for (int i = 0; i < m_numberOfOperands; i++) {
m_operands[i]->sort();
}
// Second, sort all children together
// TODO: use a heap sort instead of a buble sort
for (int i = m_numberOfOperands-1; i > 0; i--) {
bool isSorted = true;
for (int j = 0; j < m_numberOfOperands-1; j++) {
if (m_operands[j]->isGreaterThan(m_operands[j+1])) {
Expression * temp = m_operands[j];
m_operands[j] = m_operands[j+1];
m_operands[j+1] = temp;
isSorted = false;
}
}
if (isSorted) {
return;
}
}
}
}

View File

@@ -105,50 +105,6 @@ Complex<T>::Complex(const char * integralPart, int integralPartLength, bool inte
m_b = 0;
}
template<typename T>
T Complex<T>::toScalar() const {
if (m_b != 0) {
return NAN;
}
return m_a;
}
template<typename T>
int Complex<T>::numberOfRows() const {
return 1;
}
template<typename T>
int Complex<T>::numberOfColumns() const {
return 1;
}
template<typename T>
Expression::Type Complex<T>::type() const {
return Expression::Type::Complex;
}
template <class T>
Complex<T> * Complex<T>::clone() const {
return new Complex<T>(*this);
}
template <class T>
Evaluation<T> * Complex<T>::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
return this->clone();
}
template <class T>
int Complex<T>::writeTextInBuffer(char * buffer, int bufferSize) const {
return convertComplexToText(buffer, bufferSize, Preferences::sharedPreferences()->displayMode(), Preferences::sharedPreferences()->complexFormat());
}
template <class T>
Evaluation<T> * Complex<T>::createInverse() const {
return new Complex<T>(Cartesian(1/m_a, -1/m_b));
}
template <class T>
T Complex<T>::a() const {
return m_a;
@@ -185,6 +141,54 @@ Complex<T> Complex<T>::conjugate() const {
return Cartesian(m_a, -m_b);
}
template<typename T>
Expression::Type Complex<T>::type() const {
return Expression::Type::Complex;
}
template <class T>
Complex<T> * Complex<T>::clone() const {
return new Complex<T>(*this);
}
template <class T>
bool Complex<T>::isCommutative() const {
return false;
}
template<typename T>
bool Complex<T>:: hasValidNumberOfArguments() const {
return true;
}
template<typename T>
T Complex<T>::toScalar() const {
if (m_b != 0) {
return NAN;
}
return m_a;
}
template<typename T>
int Complex<T>::numberOfRows() const {
return 1;
}
template<typename T>
int Complex<T>::numberOfColumns() const {
return 1;
}
template <class T>
int Complex<T>::writeTextInBuffer(char * buffer, int bufferSize) const {
return convertComplexToText(buffer, bufferSize, Preferences::sharedPreferences()->displayMode(), Preferences::sharedPreferences()->complexFormat());
}
template <class T>
Evaluation<T> * Complex<T>::createInverse() const {
return new Complex<T>(Cartesian(1/m_a, -1/m_b));
}
template <class T>
int Complex<T>::convertFloatToText(T f, char * buffer, int bufferSize,
int numberOfSignificantDigits, Expression::FloatDisplayMode mode) {

View File

@@ -8,25 +8,21 @@ extern "C" {
namespace Poincare {
ComplexArgument::ComplexArgument() :
Function("arg")
{
}
Expression::Type ComplexArgument::type() const {
return Type::ComplexArgument;
}
Expression * ComplexArgument::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
ComplexArgument * ca = new ComplexArgument();
ca->setArgument(newOperands, numberOfOperands, cloneOperands);
return ca;
Expression * ComplexArgument::clone() const {
ComplexArgument * a = new ComplexArgument(m_operands, true);
return a;
}
bool ComplexArgument::isCommutative() const {
return false;
}
template<typename T>
Complex<T> ComplexArgument::templatedComputeComplex(const Complex<T> c) const {
Complex<T> ComplexArgument::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
return Complex<T>::Float(c.th());
}

View File

@@ -34,6 +34,16 @@ Expression::Type ComplexMatrix<T>::type() const {
return Expression::Type::ComplexMatrix;
}
template<typename T>
ComplexMatrix<T> * ComplexMatrix<T>::clone() const {
return new ComplexMatrix<T>(m_values, m_numberOfRows, m_numberOfColumns);
}
template<typename T>
bool ComplexMatrix<T>::isCommutative() const {
return false;
}
template<typename T>
T ComplexMatrix<T>::toScalar() const {
if (m_numberOfRows != 1 || m_numberOfColumns != 1) {
@@ -61,15 +71,50 @@ const Complex<T> * ComplexMatrix<T>::complexOperand(int i) const {
}
template<typename T>
ComplexMatrix<T> * ComplexMatrix<T>::clone() const {
return new ComplexMatrix<T>(m_values, m_numberOfRows, m_numberOfColumns);
}
template<typename T>
ComplexMatrix<T> * ComplexMatrix<T>::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
return new ComplexMatrix((Complex<T> *)newOperands[0], m_numberOfRows, m_numberOfColumns);
int ComplexMatrix<T>::writeTextInBuffer(char * buffer, int bufferSize) const {
buffer[bufferSize-1] = 0;
int currentChar = 0;
if (currentChar >= bufferSize) {
return 0;
}
buffer[currentChar++] = '[';
if (currentChar >= bufferSize) {
return currentChar;
}
for (int i = 0; i < numberOfRows(); i++) {
buffer[currentChar++] = '[';
if (currentChar >= bufferSize) {
return currentChar;
}
currentChar += complexOperand(i*numberOfColumns())->writeTextInBuffer(buffer+currentChar, bufferSize-currentChar);
if (currentChar >= bufferSize) {
return currentChar;
}
for (int j = 1; j < numberOfColumns(); j++) {
buffer[currentChar++] = ',';
if (currentChar >= bufferSize) {
return currentChar;
}
currentChar += complexOperand(i*numberOfColumns()+j)->writeTextInBuffer(buffer+currentChar, bufferSize-currentChar);
if (currentChar >= bufferSize) {
return currentChar;
}
}
currentChar = strlen(buffer);
if (currentChar >= bufferSize) {
return currentChar;
}
buffer[currentChar++] = ']';
if (currentChar >= bufferSize) {
return currentChar;
}
}
buffer[currentChar++] = ']';
if (currentChar >= bufferSize) {
return currentChar;
}
buffer[currentChar] = 0;
return currentChar;
}
template<typename T>

View File

@@ -1,6 +1,7 @@
#include <poincare/confidence_interval.h>
#include <poincare/matrix.h>
#include <poincare/evaluation.h>
#include <poincare/complex_matrix.h>
#include <poincare/complex.h>
extern "C" {
#include <assert.h>
}
@@ -8,27 +9,23 @@ extern "C" {
namespace Poincare {
ConfidenceInterval::ConfidenceInterval() :
Function("confidence", 2)
{
}
Expression::Type ConfidenceInterval::type() const {
return Type::ConfidenceInterval;
}
Expression * ConfidenceInterval::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
ConfidenceInterval * ci = new ConfidenceInterval();
ci->setArgument(newOperands, numberOfOperands, cloneOperands);
return ci;
Expression * ConfidenceInterval::clone() const {
ConfidenceInterval * a = new ConfidenceInterval(m_operands, true);
return a;
}
bool ConfidenceInterval::isCommutative() const {
return false;
}
template<typename T>
Evaluation<T> * ConfidenceInterval::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Evaluation<T> * fInput = m_args[0]->evaluate<T>(context, angleUnit);
Evaluation<T> * nInput = m_args[1]->evaluate<T>(context, angleUnit);
Evaluation<T> * fInput = operand(0)->evaluate<T>(context, angleUnit);
Evaluation<T> * nInput = operand(1)->evaluate<T>(context, angleUnit);
T f = fInput->toScalar();
T n = nInput->toScalar();
delete fInput;

View File

@@ -9,32 +9,28 @@ extern "C" {
namespace Poincare {
Conjugate::Conjugate() :
Function("conj")
{
}
Expression::Type Conjugate::type() const {
return Type::Conjugate;
}
Expression * Conjugate::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
Conjugate * c = new Conjugate();
c->setArgument(newOperands, numberOfOperands, cloneOperands);
return c;
Expression * Conjugate::clone() const {
Conjugate * a = new Conjugate(m_operands, true);
return a;
}
bool Conjugate::isCommutative() const {
return false;
}
template<typename T>
Complex<T> Conjugate::templatedComputeComplex(const Complex<T> c) const {
Complex<T> Conjugate::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
return c.conjugate();
}
ExpressionLayout * Conjugate::privateCreateLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const {
assert(floatDisplayMode != FloatDisplayMode::Default);
assert(complexFormat != ComplexFormat::Default);
return new ConjugateLayout(m_args[0]->createLayout(floatDisplayMode, complexFormat));
return new ConjugateLayout(operand(0)->createLayout(floatDisplayMode, complexFormat));
}
}

View File

@@ -8,25 +8,21 @@ extern "C" {
namespace Poincare {
Cosine::Cosine() :
Function("cos")
{
}
Expression::Type Cosine::type() const {
return Type::Cosine;
}
Expression * Cosine::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
Cosine * c = new Cosine();
c->setArgument(newOperands, numberOfOperands, cloneOperands);
return c;
Expression * Cosine::clone() const {
Cosine * a = new Cosine(m_operands, true);
return a;
}
bool Cosine::isCommutative() const {
return false;
}
template<typename T>
Complex<T> Cosine::compute(const Complex<T> c, AngleUnit angleUnit) {
Complex<T> Cosine::computeOnComplex(const Complex<T> c, AngleUnit angleUnit) {
assert(angleUnit != AngleUnit::Default);
if (c.b() == 0) {
T input = c.a();
@@ -47,7 +43,7 @@ Complex<T> Cosine::compute(const Complex<T> c, AngleUnit angleUnit) {
return Complex<T>::Float(result);
}
Complex<T> arg = Complex<T>::Cartesian(-c.b(), c.a());
return HyperbolicCosine::compute(arg);
return HyperbolicCosine::computeOnComplex(arg, angleUnit);
}
}

View File

@@ -9,21 +9,17 @@ extern "C" {
namespace Poincare {
Derivative::Derivative() :
Function("diff", 2)
{
}
Expression::Type Derivative::type() const {
return Type::Derivative;
}
Expression * Derivative::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
Derivative * d = new Derivative();
d->setArgument(newOperands, numberOfOperands, cloneOperands);
return d;
Expression * Derivative::clone() const {
Derivative * a = new Derivative(m_operands, true);
return a;
}
bool Derivative::isCommutative() const {
return false;
}
template<typename T>
@@ -31,13 +27,13 @@ Evaluation<T> * Derivative::templatedEvaluate(Context& context, AngleUnit angleU
static T min = sizeof(T) == sizeof(double) ? DBL_MIN : FLT_MIN;
static T max = sizeof(T) == sizeof(double) ? DBL_MAX : FLT_MAX;
VariableContext<T> xContext = VariableContext<T>('x', &context);
Symbol xSymbol = Symbol('x');
Evaluation<T> * xInput = m_args[1]->evaluate<T>(context, angleUnit);
Symbol xSymbol('x');
Evaluation<T> * xInput = operand(1)->evaluate<T>(context, angleUnit);
T x = xInput->toScalar();
delete xInput;
Complex<T> e = Complex<T>::Float(x);
xContext.setExpressionForSymbolName(&e, &xSymbol);
Evaluation<T> * fInput = m_args[1]->evaluate<T>(xContext, angleUnit);
Evaluation<T> * fInput = operand(1)->evaluate<T>(xContext, angleUnit);
T functionValue = fInput->toScalar();
delete fInput;
@@ -112,15 +108,15 @@ Evaluation<T> * Derivative::templatedEvaluate(Context& context, AngleUnit angleU
template<typename T>
T Derivative::growthRateAroundAbscissa(T x, T h, VariableContext<T> xContext, AngleUnit angleUnit) const {
Symbol xSymbol = Symbol('x');
Symbol xSymbol('x');
Complex<T> e = Complex<T>::Float(x + h);
xContext.setExpressionForSymbolName(&e, &xSymbol);
Evaluation<T> * fInput = m_args[0]->evaluate<T>(xContext, angleUnit);
Evaluation<T> * fInput = operand(0)->evaluate<T>(xContext, angleUnit);
T expressionPlus = fInput->toScalar();
delete fInput;
e = Complex<T>::Float(x-h);
xContext.setExpressionForSymbolName(&e, &xSymbol);
fInput = m_args[0]->evaluate<T>(xContext, angleUnit);
fInput = operand(0)->evaluate<T>(xContext, angleUnit);
T expressionMinus = fInput->toScalar();
delete fInput;
return (expressionPlus - expressionMinus)/(2*h);
@@ -128,20 +124,20 @@ T Derivative::growthRateAroundAbscissa(T x, T h, VariableContext<T> xContext, An
template<typename T>
T Derivative::approximateDerivate2(T x, T h, VariableContext<T> xContext, AngleUnit angleUnit) const {
Symbol xSymbol = Symbol('x');
Symbol xSymbol('x');
Complex<T> e = Complex<T>::Float(x + h);
xContext.setExpressionForSymbolName(&e, &xSymbol);
Evaluation<T> * fInput = m_args[0]->evaluate<T>(xContext, angleUnit);
Evaluation<T> * fInput = operand(0)->evaluate<T>(xContext, angleUnit);
T expressionPlus = fInput->toScalar();
delete fInput;
e = Complex<T>::Float(x);
xContext.setExpressionForSymbolName(&e, &xSymbol);
fInput = m_args[0]->evaluate<T>(xContext, angleUnit);
fInput = operand(0)->evaluate<T>(xContext, angleUnit);
T expression = fInput->toScalar();
delete fInput;
e = Complex<T>::Float(x-h);
xContext.setExpressionForSymbolName(&e, &xSymbol);
fInput = m_args[0]->evaluate<T>(xContext, angleUnit);
fInput = operand(0)->evaluate<T>(xContext, angleUnit);
T expressionMinus = fInput->toScalar();
delete fInput;
return expressionPlus - 2.0*expression + expressionMinus;

View File

@@ -1,5 +1,6 @@
#include <poincare/determinant.h>
#include <poincare/matrix.h>
#include <poincare/evaluation.h>
extern "C" {
#include <assert.h>
}
@@ -7,27 +8,23 @@ extern "C" {
namespace Poincare {
Determinant::Determinant() :
Function("det")
{
}
Expression::Type Determinant::type() const {
return Type::Determinant;
}
Expression * Determinant::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
Determinant * d = new Determinant();
d->setArgument(newOperands, numberOfOperands, cloneOperands);
return d;
Expression * Determinant::clone() const {
Determinant * a = new Determinant(m_operands, true);
return a;
}
bool Determinant::isCommutative() const {
return false;
}
template<typename T>
Evaluation<T> * Determinant::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Evaluation<T> * input = m_args[0]->evaluate<T>(context, angleUnit);
Evaluation<T> * input = operand(0)->evaluate<T>(context, angleUnit);
Evaluation<T> * result = input->createDeterminant();
delete input;
return result;

View File

@@ -1,4 +1,5 @@
#include <poincare/division_quotient.h>
#include <poincare/complex.h>
extern "C" {
#include <assert.h>
@@ -7,27 +8,23 @@ extern "C" {
namespace Poincare {
DivisionQuotient::DivisionQuotient() :
Function("quo", 2)
{
}
Expression::Type DivisionQuotient::type() const {
return Type::DivisionQuotient;
}
Expression * DivisionQuotient::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
DivisionQuotient * dq = new DivisionQuotient();
dq->setArgument(newOperands, numberOfOperands, cloneOperands);
return dq;
Expression * DivisionQuotient::clone() const {
DivisionQuotient * a = new DivisionQuotient(m_operands, true);
return a;
}
bool DivisionQuotient::isCommutative() const {
return false;
}
template<typename T>
Evaluation<T> * DivisionQuotient::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Evaluation<T> * f1Input = m_args[0]->evaluate<T>(context, angleUnit);
Evaluation<T> * f2Input = m_args[1]->evaluate<T>(context, angleUnit);
Evaluation<T> * f1Input = operand(0)->evaluate<T>(context, angleUnit);
Evaluation<T> * f2Input = operand(1)->evaluate<T>(context, angleUnit);
T f1 = f1Input->toScalar();
T f2 = f2Input->toScalar();
delete f1Input;

View File

@@ -1,4 +1,5 @@
#include <poincare/division_remainder.h>
#include <poincare/complex.h>
extern "C" {
#include <assert.h>
@@ -7,27 +8,23 @@ extern "C" {
namespace Poincare {
DivisionRemainder::DivisionRemainder() :
Function("rem", 2)
{
}
Expression::Type DivisionRemainder::type() const {
return Type::DivisionRemainder;
}
Expression * DivisionRemainder::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
DivisionRemainder * dr = new DivisionRemainder();
dr->setArgument(newOperands, numberOfOperands, cloneOperands);
return dr;
Expression * DivisionRemainder::clone() const {
DivisionRemainder * a = new DivisionRemainder(m_operands, true);
return a;
}
bool DivisionRemainder::isCommutative() const {
return false;
}
template<typename T>
Evaluation<T> * DivisionRemainder::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Evaluation<T> * f1Input = m_args[0]->evaluate<T>(context, angleUnit);
Evaluation<T> * f2Input = m_args[1]->evaluate<T>(context, angleUnit);
Evaluation<T> * f1Input = operand(0)->evaluate<T>(context, angleUnit);
Evaluation<T> * f2Input = operand(1)->evaluate<T>(context, angleUnit);
T f1 = f1Input->toScalar();
T f2 = f2Input->toScalar();
delete f1Input;

View File

@@ -0,0 +1,54 @@
#include <poincare/dynamic_hierarchy.h>
extern "C" {
#include <assert.h>
#include <stdlib.h>
}
namespace Poincare {
DynamicHierarchy::DynamicHierarchy() :
Hierarchy(0),
m_operands(nullptr)
{
}
DynamicHierarchy::DynamicHierarchy(Expression ** operands, int numberOfOperands, bool cloneOperands) :
Hierarchy(numberOfOperands)
{
assert(operands != nullptr);
assert(numberOfOperands >= 2);
m_operands = new Expression * [numberOfOperands];
for (int i=0; i<numberOfOperands; i++) {
assert(operands[i] != nullptr);
if (cloneOperands) {
m_operands[i] = operands[i]->clone();
} else {
m_operands[i] = operands[i];
}
}
}
DynamicHierarchy::~DynamicHierarchy() {
if (m_operands != nullptr) {
for (int i = 0; i < m_numberOfOperands; i++) {
delete m_operands[i];
}
}
delete[] m_operands;
}
int DynamicHierarchy::numberOfOperands() const {
return m_numberOfOperands;
}
const Expression * DynamicHierarchy::operand(int i) const {
assert(i >= 0);
assert(i < m_numberOfOperands);
return m_operands[i];
}
Expression ** DynamicHierarchy::operands() {
return m_operands;
}
}

View File

@@ -14,11 +14,6 @@ extern "C" {
namespace Poincare {
template<typename T>
bool Evaluation<T>::hasValidNumberOfArguments() const {
return true;
}
template<typename T>
const Expression * Evaluation<T>::operand(int i) const {
return complexOperand(i);

View File

@@ -0,0 +1,84 @@
#include <poincare/evaluation_engine.h>
#include <poincare/complex_matrix.h>
#include <cmath>
extern "C" {
#include <assert.h>
}
namespace Poincare {
template<typename T> Evaluation<T> * EvaluationEngine::map(const Expression * expression, Context& context, Expression::AngleUnit angleUnit, ExpressionToComplexMap<T> compute) {
assert(expression->numberOfOperands() == 1);
Evaluation<T> * input = expression->operand(0)->evaluate<T>(context, angleUnit);
Complex<T> * operands = new Complex<T>[input->numberOfRows()*input->numberOfColumns()];
for (int i = 0; i < input->numberOfOperands(); i++) {
operands[i] = compute(*input->complexOperand(i), angleUnit);
}
Evaluation<T> * result = nullptr;
if (input->numberOfOperands() == 1) {
result = new Complex<T>(operands[0]);
} else {
result = new ComplexMatrix<T>(operands, input->numberOfRows(), input->numberOfColumns());
}
delete input;
delete[] operands;
return result;
}
template<typename T> Evaluation<T> * EvaluationEngine::mapReduce(const Expression * expression, Context& context, Expression::AngleUnit angleUnit, ComplexAndComplexReduction<T> computeOnComplexes, ComplexAndMatrixReduction<T> computeOnComplexAndMatrix, MatrixAndComplexReduction<T> computeOnMatrixAndComplex, MatrixAndMatrixReduction<T> computeOnMatrices) {
Evaluation<T> * result = expression->operand(0)->evaluate<T>(context, angleUnit);
for (int i = 1; i < expression->numberOfOperands(); i++) {
Evaluation<T> * intermediateResult = nullptr;
Evaluation<T> * nextOperandEvaluation = expression->operand(i)->evaluate<T>(context, angleUnit);
if (result->numberOfRows() == 1 && result->numberOfColumns() == 1 && nextOperandEvaluation->numberOfRows() == 1 && nextOperandEvaluation->numberOfColumns() == 1) {
intermediateResult = new Complex<T>(computeOnComplexes(*(result->complexOperand(0)), *(nextOperandEvaluation->complexOperand(0))));
} else if (result->numberOfRows() == 1 && result->numberOfColumns() == 1) {
intermediateResult = computeOnComplexAndMatrix(result->complexOperand(0), nextOperandEvaluation);
} else if (nextOperandEvaluation->numberOfRows() == 1 && nextOperandEvaluation->numberOfColumns() == 1) {
intermediateResult = computeOnMatrixAndComplex(result, nextOperandEvaluation->complexOperand(0));
} else {
intermediateResult = computeOnMatrices(result, nextOperandEvaluation);
}
delete result;
delete nextOperandEvaluation;
result = intermediateResult;
if (result == nullptr) {
return new Complex<T>(Complex<T>::Float(NAN));
}
}
return result;
}
template<typename T> Evaluation<T> * EvaluationEngine::elementWiseOnComplexAndComplexMatrix(const Complex<T> * c, Evaluation<T> * m, ComplexAndComplexReduction<T> computeOnComplexes) {
Complex<T> * operands = new Complex<T>[m->numberOfRows()*m->numberOfColumns()];
for (int i = 0; i < m->numberOfOperands(); i++) {
operands[i] = computeOnComplexes(*(m->complexOperand(i)), *c);
}
Evaluation<T> * result = new ComplexMatrix<T>(operands, m->numberOfRows(), m->numberOfColumns());
delete[] operands;
return result;
}
template<typename T> Evaluation<T> * EvaluationEngine::elementWiseOnComplexMatrices(Evaluation<T> * m, Evaluation<T> * n, ComplexAndComplexReduction<T> computeOnComplexes) {
if (m->numberOfRows() != n->numberOfRows() && m->numberOfColumns() != n->numberOfColumns()) {
return nullptr;
}
Complex<T> * operands = new Complex<T>[m->numberOfRows()*m->numberOfColumns()];
for (int i = 0; i < m->numberOfOperands(); i++) {
operands[i] = computeOnComplexes(*(m->complexOperand(i)), *(n->complexOperand(i)));
}
Evaluation<T> * result = new ComplexMatrix<T>(operands, m->numberOfRows(), m->numberOfColumns());
delete[] operands;
return result;
}
template Poincare::Evaluation<float> * Poincare::EvaluationEngine::map(const Poincare::Expression * expression, Poincare::Context& context, Poincare::Expression::AngleUnit angleUnit, Poincare::EvaluationEngine::ExpressionToComplexMap<float> compute);
template Poincare::Evaluation<double> * Poincare::EvaluationEngine::map(const Poincare::Expression * expression, Poincare::Context& context, Poincare::Expression::AngleUnit angleUnit, Poincare::EvaluationEngine::ExpressionToComplexMap<double> compute);
template Poincare::Evaluation<float> * Poincare::EvaluationEngine::mapReduce(const Poincare::Expression * expression, Poincare::Context& context, Poincare::Expression::AngleUnit angleUnit, Poincare::EvaluationEngine::ComplexAndComplexReduction<float> computeOnComplexes, Poincare::EvaluationEngine::ComplexAndMatrixReduction<float> computeOnComplexAndMatrix, Poincare::EvaluationEngine::MatrixAndComplexReduction<float> computeOnMatrixAndComplex, Poincare::EvaluationEngine::MatrixAndMatrixReduction<float> computeOnMatrices);
template Poincare::Evaluation<double> * Poincare::EvaluationEngine::mapReduce(const Poincare::Expression * expression, Poincare::Context& context, Poincare::Expression::AngleUnit angleUnit, Poincare::EvaluationEngine::ComplexAndComplexReduction<double> computeOnComplexes, Poincare::EvaluationEngine::ComplexAndMatrixReduction<double> computeOnComplexAndMatrix, Poincare::EvaluationEngine::MatrixAndComplexReduction<double> computeOnMatrixAndComplex, Poincare::EvaluationEngine::MatrixAndMatrixReduction<double> computeOnMatrices);
template Poincare::Evaluation<float>* Poincare::EvaluationEngine::elementWiseOnComplexAndComplexMatrix<float>(Poincare::Complex<float> const*, Poincare::Evaluation<float>*, Poincare::Complex<float> (*)(Poincare::Complex<float>, Poincare::Complex<float>));
template Poincare::Evaluation<double>* Poincare::EvaluationEngine::elementWiseOnComplexAndComplexMatrix<double>(Poincare::Complex<double> const*, Poincare::Evaluation<double>*, Poincare::Complex<double> (*)(Poincare::Complex<double>, Poincare::Complex<double>));
template Poincare::Evaluation<float>* Poincare::EvaluationEngine::elementWiseOnComplexMatrices<float>(Poincare::Evaluation<float>*, Poincare::Evaluation<float>*, Poincare::Complex<float> (*)(Poincare::Complex<float>, Poincare::Complex<float>));
template Poincare::Evaluation<double>* Poincare::EvaluationEngine::elementWiseOnComplexMatrices<double>(Poincare::Evaluation<double>*, Poincare::Evaluation<double>*, Poincare::Complex<double> (*)(Poincare::Complex<double>, Poincare::Complex<double>));
}

View File

@@ -1,7 +1,7 @@
#include <poincare/expression.h>
#include <poincare/preferences.h>
#include <poincare/function.h>
#include <poincare/symbol.h>
#include <poincare/static_hierarchy.h>
#include <poincare/list_data.h>
#include <poincare/matrix_data.h>
#include <poincare/evaluation.h>
@@ -40,6 +40,26 @@ Expression * Expression::parse(char const * string) {
return expression;
}
void Expression::setCircuitBreaker(CircuitBreaker cb) {
sCircuitBreaker = cb;
}
bool Expression::shouldStopProcessing() {
if (sCircuitBreaker == nullptr) {
return false;
}
return sCircuitBreaker();
}
bool Expression::hasValidNumberOfArguments() const {
for (int i = 0; i < numberOfOperands(); i++) {
if (!operand(i)->hasValidNumberOfArguments()) {
return false;
}
}
return true;
}
ExpressionLayout * Expression::createLayout(FloatDisplayMode floatDisplayMode, ComplexFormat complexFormat) const {
switch (floatDisplayMode) {
case FloatDisplayMode::Default:
@@ -59,6 +79,36 @@ ExpressionLayout * Expression::createLayout(FloatDisplayMode floatDisplayMode, C
}
}
void Expression::sort() {
if (this->type() == Type::Complex) {
// TODO: this case should be useless once complex is a leaf expression!
return;
}
for (int i = 0; i < numberOfOperands(); i++) {
((Expression *)operand(i))->sort(); // TODO: implement an editatble operand?
}
}
int Expression::comparesTo(const Expression * e) const {
if (this->nodeComparesTo(e) != 0) {
return this->nodeComparesTo(e);
}
for (int i = 0; i < this->numberOfOperands(); i++) {
// The NULL node is the least node type.
if (e->numberOfOperands() <= i) {
return 1;
}
if (this->operand(i)->comparesTo(e->operand(i)) != 0) {
return this->operand(i)->comparesTo(e->operand(i));
}
}
// The NULL node is the least node type.
if (e->numberOfOperands() > numberOfOperands()) {
return -1;
}
return 0;
}
template<typename T> Evaluation<T> * Expression::evaluate(Context& context, AngleUnit angleUnit) const {
switch (angleUnit) {
case AngleUnit::Default:
@@ -87,11 +137,6 @@ template<typename T> T Expression::approximate(const char * text, Context& conte
return result;
}
template<typename T> T Expression::epsilon() {
static T epsilon = sizeof(T) == sizeof(double) ? 1E-15 : 1E-7f;
return epsilon;
}
/*Expression * Expression::simplify() const {
// pre-process:
// - remonter les noeuds de matrices en root ou les faire disparaitre
@@ -154,66 +199,19 @@ template<typename T> T Expression::epsilon() {
return result;
}*/
bool Expression::isIdenticalTo(const Expression * e) const {
if (!this->nodeEquals(e) || e->numberOfOperands() != this->numberOfOperands()) {
return false;
template<typename T> T Expression::epsilon() {
static T epsilon = sizeof(T) == sizeof(double) ? 1E-15 : 1E-7f;
return epsilon;
}
int Expression::nodeComparesTo(const Expression * e) const {
if (e->type() == this->type()) {
return 0;
}
/* The children must be sorted! */
for (int i = 0; i < this->numberOfOperands(); i++) {
if (!e->operand(i)->isIdenticalTo(this->operand(i))) {
return false;
}
if (e->type() > this->type()) {
return 1;
}
return true;
}
bool Expression::nodeEquals(const Expression * e) const {
return e->type() == this->type();
}
bool Expression::isGreaterThan(const Expression * e) const {
if (!this->nodeEquals(e)) {
return this->nodeGreaterThan(e);
}
for (int i = 0; i < this->numberOfOperands(); i++) {
// The NULL node is the least node type.
if (e->numberOfOperands() <= i) {
return true;
}
if (this->operand(i)->isGreaterThan(e->operand(i))) {
return true;
}
if (!this->operand(i)->isIdenticalTo(e->operand(i))) {
return false;
}
}
// The NULL node is the least node type.
if (e->numberOfOperands() > numberOfOperands()) {
return false;
}
return true;
}
bool Expression::nodeGreaterThan(const Expression * e) const {
return e->type() > this->type();
}
void Expression::sort() {
}
int Expression::writeTextInBuffer(char * buffer, int bufferSize) const {
return 0;
}
void Expression::setCircuitBreaker(CircuitBreaker cb) {
sCircuitBreaker = cb;
}
bool Expression::shouldStopProcessing() const {
if (sCircuitBreaker == nullptr) {
return false;
}
return sCircuitBreaker(this);
return -1;
}
}

View File

@@ -25,15 +25,17 @@ ExpressionMatrix::~ExpressionMatrix() {
delete m_matrixData;
}
bool ExpressionMatrix::hasValidNumberOfArguments() const {
for (int i = 0; i < numberOfOperands(); i++) {
if (!operand(i)->hasValidNumberOfArguments()) {
return false;
}
}
return true;
Expression::Type ExpressionMatrix::type() const {
return Type::ExpressionMatrix;
}
Expression * ExpressionMatrix::clone() const {
return new ExpressionMatrix(m_matrixData->operands(), numberOfOperands(), numberOfRows(), numberOfColumns(), true);
}
bool ExpressionMatrix::isCommutative() const {
return false;
}
int ExpressionMatrix::numberOfRows() const {
return m_matrixData->numberOfRows();
@@ -49,20 +51,6 @@ const Expression * ExpressionMatrix::operand(int i) const {
return m_matrixData->operands()[i];
}
Expression * ExpressionMatrix::clone() const {
return this->cloneWithDifferentOperands(m_matrixData->operands(), numberOfOperands(), true);
}
Expression::Type ExpressionMatrix::type() const {
return Type::ExpressionMatrix;
}
Expression * ExpressionMatrix::cloneWithDifferentOperands(Expression** newOperands,
int numberOfOperands, bool cloneOperands) const {
assert(newOperands != nullptr);
return new ExpressionMatrix(newOperands, numberOfOperands, numberOfRows(), numberOfColumns(), cloneOperands);
}
template<typename T>
Evaluation<T> * ExpressionMatrix::templatedEvaluate(Context& context, AngleUnit angleUnit) const {
Complex<T> * operands = new Complex<T>[numberOfOperands()];

Some files were not shown because too many files have changed in this diff Show More