pimath 0.0.59 → 0.0.62

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (58) hide show
  1. package/.eslintrc.js +23 -23
  2. package/.idea/misc.xml +5 -0
  3. package/.idea/php.xml +1 -1
  4. package/.idea/shelf/Uncommitted_changes_before_Update_at_17_04_2022_12_40_[Changes]/shelved.patch +21 -0
  5. package/.idea/shelf/Uncommitted_changes_before_Update_at_17_04_2022_12_40__Changes_.xml +4 -0
  6. package/dist/pi.js +169 -357
  7. package/dist/pi.js.map +1 -1
  8. package/dist/pi.min.js +1 -1
  9. package/dist/pi.min.js.map +1 -1
  10. package/docs/assets/highlight.css +78 -78
  11. package/docs/assets/main.js +52 -52
  12. package/docs/assets/style.css +1413 -1413
  13. package/docs/classes/Logicalset.Logicalset-1.html +4 -4
  14. package/docs/classes/Polynom.Rational.html +3 -3
  15. package/docs/classes/algebra_equation.Equation.html +25 -25
  16. package/docs/classes/algebra_monom.Monom.html +113 -113
  17. package/docs/classes/algebra_polynom.Polynom.html +29 -29
  18. package/docs/classes/coefficients_fraction.Fraction.html +18 -18
  19. package/docs/classes/coefficients_nthroot.NthRoot.html +2 -2
  20. package/docs/classes/geometry_circle.Circle.html +2 -2
  21. package/docs/classes/geometry_line.Line.html +2 -2
  22. package/docs/classes/geometry_triangle.Triangle.html +16 -16
  23. package/docs/classes/numeric.Numeric.html +13 -13
  24. package/docs/classes/shutingyard.Shutingyard.html +17 -17
  25. package/docs/index.html +10 -10
  26. package/docs/interfaces/algebra_equation.ISolution.html +2 -2
  27. package/docs/modules/Logicalset.html +2 -2
  28. package/docs/modules/Polynom.html +2 -2
  29. package/docs/modules/Vector.html +2 -2
  30. package/esm/maths/algebra/linearSystem.js +0 -1
  31. package/esm/maths/algebra/linearSystem.js.map +1 -1
  32. package/esm/maths/algebra/monom.d.ts +1 -0
  33. package/esm/maths/algebra/monom.js +18 -0
  34. package/esm/maths/algebra/monom.js.map +1 -1
  35. package/esm/maths/algebra/polynom.d.ts +36 -11
  36. package/esm/maths/algebra/polynom.js +144 -258
  37. package/esm/maths/algebra/polynom.js.map +1 -1
  38. package/esm/maths/algebra/rational.d.ts +15 -15
  39. package/esm/maths/algebra/rational.js +10 -101
  40. package/esm/maths/algebra/rational.js.map +1 -1
  41. package/esm/maths/algebra/study/rationalStudy.d.ts +33 -0
  42. package/esm/maths/algebra/study/rationalStudy.js +183 -0
  43. package/esm/maths/algebra/study/rationalStudy.js.map +1 -0
  44. package/esm/maths/algebra/study.d.ts +140 -0
  45. package/esm/maths/algebra/study.js +290 -0
  46. package/esm/maths/algebra/study.js.map +1 -0
  47. package/package.json +1 -1
  48. package/src/maths/algebra/linearSystem.ts +0 -1
  49. package/src/maths/algebra/monom.ts +19 -0
  50. package/src/maths/algebra/polynom.ts +185 -278
  51. package/src/maths/algebra/rational.ts +23 -134
  52. package/src/maths/algebra/study/rationalStudy.ts +208 -0
  53. package/src/maths/algebra/study.ts +384 -0
  54. package/tests/algebra/monom.test.ts +2 -5
  55. package/tests/algebra/polynom.test.ts +2 -3
  56. package/tests/algebra/rationnal.test.ts +0 -43
  57. package/tests/algebra/study.test.ts +18 -0
  58. package/tests/numexp.test.ts +1 -1
