[poincare] Add ref and rref matrix functions

Change-Id: Id0e57a4f85d551ca5320c4b6e3c0baadae70946d
This commit is contained in:
Hugo Saint-Vignes
2020-06-22 16:46:42 +02:00
committed by Émilie Feral
parent 997c103fba
commit 007c38652f
28 changed files with 349 additions and 13 deletions

View File

@@ -63,6 +63,8 @@ class Expression : public TreeHandle {
friend class MatrixInverse;
friend class MatrixTrace;
friend class MatrixTranspose;
friend class MatrixRef;
friend class MatrixRref;
friend class Multiplication;
friend class MultiplicationNode;
friend class NaperianLogarithm;

View File

@@ -103,6 +103,8 @@ public:
MatrixIdentity,
MatrixInverse,
MatrixTranspose,
MatrixRef,
MatrixRref,
PredictionInterval,
Matrix,
EmptyExpression

View File

@@ -79,6 +79,7 @@ public:
template<typename T> static int ArrayInverse(T * array, int numberOfRows, int numberOfColumns);
static Matrix CreateIdentity(int dim);
Matrix createTranspose() const;
Expression createRef(ExpressionNode::ReductionContext reductionContext, bool * couldComputeRef, bool reduced) const;
/* createInverse can be called on any matrix, reduced or not, approximated or
* not. */
Expression createInverse(ExpressionNode::ReductionContext reductionContext, bool * couldComputeInverse) const;
@@ -94,10 +95,10 @@ private:
void setNumberOfRows(int rows) { assert(rows >= 0); node()->setNumberOfRows(rows); }
void setNumberOfColumns(int columns) { assert(columns >= 0); node()->setNumberOfColumns(columns); }
Expression computeInverseOrDeterminant(bool computeDeterminant, ExpressionNode::ReductionContext reductionContext, bool * couldCompute) const;
// rowCanonize turns a matrix in its reduced row echelon form.
Matrix rowCanonize(ExpressionNode::ReductionContext reductionContext, Expression * determinant);
// rowCanonize turns a matrix in its row echelon form, reduced or not.
Matrix rowCanonize(ExpressionNode::ReductionContext reductionContext, Expression * determinant, bool reduced = true);
// Row canonize the array in place
template<typename T> static void ArrayRowCanonize(T * array, int numberOfRows, int numberOfColumns, T * c = nullptr);
template<typename T> static void ArrayRowCanonize(T * array, int numberOfRows, int numberOfColumns, T * c = nullptr, bool reduced = true);
};

View File

@@ -46,6 +46,7 @@ public:
std::complex<T> determinant() const override;
MatrixComplex<T> inverse() const;
MatrixComplex<T> transpose() const;
MatrixComplex<T> ref(bool reduced) const;
private:
// See comment on Matrix
uint16_t m_numberOfRows;
@@ -63,6 +64,7 @@ public:
static MatrixComplex<T> CreateIdentity(int dim);
MatrixComplex<T> inverse() const { return node()->inverse(); }
MatrixComplex<T> transpose() const { return node()->transpose(); }
MatrixComplex<T> ref(bool reduced) const { return node()->ref(reduced); }
std::complex<T> complexAtIndex(int index) const {
return node()->complexAtIndex(index);
}

View File

