[poincare] Improve Cosine::immediateSimplify

Change-Id: Icc6329625895c9b33cf8342ab4cdea4ee748d5d4
This commit is contained in:
Émilie Feral
2017-10-13 14:30:10 +02:00
parent 1b4a553f1b
commit 47ce822c42
6 changed files with 51 additions and 1 deletions

View File

@@ -77,6 +77,7 @@ objs += $(addprefix poincare/src/,\
sum.o\
symbol.o\
tangent.o\
trigonometry.o\
undefined.o\
variable_context.o\
)

View File

@@ -0,0 +1,20 @@
#ifndef POINCARE_TRIGONOMETRY_H
#define POINCARE_TRIGONOMETRY_H
#include <poincare/expression.h>
namespace Poincare {
class Trigonometry {
public:
enum class Function {
Cosine = 0,
Sine = 1,
};
static Expression * table(const Expression * e, Function f, bool inverse); // , Function f, bool inverse
constexpr static int k_numberOfEntries = 3;
};
}
#endif

View File

@@ -3,6 +3,7 @@
#include <poincare/complex.h>
#include <poincare/symbol.h>
#include <poincare/rational.h>
#include <poincare/trigonometry.h>
#include <ion.h>
extern "C" {
#include <assert.h>
@@ -42,6 +43,10 @@ Expression * Cosine::immediateSimplify() {
}
assert(r->sign() > 0);
assert(r->numerator().isLowerThan(r->denominator()));
Expression * lookup = Trigonometry::table(operand(0), Trigonometry::Function::Cosine, false);
if (lookup != nullptr) {
return replaceWith(lookup, true);
}
}
return this;
}

View File

@@ -152,8 +152,8 @@ void DynamicHierarchy::sortChildren() {
}
Expression * DynamicHierarchy::squashUnaryHierarchy() {
assert(parent() != nullptr);
if (numberOfOperands() == 1) {
assert(parent() != nullptr);
Expression * o = const_cast<Expression *>(operand(0));
replaceWith(o, true);
return o;

View File

@@ -0,0 +1,23 @@
#include <poincare/trigonometry.h>
#include <ion.h>
namespace Poincare {
static_assert('\x89' == Ion::Charset::SmallPi, "Incorrect");
constexpr const char * cheatTable[Trigonometry::k_numberOfEntries][3] = {{"\x89*12^(-1)", "\x89*5*12^(-1)", "6^(1/2)*4^(-1)+2^(1/2)*4^(-1)"}, {"\x89*8^(-1)", "\x89*3*8^(-1)", "(2+2^(1/2))^(1/2)*2^(-1)"}, {"\x89*6^(-1)", "\x89*3^(-1)", "3^(1/2)*2^(-1)"}};
Expression * Trigonometry::table(const Expression * e, Function f, bool inverse) {
int inputIndex = inverse ? 2 : (int)f;
int outputIndex = inverse ? (int)f : 2;
for (int i = 0; i < k_numberOfEntries; i++) {
Expression * input = Expression::parse(cheatTable[i][inputIndex]);
input->simplify(); // input expression does not change, no root needed and we can use entry after
if (input->compareTo(e) == 0) {
Expression * output = Expression::parse(cheatTable[i][outputIndex]);
return output->simplify();
}
}
return nullptr;
}
}

View File

@@ -149,6 +149,7 @@ QUIZ_CASE(poincare_simplify_easy) {
assert_parsed_expression_simplify_to("cos(-P*35/29)", "cos(P*6/29)");
assert_parsed_expression_simplify_to("cos(P*340000)", "1");
assert_parsed_expression_simplify_to("cos(-P*340000)", "1");
assert_parsed_expression_simplify_to("cos(P/12)", "(R(6)+R(2))/4");
/* This does not work but should not as it is above k_primorial32 = 1*3*5*7*11*... (product of first 32 primes. */
//assert_parsed_expression_simplify_to("1881676377434183981909562699940347954480361860897069^(1/3)", "123456789123456789");