package/dist/pi.js CHANGED
@@ -932,7 +932,6 @@ class LinearSystem {
932
932
  this.log = () => {
933
933
  let str = '';
934
934
  for (let E of this._equations) {
935
- console.log(E.tex);
936
935
  str += `${E.tex}\\n}`;
937
936
  }
938
937
  return str;
@@ -1673,6 +1672,9 @@ class Monom {
1673
1672
  return this.evaluate(tmpValues);
1674
1673
  }
1675
1674
  if (typeof values === 'object') {
1675
+ if (this.variables.length === 0) {
1676
+ return this.coefficient;
1677
+ }
1676
1678
  for (let L in this._literal) {
1677
1679
  if (values[L] === undefined) {
1678
1680
  return new fraction_1.Fraction().zero();
@@ -1760,6 +1762,21 @@ class Monom {
1760
1762
  // All checks passed.
1761
1763
  return true;
1762
1764
  };
1765
+ this.isDivisible = (div) => {
1766
+ // For all variables (letters), the current monom must have a degree higher than the divider
1767
+ if (div.degree().isStrictlyPositive()) {
1768
+ for (let letter of div.variables) {
1769
+ if (!this.degree(letter).geq(div.degree(letter))) {
1770
+ return false;
1771
+ }
1772
+ }
1773
+ }
1774
+ // If the coefficient is rational, we suppose we don't need to check the division by the coefficient.
1775
+ if (this.coefficient.isRational() || div.coefficient.isRational()) {
1776
+ return true;
1777
+ }
1778
+ return this.coefficient.clone().divide(div.coefficient).isRelative();
1779
+ };
1763
1780
  this.zero();
1764
1781
  if (value !== undefined) {
1765
1782
  // A string is given - try to parse the value.
@@ -2135,6 +2152,11 @@ class Polynom {
2135
2152
  * @param values
2136
2153
  */
2137
2154
  constructor(polynomString, ...values) {
2155
+ this.mark_as_dirty = () => {
2156
+ this.dirty_factors = true;
2157
+ this.dirty_zeroes = true;
2158
+ this.euclidianCache = {};
2159
+ };
2138
2160
  this.addToken = (stack, element) => {
2139
2161
  switch (element.tokenType) {
2140
2162
  case shutingyard_1.ShutingyardType.COEFFICIENT:
@@ -2222,6 +2244,7 @@ class Polynom {
2222
2244
  // Reset the main variables.
2223
2245
  this._monoms = [];
2224
2246
  this._factors = [];
2247
+ this.mark_as_dirty();
2225
2248
  if (typeof inputStr === 'string') {
2226
2249
  return this._parseString(inputStr, ...values);
2227
2250
  }
@@ -2262,88 +2285,32 @@ class Polynom {
2262
2285
  this._monoms = [];
2263
2286
  this._monoms.push(new monom_1.Monom().zero());
2264
2287
  this._rawString = '0';
2288
+ this.mark_as_dirty();
2265
2289
  return this;
2266
2290
  };
2267
2291
  this.one = () => {
2268
2292
  this._monoms = [];
2269
2293
  this._monoms.push(new monom_1.Monom().one());
2270
2294
  this._rawString = '1';
2295
+ this.mark_as_dirty();
2271
2296
  return this;
2272
2297
  };
2273
2298
  this.empty = () => {
2274
2299
  this._monoms = [];
2275
2300
  this._rawString = '';
2301
+ this.mark_as_dirty();
2276
2302
  return this;
2277
2303
  };
2278
2304
  // ------------------------------------------
2279
2305
  this.opposed = () => {
2280
2306
  this._monoms = this._monoms.map(m => m.opposed());
2307
+ this.mark_as_dirty();
2281
2308
  return this;
2282
2309
  };
2283
- // // -----------------------------------------------
2284
- // // Polynom generators and randomizers
2285
- // // -----------------------------------------------
2286
- // random(config?: randomPolynomConfig) {
2287
- // return Random.polynom(config);
2288
- // }
2289
- //
2290
- // private _randomizeDefaults: { [key: string]: number | string | boolean } = {
2291
- // degree: 2,
2292
- // unit: true,
2293
- // fractions: false,
2294
- // factorable: false,
2295
- // letters: 'x',
2296
- // allowNullMonom: false,
2297
- // numberOfMonoms: false
2298
- // };
2299
- // get randomizeDefaults(): { [key: string]: number | string | boolean } {
2300
- // return this._randomizeDefaults;
2301
- // }
2302
- //
2303
- // set randomizeDefaults(value) {
2304
- // this._randomizeDefaults = value;
2305
- // }
2306
- //
2307
- // randomize = (config: { [key: string]: number | string | boolean }): Polynom => {
2308
- // let P = new Polynom();
2309
- //
2310
- // // Check the config file and use the default values.
2311
- // if (config === undefined) {
2312
- // config = {};
2313
- // }
2314
- // for (let k in this._randomizeDefaults) {
2315
- // if (config[k] === undefined) {
2316
- // config[k] = this._randomizeDefaults[k];
2317
- // }
2318
- // }
2319
- //
2320
- // // TODO: Build a more robust randomize function
2321
- // return P;
2322
- // }
2323
- //
2324
- // rndFactorable = (degree: number = 2, unit: boolean | number = false, letters: string = 'x'): Polynom => {
2325
- // // TODO: Make rndFactorable polynom generator more user friendly
2326
- // this._factors = [];
2327
- // for (let i = 0; i < degree; i++) {
2328
- // let factorUnit = unit === true || i >= unit,
2329
- // p = Random.polynom({
2330
- // degree: 1,
2331
- // unit: factorUnit,
2332
- // fraction: false,
2333
- // letters
2334
- // });
2335
- // this._factors.push(p);
2336
- // }
2337
- //
2338
- // this.empty().monoms = this._factors[0].monoms;
2339
- // for (let i = 1; i < this._factors.length; i++) {
2340
- // this.multiply(this._factors[i]);
2341
- // }
2342
- // return this;
2343
- // };
2344
2310
  // ------------------------------------------
2345
2311
  // Mathematical operations
2346
2312
  this.add = (...values) => {
2313
+ this.mark_as_dirty();
2347
2314
  for (let value of values) {
2348
2315
  if (value instanceof Polynom) {
2349
2316
  this._monoms = this._monoms.concat(value.monoms);
@@ -2361,6 +2328,7 @@ class Polynom {
2361
2328
  return this.reduce();
2362
2329
  };
2363
2330
  this.subtract = (...values) => {
2331
+ this.mark_as_dirty();
2364
2332
  for (let value of values) {
2365
2333
  if (value instanceof Polynom) {
2366
2334
  this._monoms = this._monoms.concat(value.clone().opposed().monoms);
@@ -2378,6 +2346,7 @@ class Polynom {
2378
2346
  return this.reduce();
2379
2347
  };
2380
2348
  this.multiply = (value) => {
2349
+ this.mark_as_dirty();
2381
2350
  if (value instanceof Polynom) {
2382
2351
  return this.multiplyByPolynom(value);
2383
2352
  }
@@ -2399,6 +2368,9 @@ class Polynom {
2399
2368
  * returns {quotient: Polynom, reminder: Polynom}
2400
2369
  */
2401
2370
  this.euclidian = (P) => {
2371
+ if (this.euclidianCache[P.tex] !== undefined) {
2372
+ return this.euclidianCache[P.tex];
2373
+ }
2402
2374
  const letter = P.variables[0];
2403
2375
  const quotient = new Polynom().zero();
2404
2376
  const reminder = this.clone().reorder(letter);
@@ -2432,6 +2404,7 @@ class Polynom {
2432
2404
  return { quotient, reminder };
2433
2405
  };
2434
2406
  this.divide = (value) => {
2407
+ this.mark_as_dirty();
2435
2408
  if (value instanceof fraction_1.Fraction) {
2436
2409
  return this.divideByFraction(value);
2437
2410
  }
@@ -2445,6 +2418,7 @@ class Polynom {
2445
2418
  }
2446
2419
  };
2447
2420
  this.pow = (nb) => {
2421
+ this.mark_as_dirty();
2448
2422
  if (!Number.isSafeInteger(nb)) {
2449
2423
  return this.zero();
2450
2424
  }
@@ -2645,6 +2619,7 @@ class Polynom {
2645
2619
  * @param P
2646
2620
  */
2647
2621
  this.replaceBy = (letter, P) => {
2622
+ this.mark_as_dirty();
2648
2623
  let pow;
2649
2624
  const resultPolynom = new Polynom().zero();
2650
2625
  for (const m of this.monoms) {
@@ -2704,146 +2679,108 @@ class Polynom {
2704
2679
  * @param maxValue Defines the greatest value to search to (default is 20).
2705
2680
  */
2706
2681
  this.factorize = (letter) => {
2707
- let factors = [];
2708
- // Extract the common monom
2709
- let P = this.clone().reorder(), M = P.commonMonom(), tempPolynom;
2710
- // It has a common monom.
2711
- if (!M.isOne()) {
2712
- tempPolynom = new Polynom(M);
2713
- factors = [tempPolynom.clone()];
2714
- P = P.euclidian(tempPolynom).quotient;
2715
- }
2716
- let securityLoop = P.degree().clone().multiply(2).value;
2717
- let result;
2718
- // securityLoop = 0
2719
- while (securityLoop >= 0) {
2720
- securityLoop--;
2721
- if (P.monoms.length < 2) {
2722
- if (!P.isOne()) {
2682
+ if (this.dirty_factors) {
2683
+ let factors = [];
2684
+ let P = this.clone().reorder();
2685
+ // Extract the common monom
2686
+ // 2x^3+6x^2 => 2x^2
2687
+ let M = P.commonMonom();
2688
+ if (!M.isOne()) {
2689
+ let tempPolynom = new Polynom(M);
2690
+ factors = [tempPolynom.clone()];
2691
+ P = P.euclidian(tempPolynom).quotient;
2692
+ }
2693
+ // Main loop
2694
+ let securityLoop = P.degree().clone().multiply(2).value, maxDegree = 1;
2695
+ while (securityLoop >= 0) {
2696
+ securityLoop--;
2697
+ if (P.monoms.length < 2) {
2698
+ // The polynom has only one monom => 7x^2
2699
+ // No need to continue.
2700
+ if (!P.isOne()) {
2701
+ factors.push(P.clone());
2702
+ P.one();
2703
+ }
2704
+ break;
2705
+ }
2706
+ else if (P.degree(letter).isOne()) {
2707
+ // The polynom is a first degree polynom => 3x-5
2708
+ // No need to continue
2723
2709
  factors.push(P.clone());
2724
2710
  P.one();
2711
+ break;
2712
+ }
2713
+ else {
2714
+ // Create the list of all "potential" polynom dividers.
2715
+ let allDividers = this._getAllPotentialFactors(P, maxDegree, letter);
2716
+ maxDegree = P.degree(letter).value;
2717
+ // Actually: 100ms
2718
+ while (allDividers.length > 0) {
2719
+ let div = allDividers[0];
2720
+ if (!P.isDividableBy(div)) {
2721
+ // Not dividable. Remove it from the list
2722
+ allDividers.shift();
2723
+ }
2724
+ else {
2725
+ // It's dividable - so make the division
2726
+ let result = P.euclidian(div);
2727
+ // Add the factor
2728
+ factors.push(div);
2729
+ // As it's dividable, get the quotient.
2730
+ P = result.quotient.clone();
2731
+ // filter all dividers that are no more suitable.
2732
+ allDividers = allDividers.filter(x => {
2733
+ let pX = P.monoms[0], pC = P.monoms[P.monoms.length - 1], dX = x.monoms[0], dC = x.monoms[x.monoms.length - 1];
2734
+ // Check last item (degree zero)
2735
+ if (!pC.isDivisible(dC)) {
2736
+ return false;
2737
+ }
2738
+ // Check the first item (degree max)
2739
+ if (!pX.isDivisible(dX)) {
2740
+ return false;
2741
+ }
2742
+ return true;
2743
+ });
2744
+ }
2745
+ }
2725
2746
  }
2726
- break;
2727
2747
  }
2728
- else if (P.degree(letter).isOne()) {
2748
+ // Maybe there is still something in the Polynom (not everything was possible to factorize)
2749
+ if (!P.isOne()) {
2729
2750
  factors.push(P.clone());
2730
- P.one();
2731
- break;
2751
+ }
2752
+ // Save the factors
2753
+ this._factors = factors;
2754
+ // The factors list is no more dirty
2755
+ this.dirty_factors = false;
2756
+ }
2757
+ return this._factors;
2758
+ };
2759
+ this.isDividableBy = (div) => {
2760
+ // Quick evaluation.
2761
+ if (div.degree().isOne()) {
2762
+ let zero = div.getZeroes()[0];
2763
+ if (zero.exact instanceof fraction_1.Fraction) {
2764
+ return this.evaluate(zero.exact).isZero();
2732
2765
  }
2733
2766
  else {
2734
- // Get the first and last monom and build all their dividers.
2735
- // let m1 = P.monoms[0].dividers,
2736
- // m2 = P.monoms[P.monoms.length - 1].dividers
2737
- // Create the list of all "potential" polynom dividers.
2738
- let allDividers = this._getAllPotentialFactors(P, letter);
2739
- allDividers.every(div => {
2740
- result = P.euclidian(div);
2741
- if (result.reminder.isZero()) {
2742
- P = result.quotient.clone();
2743
- factors.push(div);
2744
- return false;
2745
- }
2746
- return true;
2747
- });
2767
+ return false;
2748
2768
  }
2749
2769
  }
2750
- if (!P.isOne()) {
2751
- factors.push(P.clone());
2770
+ else {
2771
+ this.euclidianCache[div.tex] = this.euclidian(div);
2772
+ return this.euclidianCache[div.tex].reminder.isZero();
2752
2773
  }
2753
- this.factors = factors;
2754
- return factors;
2755
2774
  };
2756
2775
  // TODO: get zeroes for more than first degree and for more than natural degrees
2757
2776
  this.getZeroes = () => {
2758
- let equ = new equation_1.Equation(this.clone(), 0);
2759
- equ.solve();
2760
- return equ.solutions;
2761
- //
2762
- // const Z: Fraction[] = [];
2763
- //
2764
- // // ISolution: {tex: string, value: number, exact: boolean|Fraction|...}
2765
- //
2766
- // switch (this.degree().value) {
2767
- // case 0:
2768
- // if (this._monoms[0].coefficient.value === 0) {
2769
- // return [{
2770
- // tex: '\\mathbb{R}',
2771
- // value: NaN,
2772
- // exact: false
2773
- // }];
2774
- // } else {
2775
- // return [{
2776
- // tex: '\\varnothing',
2777
- // value: NaN,
2778
- // exact: false
2779
- // }];
2780
- // }
2781
- // case 1:
2782
- // // There is only one monoms,
2783
- // if (this._monoms.length === 1) {
2784
- // return [{
2785
- // tex: '0',
2786
- // value: 0,
2787
- // exact: new Fraction().zero()
2788
- // }];
2789
- // } else {
2790
- // const P = this.clone().reduce().reorder();
2791
- // const coeff = P.monoms[1].coefficient.opposed().divide(P.monoms[0].coefficient)
2792
- // return [{
2793
- // tex: coeff.tex,
2794
- // value: coeff.value,
2795
- // exact: coeff
2796
- // }];
2797
- // }
2798
- // // TODO: Determine the zeros of an equation of second degree.
2799
- // //case 2:
2800
- // default:
2801
- // // Make sure the polynom is factorized.
2802
- // if (this._factors.length === 0) {
2803
- // this.factorize()
2804
- // }
2805
- //
2806
- // let zeroes:Fraction[] = [], zeroesAsTex = [];
2807
- // for (let P of this._factors) {
2808
- // if (P.degree().greater(2)) {
2809
- // // TODO: get zeroes of polynom with a degree greater than 2.
2810
- //
2811
- // } else if (P.degree().value === 2) {
2812
- // let A = P.monomByDegree(2).coefficient,
2813
- // B = P.monomByDegree(1).coefficient,
2814
- // C = P.monomByDegree(0).coefficient,
2815
- // D = B.clone().pow(2).subtract(A.clone().multiply(C).multiply(4));
2816
- //
2817
- // if (D.value > 0) {
2818
- // /*console.log('Two zeroes for ', P.tex); */
2819
- // let x1 = (-(B.value) + Math.sqrt(D.value)) / (2 * A.value),
2820
- // x2 = (-(B.value) - Math.sqrt(D.value)) / (2 * A.value);
2821
- //
2822
- // zeroes.push(new Fraction(x1.toFixed(3)).reduce());
2823
- // zeroes.push(new Fraction(x2.toFixed(3)).reduce());
2824
- // } else if (D.value === 0) {
2825
- // /*console.log('One zero for ', P.tex); */
2826
- // } else {
2827
- // console.log('No zero for ', P.tex);
2828
- // }
2829
- // } else {
2830
- // for (let z of P.getZeroes()) {
2831
- // // Check if the zero is already in the list.
2832
- // // if (z === false || z === true) {
2833
- // // continue;
2834
- // // }
2835
- // if (zeroesAsTex.indexOf(z.frac) === -1) {
2836
- // zeroes.push(z);
2837
- // zeroesAsTex.push(z.frac);
2838
- // }
2839
- // }
2840
- // }
2841
- // }
2842
- //
2843
- //
2844
- // return zeroes;
2845
- // }
2846
- // return Z;
2777
+ if (this.dirty_zeroes) {
2778
+ let equ = new equation_1.Equation(this.clone(), 0);
2779
+ equ.solve();
2780
+ this._zeroes = equ.solutions;
2781
+ this.dirty_zeroes = false;
2782
+ }
2783
+ return this._zeroes;
2847
2784
  };
2848
2785
  // TODO: analyse the next functions to determine if they are useful or not...
2849
2786
  this.monomByDegree = (degree, letter) => {
@@ -2958,16 +2895,19 @@ class Polynom {
2958
2895
  // Any other cases
2959
2896
  return (new fraction_1.Fraction()).zero();
2960
2897
  };
2961
- this._getAllPotentialFactors = (P, letter) => {
2898
+ this._getAllPotentialFactors = (P, maxDegree, letter) => {
2962
2899
  let m1 = P.monoms[0].dividers, m2 = P.monoms[P.monoms.length - 1].dividers;
2963
2900
  let allDividers = [];
2964
2901
  m1.forEach(m1d => {
2965
- m2.forEach(m2d => {
2966
- if (m1d.degree(letter).isNotEqual(m2d.degree(letter))) {
2967
- allDividers.push(new Polynom(m1d, m2d));
2968
- allDividers.push(new Polynom(m1d, m2d.clone().opposed()));
2969
- }
2970
- });
2902
+ // Get only polynom that has a degree less than a specific value
2903
+ if (m1d.degree(letter).leq(maxDegree)) {
2904
+ m2.forEach(m2d => {
2905
+ if (m1d.degree(letter).isNotEqual(m2d.degree(letter))) {
2906
+ allDividers.push(new Polynom(m1d, m2d));
2907
+ allDividers.push(new Polynom(m1d, m2d.clone().opposed()));
2908
+ }
2909
+ });
2910
+ }
2971
2911
  });
2972
2912
  return allDividers;
2973
2913
  };
@@ -3019,41 +2959,6 @@ class Polynom {
3019
2959
  this.add(stack[0]);
3020
2960
  }
3021
2961
  return this;
3022
- /**
3023
- let m1: Polynom;
3024
- let m2: Polynom;
3025
-
3026
- let stack: Polynom[] = [],
3027
- previousToken: string = null,
3028
- tempPolynom
3029
-
3030
- for (const element of rpn) {
3031
- if (element.tokenType === 'coefficient' || element.tokenType === 'variable') {
3032
- tempPolynom = new Polynom().zero();
3033
- tempPolynom.monoms = [new Monom(element.token)]
3034
- stack.push(tempPolynom.clone())
3035
- } else if (element.tokenType === 'operation') {
3036
- m2 = (stack.pop()) || new Polynom().zero();
3037
- m1 = (stack.pop()) || new Polynom().zero();
3038
- switch (element.token) {
3039
- case '+':
3040
- stack.push(m1.add(m2))
3041
- break;
3042
- case '-':
3043
- stack.push(m1.subtract(m2))
3044
- break;
3045
- case '*':
3046
- stack.push(m1.multiply(m2))
3047
- break;
3048
- case '^':
3049
- stack.push(m1.pow(+previousToken))
3050
- }
3051
- }
3052
- previousToken = element.token;
3053
- }
3054
-
3055
- this._monoms = stack[0].monoms;
3056
- return this;*/
3057
2962
  };
3058
2963
  this.multiplyByPolynom = (P) => {
3059
2964
  const M = [];
@@ -3178,33 +3083,6 @@ class Polynom {
3178
3083
  }
3179
3084
  }
3180
3085
  return [this.clone()];
3181
- //
3182
- // console.log(a.tex, b.tex, c.tex)
3183
- // if (a.isSquare() && c.isSquare()) {
3184
- // console.log('A C squares')
3185
- // if (a.clone().sqrt().multiply(c.clone().sqrt()).multiplyByNumber(2).isSameAs(b)) {
3186
- // console.log('HERE')
3187
- // if (a.coefficient.sign() === b.coefficient.sign()) {
3188
- // return []
3189
- // }else{
3190
- // return []
3191
- // }
3192
- // }
3193
- // } else if(a.isLiteralSquare() && c.isLiteralSquare()) {
3194
- // console.log('A C litteral SQUARES')
3195
- // // Check that the middle element is the product of a and c.
3196
- //
3197
- // if(b.clone().pow(2).isSameAs(a.clone().multiply(c))){
3198
- // console.log('SAME')
3199
- //
3200
- // }else{
3201
- // console.log('NOT SAME')
3202
- // }
3203
- //
3204
- // return [this.clone()]
3205
- // } else {
3206
- // console.log('NOT SQUARES AT ALL !!!!')
3207
- // }
3208
3086
  }
3209
3087
  };
3210
3088
  this._factorizeByGroups = () => {
@@ -3213,11 +3091,31 @@ class Polynom {
3213
3091
  };
3214
3092
  this._monoms = [];
3215
3093
  this._factors = [];
3094
+ this.mark_as_dirty();
3216
3095
  if (polynomString !== undefined) {
3217
3096
  this.parse(polynomString, ...values);
3218
3097
  }
3219
3098
  return this;
3220
3099
  }
3100
+ get euclidianCache() {
3101
+ return this._euclidianCache;
3102
+ }
3103
+ set euclidianCache(value) {
3104
+ this._euclidianCache = value;
3105
+ }
3106
+ get dirty_zeroes() {
3107
+ return this._dirty_zeroes;
3108
+ }
3109
+ set dirty_zeroes(value) {
3110
+ this._dirty_zeroes = value;
3111
+ }
3112
+ // ------------------------------------------
3113
+ get dirty_factors() {
3114
+ return this._dirty_factors;
3115
+ }
3116
+ set dirty_factors(value) {
3117
+ this._dirty_factors = value;
3118
+ }
3221
3119
  // ------------------------------------------
3222
3120
  get monoms() {
3223
3121
  return this._monoms;
@@ -3225,10 +3123,14 @@ class Polynom {
3225
3123
  set monoms(M) {
3226
3124
  this._monoms = M;
3227
3125
  }
3126
+ get zeroes() {
3127
+ return this.getZeroes();
3128
+ }
3228
3129
  get factors() {
3229
- return this._factors;
3130
+ return this.factorize();
3230
3131
  }
3231
3132
  set factors(value) {
3133
+ this.mark_as_dirty();
3232
3134
  this._factors = value;
3233
3135
  }
3234
3136
  get texString() {
@@ -3373,17 +3275,15 @@ class Rational {
3373
3275
  */
3374
3276
  constructor(numerator, denominator) {
3375
3277
  this.clone = () => {
3376
- this._numerator = this._numerator.clone();
3377
- this._denominator = this._denominator.clone();
3378
- return this;
3278
+ return new Rational(this._numerator.clone(), this._denominator.clone());
3379
3279
  };
3380
3280
  this.domain = () => {
3381
3281
  let zeroes = this._denominator.getZeroes();
3382
3282
  if (zeroes.length === 0 || zeroes[0].tex === equation_1.PARTICULAR_SOLUTION.real) {
3383
- return equation_1.PARTICULAR_SOLUTION.real;
3283
+ return equation_1.PARTICULAR_SOLUTION.varnothing;
3384
3284
  }
3385
3285
  else if (zeroes[0].tex === equation_1.PARTICULAR_SOLUTION.varnothing) {
3386
- return equation_1.PARTICULAR_SOLUTION.varnothing;
3286
+ return equation_1.PARTICULAR_SOLUTION.real;
3387
3287
  }
3388
3288
  else {
3389
3289
  return '\\mathbb{R}\\setminus\\left\\{' +
@@ -3440,6 +3340,10 @@ class Rational {
3440
3340
  this.subtract = (R) => {
3441
3341
  return this.add(R.clone().opposed());
3442
3342
  };
3343
+ this.euclidian = () => {
3344
+ return this._numerator.euclidian(this._denominator);
3345
+ };
3346
+ // TODO : where and how is used limits ?
3443
3347
  this.limits = (value, offset, letter) => {
3444
3348
  if (value === Infinity || value === -Infinity) {
3445
3349
  let { quotient, reminder } = this._numerator.clone().euclidian(this._denominator);
@@ -3480,101 +3384,9 @@ class Rational {
3480
3384
  }
3481
3385
  }
3482
3386
  };
3483
- this.makeTableOfSigns = () => {
3484
- // Factorize the numerator and the denominator
3485
- this._numerator.factorize();
3486
- this._denominator.factorize();
3487
- let zeroes = equation_1.Equation.makeSolutionsUnique([...this._numerator.getZeroes(), ...this._denominator.getZeroes()], true).filter(x => !isNaN(x.value)), NFactors = this._numerator.factors, DFactors = this._denominator.factors;
3488
- let tableOfSigns = [], result = [];
3489
- NFactors.forEach(factor => {
3490
- tableOfSigns.push(this._makeOneLineOfTableOfSigns(factor, zeroes, 'z'));
3491
- });
3492
- DFactors.forEach(factor => {
3493
- tableOfSigns.push(this._makeOneLineOfTableOfSigns(factor, zeroes, 'd'));
3494
- });
3495
- // Empty line
3496
- tableOfSigns.push([]);
3497
- // Add the final row as cumulative
3498
- let resultLine = tableOfSigns[0].map((x, index) => {
3499
- if (index === 0) {
3500
- return '';
3501
- }
3502
- if (index === tableOfSigns[0].length - 1) {
3503
- return '';
3504
- }
3505
- if (index % 2 === 0) {
3506
- return 't';
3507
- }
3508
- return '+';
3509
- });
3510
- for (let current of tableOfSigns) {
3511
- for (let i = 0; i < current.length; i++) {
3512
- if (i % 2 === 0) {
3513
- // t, z or d
3514
- if (resultLine[i] === 'd') {
3515
- continue;
3516
- }
3517
- if (current[i] !== 't') {
3518
- resultLine[i] = current[i];
3519
- }
3520
- }
3521
- else {
3522
- // + or -
3523
- if (current[i] === '-') {
3524
- resultLine[i] = resultLine[i] === '+' ? '-' : '+';
3525
- }
3526
- }
3527
- }
3528
- }
3529
- // Add the variation line.
3530
- // TODO: add the variation line.
3531
- tableOfSigns.push(resultLine);
3532
- let tos = {
3533
- factors: [...NFactors, ...DFactors],
3534
- zeroes: zeroes,
3535
- signs: tableOfSigns,
3536
- tex: ''
3537
- };
3538
- this._makeTexFromTableOfSigns(tos);
3539
- return tos;
3540
- };
3541
- this._makeTexFromTableOfSigns = (tos) => {
3542
- let tex = `\\begin{tikzpicture}
3543
- \\tkzTabInit[lgt=3,espcl=2,deltacl=0]{/1.2,\\(${tos.factors.map(x => x.tex).join('\\)/1,\\(')}\\)/1,/.1,\\(f(x)\\)/1.2}{{\\scriptsize \\hspace{1cm} \\(-\\infty\\)},\\(${tos.zeroes.map(x => x.tex).join('\\),\\(')}\\),{\\scriptsize \\hspace{-1cm} \\(+\\infty\\)}}`;
3544
- tos.signs.forEach(list => {
3545
- tex += (`\n\\tkzTabLine{${list.join(',')}}`);
3546
- });
3547
- tex += `\n\\end{tikzpicture}`;
3548
- tos.tex = tex;
3549
- return tex;
3550
- };
3551
- this._makeOneLineOfTableOfSigns = (factor, zeroes, zeroSign) => {
3552
- let oneLine = [], currentZero = factor.getZeroes().map(x => x.tex);
3553
- // First +/- sign, before the first zero
3554
- oneLine.push('');
3555
- if (factor.degree().isZero()) {
3556
- oneLine.push(factor.monoms[0].coefficient.sign() === 1 ? '+' : '-');
3557
- }
3558
- else {
3559
- oneLine.push(factor.evaluate(zeroes[0].value - 1).sign() === 1 ? '+' : '-');
3560
- }
3561
- for (let i = 0; i < zeroes.length; i++) {
3562
- // Add the zero if it's the current one
3563
- oneLine.push(currentZero.includes(zeroes[i].tex) ? zeroSign : 't');
3564
- // + / - sign after the current zero
3565
- if (i < zeroes.length - 1) {
3566
- oneLine.push(factor.evaluate((zeroes[i].value + zeroes[i + 1].value) / 2).sign() === 1 ? '+' : '-');
3567
- }
3568
- else if (i === zeroes.length - 1) {
3569
- oneLine.push(factor.evaluate(zeroes[i].value + 1).sign() === 1 ? '+' : '-');
3570
- }
3571
- }
3572
- oneLine.push('');
3573
- return oneLine;
3574
- };
3575
3387
  this.evaluate = (values) => {
3576
3388
  const r = new fraction_1.Fraction().zero();
3577
- let N = this._numerator.evaluate(values), D = this._numerator.evaluate(values);
3389
+ let N = this._numerator.evaluate(values), D = this._denominator.evaluate(values);
3578
3390
  return N.divide(D);
3579
3391
  };
3580
3392
  if (numerator instanceof polynom_1.Polynom) {