@@ -0,0 +1,48 @@
#ifndef POINCARE_MATRIX_REF_H
#define POINCARE_MATRIX_REF_H
#include <poincare/expression.h>
namespace Poincare {
class MatrixRefNode final : public ExpressionNode {
public:
// TreeNode
size_t size() const override { return sizeof(MatrixRefNode); }
int numberOfChildren() const override;
#if POINCARE_TREE_LOG
void logNodeName(std::ostream & stream) const override {
stream << "MatrixRef";
}
#endif
// Properties
Type type() const override { return Type::MatrixRef; }
private:
// Layout
Layout createLayout(Preferences::PrintFloatMode floatDisplayMode, int numberOfSignificantDigits) const override;
int serialize(char * buffer, int bufferSize, Preferences::PrintFloatMode floatDisplayMode, int numberOfSignificantDigits) const override;
// Simplification
Expression shallowReduce(ReductionContext reductionContext) override;
LayoutShape leftLayoutShape() const override { return LayoutShape::MoreLetters; };
LayoutShape rightLayoutShape() const override { return LayoutShape::BoundaryPunctuation; }
// Evaluation
Evaluation<float> approximate(SinglePrecision p, Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const override { return templatedApproximate<float>(context, complexFormat, angleUnit); }
Evaluation<double> approximate(DoublePrecision p, Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const override { return templatedApproximate<double>(context, complexFormat, angleUnit); }
template<typename T> Evaluation<T> templatedApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const;
};
class MatrixRef final : public Expression {
public:
MatrixRef(const MatrixRefNode * n) : Expression(n) {}
static MatrixRef Builder(Expression child) { return TreeHandle::FixedArityBuilder<MatrixRef, MatrixRefNode>({child}); }
static constexpr Expression::FunctionHelper s_functionHelper = Expression::FunctionHelper("ref", 1, &UntypedBuilderOneChild<MatrixRef>);
Expression shallowReduce(ExpressionNode::ReductionContext reductionContext);
};
}
#endif

View File

@@ -0,0 +1,48 @@
#ifndef POINCARE_MATRIX_RREF_H
#define POINCARE_MATRIX_RREF_H
#include <poincare/expression.h>
namespace Poincare {
class MatrixRrefNode final : public ExpressionNode {
public:
// TreeNode
size_t size() const override { return sizeof(MatrixRrefNode); }
int numberOfChildren() const override;
#if POINCARE_TREE_LOG
void logNodeName(std::ostream & stream) const override {
stream << "MatrixRref";
}
#endif
// Properties
Type type() const override { return Type::MatrixRref; }
private:
// Layout
Layout createLayout(Preferences::PrintFloatMode floatDisplayMode, int numberOfSignificantDigits) const override;
int serialize(char * buffer, int bufferSize, Preferences::PrintFloatMode floatDisplayMode, int numberOfSignificantDigits) const override;
// Simplification
Expression shallowReduce(ReductionContext reductionContext) override;
LayoutShape leftLayoutShape() const override { return LayoutShape::MoreLetters; };
LayoutShape rightLayoutShape() const override { return LayoutShape::BoundaryPunctuation; }
// Evaluation
Evaluation<float> approximate(SinglePrecision p, Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const override { return templatedApproximate<float>(context, complexFormat, angleUnit); }
Evaluation<double> approximate(DoublePrecision p, Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const override { return templatedApproximate<double>(context, complexFormat, angleUnit); }
template<typename T> Evaluation<T> templatedApproximate(Context * context, Preferences::ComplexFormat complexFormat, Preferences::AngleUnit angleUnit) const;
};
class MatrixRref final : public Expression {
public:
MatrixRref(const MatrixRrefNode * n) : Expression(n) {}
static MatrixRref Builder(Expression child) { return TreeHandle::FixedArityBuilder<MatrixRref, MatrixRrefNode>({child}); }
static constexpr Expression::FunctionHelper s_functionHelper = Expression::FunctionHelper("rref", 1, &UntypedBuilderOneChild<MatrixRref>);
Expression shallowReduce(ExpressionNode::ReductionContext reductionContext);
};
}
#endif

View File

@@ -54,6 +54,8 @@
#include <poincare/matrix_inverse.h>
#include <poincare/matrix_trace.h>
#include <poincare/matrix_transpose.h>
#include <poincare/matrix_ref.h>
#include <poincare/matrix_rref.h>
#include <poincare/multiplication.h>
#include <poincare/naperian_logarithm.h>
#include <poincare/norm_cdf.h>