pimath 0.0.11 → 0.0.15
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.
- package/.idea/codeStyles/codeStyleConfig.xml +1 -1
- package/dev/index.html +3 -7
- package/dist/pi.js +1 -1
- package/dist/pi.js.map +1 -1
- package/docs/assets/highlight.css +7 -0
- package/docs/assets/search.js +1 -1
- package/docs/classes/algebra.Algebra.Equation.html +26 -0
- package/docs/classes/algebra.Algebra.LinearSystem.html +1 -0
- package/docs/classes/algebra.Algebra.LogicalSet.html +3 -0
- package/docs/classes/algebra.Algebra.Monom.html +111 -0
- package/docs/classes/algebra.Algebra.Polynom.html +36 -0
- package/docs/classes/algebra.Algebra.Rational.html +2 -0
- package/docs/classes/algebra.Equation.html +28 -0
- package/docs/classes/algebra.LinearSystem.html +1 -0
- package/docs/classes/algebra.Logicalset.html +5 -0
- package/docs/classes/algebra.Monom.html +111 -0
- package/docs/classes/algebra.Polynom.html +43 -0
- package/docs/classes/algebra.Rational.html +4 -0
- package/docs/classes/coefficients.Fraction.html +15 -0
- package/docs/classes/coefficients.Nthroot.html +1 -0
- package/docs/classes/geometry.Circle.html +1 -0
- package/docs/classes/geometry.Geometry.Circle.html +1 -0
- package/docs/classes/geometry.Geometry.Line.html +1 -0
- package/docs/classes/geometry.Geometry.Point.html +1 -0
- package/docs/classes/geometry.Geometry.Triangle.html +9 -0
- package/docs/classes/geometry.Geometry.Vector.html +1 -0
- package/docs/classes/geometry.Line.html +1 -0
- package/docs/classes/geometry.Point.html +1 -0
- package/docs/classes/geometry.Triangle.html +17 -0
- package/docs/classes/geometry.Vector.html +1 -0
- package/docs/classes/{Numeric.html → numeric.Numeric.html} +5 -5
- package/docs/classes/shutingyard.Shutingyard.html +19 -0
- package/docs/index.html +2 -2
- package/docs/interfaces/geometry.remarquableLines.html +1 -0
- package/docs/modules/algebra.Algebra.html +1 -0
- package/docs/modules/algebra.html +1 -0
- package/docs/modules/coefficients.html +1 -0
- package/docs/modules/geometry.Geometry.html +1 -0
- package/docs/modules/geometry.html +1 -0
- package/docs/modules/numeric.html +1 -0
- package/docs/modules/random.Random.html +1 -0
- package/docs/modules/random.html +1 -0
- package/docs/modules/shutingyard.html +1 -0
- package/docs/modules.html +1 -1
- package/esm/docs.d.ts +6 -0
- package/esm/docs.js +7 -0
- package/esm/docs.js.map +1 -0
- package/esm/main.js +6 -16
- package/esm/main.js.map +1 -1
- package/esm/maths/algebra/equation.d.ts +2 -2
- package/esm/maths/algebra/equation.js +5 -5
- package/esm/maths/algebra/equation.js.map +1 -1
- package/esm/maths/algebra/index.d.ts +26 -0
- package/esm/maths/algebra/index.js +34 -0
- package/esm/maths/algebra/index.js.map +1 -0
- package/esm/maths/algebra/linearSystem.d.ts +3 -3
- package/esm/maths/algebra/linearSystem.js +5 -5
- package/esm/maths/algebra/linearSystem.js.map +1 -1
- package/esm/maths/algebra/logicalset.d.ts +1 -1
- package/esm/maths/algebra/logicalset.js +2 -2
- package/esm/maths/algebra/logicalset.js.map +1 -1
- package/esm/maths/algebra/monom.d.ts +2 -2
- package/esm/maths/algebra/monom.js +3 -3
- package/esm/maths/algebra/monom.js.map +1 -1
- package/esm/maths/algebra/polynom.d.ts +5 -3
- package/esm/maths/algebra/polynom.js +9 -6
- package/esm/maths/algebra/polynom.js.map +1 -1
- package/esm/maths/algebra/rational.d.ts +3 -3
- package/esm/maths/algebra/rational.js +2 -2
- package/esm/maths/algebra/rational.js.map +1 -1
- package/esm/maths/coefficients/fraction.d.ts +1 -1
- package/esm/maths/coefficients/fraction.js +2 -2
- package/esm/maths/coefficients/fraction.js.map +1 -1
- package/esm/maths/coefficients/index.d.ts +2 -0
- package/esm/maths/coefficients/index.js +3 -0
- package/esm/maths/coefficients/index.js.map +1 -0
- package/esm/maths/coefficients/nthroot.d.ts +1 -1
- package/esm/maths/coefficients/nthroot.js +1 -1
- package/esm/maths/coefficients/nthroot.js.map +1 -1
- package/esm/maths/geometry/circle.d.ts +1 -1
- package/esm/maths/geometry/circle.js +5 -5
- package/esm/maths/geometry/circle.js.map +1 -1
- package/esm/maths/geometry/index.d.ts +22 -0
- package/esm/maths/geometry/index.js +29 -0
- package/esm/maths/geometry/index.js.map +1 -0
- package/esm/maths/geometry/line.d.ts +5 -5
- package/esm/maths/geometry/line.js +7 -7
- package/esm/maths/geometry/line.js.map +1 -1
- package/esm/maths/geometry/point.d.ts +2 -2
- package/esm/maths/geometry/point.js +2 -2
- package/esm/maths/geometry/point.js.map +1 -1
- package/esm/maths/geometry/triangle.d.ts +5 -6
- package/esm/maths/geometry/triangle.js +6 -6
- package/esm/maths/geometry/triangle.js.map +1 -1
- package/esm/maths/geometry/vector.d.ts +2 -2
- package/esm/maths/geometry/vector.js +3 -3
- package/esm/maths/geometry/vector.js.map +1 -1
- package/esm/maths/numeric.d.ts +1 -1
- package/esm/maths/numeric.js +1 -1
- package/esm/maths/numeric.js.map +1 -1
- package/esm/maths/random/index.d.ts +13 -0
- package/esm/maths/random/index.js +28 -0
- package/esm/maths/random/index.js.map +1 -0
- package/esm/maths/random/random.d.ts +2 -2
- package/esm/maths/random/random.js +3 -3
- package/esm/maths/random/random.js.map +1 -1
- package/esm/maths/random/randomCore.d.ts +1 -1
- package/esm/maths/random/randomCore.js +1 -1
- package/esm/maths/random/randomCore.js.map +1 -1
- package/esm/maths/random/rndHelpers.d.ts +1 -1
- package/esm/maths/random/rndHelpers.js +1 -1
- package/esm/maths/random/rndHelpers.js.map +1 -1
- package/esm/maths/random/rndMonom.d.ts +3 -3
- package/esm/maths/random/rndMonom.js +4 -4
- package/esm/maths/random/rndMonom.js.map +1 -1
- package/esm/maths/random/rndPolynom.d.ts +3 -3
- package/esm/maths/random/rndPolynom.js +15 -6
- package/esm/maths/random/rndPolynom.js.map +1 -1
- package/esm/maths/shutingyard.d.ts +1 -1
- package/esm/maths/shutingyard.js +1 -1
- package/esm/maths/shutingyard.js.map +1 -1
- package/package.json +1 -1
- package/src/main.ts +1 -1
- package/src/maths/algebra/equation.ts +20 -5
- package/src/maths/algebra/index.ts +16 -0
- package/src/maths/algebra/linearSystem.ts +265 -265
- package/src/maths/algebra/logicalset.ts +162 -150
- package/src/maths/algebra/monom.ts +631 -629
- package/src/maths/algebra/polynom.ts +1143 -1139
- package/src/maths/algebra/rational.ts +110 -99
- package/src/maths/geometry/index.ts +15 -1
- package/src/maths/geometry/triangle.ts +1 -1
- package/src/maths/random/{random.ts → index.ts} +4 -17
- package/src/maths/random/rndMonom.ts +1 -1
- package/src/maths/random/rndPolynom.ts +16 -5
- package/tests/algebra/monom.test.ts +1 -1
- package/tsconfig.json +9 -2
- package/docs/classes/Circle.html +0 -1
- package/docs/classes/Equation.html +0 -19
- package/docs/classes/Fraction.html +0 -15
- package/docs/classes/Line.html +0 -1
- package/docs/classes/LinearSystem.html +0 -1
- package/docs/classes/Logicalset.html +0 -5
- package/docs/classes/Monom.html +0 -111
- package/docs/classes/Nthroot.html +0 -1
- package/docs/classes/Point.html +0 -1
- package/docs/classes/Polynom.html +0 -43
- package/docs/classes/Rational.html +0 -4
- package/docs/classes/Shutingyard.html +0 -19
- package/docs/classes/Triangle.html +0 -17
- package/docs/classes/Vector.html +0 -1
- package/docs/modules/Random.html +0 -1
- package/src/docs.ts +0 -7
|
@@ -6,739 +6,741 @@
|
|
|
6
6
|
import {Fraction} from "../coefficients/fraction";
|
|
7
7
|
import {Numeric} from "../numeric";
|
|
8
8
|
|
|
9
|
-
export class Monom {
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
return this;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
// ------------------------------------------
|
|
29
|
-
// Getter and setter
|
|
30
|
-
// ------------------------------------------
|
|
31
|
-
get isMonom() {
|
|
32
|
-
return true;
|
|
33
|
-
}
|
|
9
|
+
export class Monom {
|
|
10
|
+
private _coefficient: Fraction;
|
|
11
|
+
private _literal: { [Key: string]: number };
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Create the monom object.
|
|
15
|
+
* @param value (optional) string
|
|
16
|
+
*/
|
|
17
|
+
constructor(value?: string) {
|
|
18
|
+
this.zero();
|
|
19
|
+
|
|
20
|
+
if (value !== undefined) {
|
|
21
|
+
// A string is given - try to parse the value.
|
|
22
|
+
this.parse(value);
|
|
23
|
+
}
|
|
34
24
|
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
*/
|
|
38
|
-
get coefficient(): Fraction {
|
|
39
|
-
return this._coefficient;
|
|
40
|
-
}
|
|
25
|
+
return this;
|
|
26
|
+
}
|
|
41
27
|
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
}
|
|
28
|
+
// ------------------------------------------
|
|
29
|
+
// Getter and setter
|
|
30
|
+
// ------------------------------------------
|
|
31
|
+
get isMonom() {
|
|
32
|
+
return true;
|
|
33
|
+
}
|
|
49
34
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
35
|
+
/**
|
|
36
|
+
* Get the coefficient as fraction
|
|
37
|
+
*/
|
|
38
|
+
get coefficient(): Fraction {
|
|
39
|
+
return this._coefficient;
|
|
40
|
+
}
|
|
56
41
|
|
|
57
|
-
|
|
42
|
+
/**
|
|
43
|
+
* Set the coefficient value of the monom
|
|
44
|
+
* @param F Fraction
|
|
45
|
+
*/
|
|
46
|
+
set coefficient(F: Fraction) {
|
|
47
|
+
this._coefficient = F;
|
|
48
|
+
}
|
|
58
49
|
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
}
|
|
64
|
-
return L;
|
|
65
|
-
} else {
|
|
50
|
+
/**
|
|
51
|
+
* Get the literal part, as dictionary
|
|
52
|
+
*/
|
|
53
|
+
get literal(): { [Key: string]: number } {
|
|
66
54
|
return this._literal;
|
|
67
55
|
}
|
|
68
|
-
}
|
|
69
56
|
|
|
70
|
-
|
|
71
|
-
* Set the literal part of the monom
|
|
72
|
-
* @param L Literal part as dictionary: <setLetter: exposant>
|
|
73
|
-
*/
|
|
74
|
-
set literal(L: { [Key: string]: number }) {
|
|
75
|
-
this._literal = L;
|
|
76
|
-
}
|
|
57
|
+
get literalSqrt(): { [Key: string]: number } {
|
|
77
58
|
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
this._literal[v[1]] = 0;
|
|
87
|
-
}
|
|
88
|
-
this._literal[v[1]] += +v[2];
|
|
89
|
-
}
|
|
90
|
-
for (const v of [...inputStr.matchAll(/([a-z](?!\^))/g)]) {
|
|
91
|
-
// Match all single letters
|
|
92
|
-
if (!(v[1] in this._literal)) {
|
|
93
|
-
this._literal[v[1]] = 0;
|
|
59
|
+
if (this.isLitteralSquare()) {
|
|
60
|
+
let L: { [Key: string]: number } = {}
|
|
61
|
+
for (let key in this._literal) {
|
|
62
|
+
L[key] = this._literal[key] / 2
|
|
63
|
+
}
|
|
64
|
+
return L;
|
|
65
|
+
} else {
|
|
66
|
+
return this._literal;
|
|
94
67
|
}
|
|
95
|
-
this._literal[v[1]] += 1;
|
|
96
68
|
}
|
|
97
|
-
}
|
|
98
69
|
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
}
|
|
70
|
+
/**
|
|
71
|
+
* Set the literal part of the monom
|
|
72
|
+
* @param L Literal part as dictionary: <setLetter: exposant>
|
|
73
|
+
*/
|
|
74
|
+
set literal(L: { [Key: string]: number }) {
|
|
75
|
+
this._literal = L;
|
|
76
|
+
}
|
|
107
77
|
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
if (this._literal[letter] > 1) {
|
|
118
|
-
L += `^${this._literal[letter]}`;
|
|
78
|
+
/**
|
|
79
|
+
* Set the literal part of the monom from a string
|
|
80
|
+
* @param inputStr String like x^2y^3
|
|
81
|
+
*/
|
|
82
|
+
set literalStr(inputStr: string) {
|
|
83
|
+
// Match all x^n
|
|
84
|
+
for (const v of [...inputStr.matchAll(/([a-z])\^([+-]?[0-9]+)/g)]) {
|
|
85
|
+
if (!(v[1] in this._literal)) {
|
|
86
|
+
this._literal[v[1]] = 0;
|
|
119
87
|
}
|
|
88
|
+
this._literal[v[1]] += +v[2];
|
|
89
|
+
}
|
|
90
|
+
for (const v of [...inputStr.matchAll(/([a-z](?!\^))/g)]) {
|
|
91
|
+
// Match all single letters
|
|
92
|
+
if (!(v[1] in this._literal)) {
|
|
93
|
+
this._literal[v[1]] = 0;
|
|
94
|
+
}
|
|
95
|
+
this._literal[v[1]] += 1;
|
|
120
96
|
}
|
|
121
97
|
}
|
|
122
98
|
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
99
|
+
// Getter heplers.
|
|
100
|
+
/**
|
|
101
|
+
* Get the variables letters
|
|
102
|
+
*/
|
|
103
|
+
get variables(): string[] {
|
|
104
|
+
this.clone().clean();
|
|
105
|
+
return Object.keys(this._literal)
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
// Display getter
|
|
109
|
+
/**
|
|
110
|
+
* This display getter is to be used in the polynom display getter
|
|
111
|
+
*/
|
|
112
|
+
get display(): string {
|
|
113
|
+
let L: string = '';
|
|
114
|
+
for (let letter in this._literal) {
|
|
115
|
+
if (this._literal[letter] !== 0) {
|
|
116
|
+
L += `${letter}`;
|
|
117
|
+
if (this._literal[letter] > 1) {
|
|
118
|
+
L += `^${this._literal[letter]}`;
|
|
119
|
+
}
|
|
120
|
+
}
|
|
129
121
|
}
|
|
130
|
-
|
|
131
|
-
if (
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
122
|
+
|
|
123
|
+
if (L === '') {
|
|
124
|
+
// No setLetter - means it's only a number !
|
|
125
|
+
if (this._coefficient.value != 0) {
|
|
126
|
+
return `${this._coefficient.display}`;
|
|
127
|
+
} else {
|
|
128
|
+
return '';
|
|
129
|
+
}
|
|
137
130
|
} else {
|
|
138
|
-
|
|
131
|
+
if (this._coefficient.value === 1) {
|
|
132
|
+
return L;
|
|
133
|
+
} else if (this._coefficient.value === -1) {
|
|
134
|
+
return `-${L}`;
|
|
135
|
+
} else if (this._coefficient.value === 0) {
|
|
136
|
+
return '0';
|
|
137
|
+
} else {
|
|
138
|
+
return `${this._coefficient.display}${L}`;
|
|
139
|
+
}
|
|
139
140
|
}
|
|
140
141
|
}
|
|
141
|
-
}
|
|
142
142
|
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
143
|
+
get dividers(): Monom[] {
|
|
144
|
+
// Decompose only if the coefficient it a complet value
|
|
145
|
+
if (this.coefficient.denominator !== 1) {
|
|
146
|
+
return [this.clone()]
|
|
147
|
+
}
|
|
148
148
|
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
149
|
+
// Security : do not do this if greater than 10000
|
|
150
|
+
if (this.coefficient.numerator > 10000) {
|
|
151
|
+
return [this.clone()]
|
|
152
|
+
}
|
|
153
|
+
const dividers = Numeric.dividers(Math.abs(this.coefficient.numerator))
|
|
154
154
|
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
155
|
+
// Decompose the litterals parts.
|
|
156
|
+
let litterals: { [key: string]: number }[] = [];
|
|
157
|
+
for (let L in this.literal) {
|
|
158
|
+
// L is the letter.
|
|
159
|
+
litterals = this._getLitteralDividers(litterals, L)
|
|
160
|
+
}
|
|
161
161
|
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
162
|
+
const monomDividers: Monom[] = [];
|
|
163
|
+
if (litterals.length > 0 && dividers.length > 0) {
|
|
164
|
+
for (let N of dividers) {
|
|
165
|
+
for (let L of litterals) {
|
|
166
|
+
let M = new Monom();
|
|
167
|
+
M.coefficient = new Fraction(N)
|
|
168
|
+
M.literal = L
|
|
169
|
+
monomDividers.push(M)
|
|
170
|
+
}
|
|
171
|
+
}
|
|
172
|
+
} else if (dividers.length === 0) {
|
|
165
173
|
for (let L of litterals) {
|
|
166
174
|
let M = new Monom();
|
|
167
|
-
M.coefficient = new Fraction(
|
|
175
|
+
M.coefficient = new Fraction().one()
|
|
168
176
|
M.literal = L
|
|
169
177
|
monomDividers.push(M)
|
|
170
178
|
}
|
|
179
|
+
} else {
|
|
180
|
+
for (let N of dividers) {
|
|
181
|
+
let M = new Monom();
|
|
182
|
+
M.coefficient = new Fraction(N)
|
|
183
|
+
monomDividers.push(M)
|
|
184
|
+
}
|
|
171
185
|
}
|
|
172
|
-
}else if (dividers.length===0) {
|
|
173
|
-
for (let L of litterals) {
|
|
174
|
-
let M = new Monom();
|
|
175
|
-
M.coefficient = new Fraction().one()
|
|
176
|
-
M.literal = L
|
|
177
|
-
monomDividers.push(M)
|
|
178
|
-
}
|
|
179
|
-
} else {
|
|
180
|
-
for (let N of dividers) {
|
|
181
|
-
let M = new Monom();
|
|
182
|
-
M.coefficient = new Fraction(N)
|
|
183
|
-
monomDividers.push(M)
|
|
184
|
-
}
|
|
185
|
-
}
|
|
186
186
|
|
|
187
|
-
|
|
188
|
-
|
|
187
|
+
return monomDividers.length === 0 ? [new Monom().one()] : monomDividers;
|
|
188
|
+
}
|
|
189
189
|
|
|
190
|
-
|
|
191
|
-
|
|
190
|
+
private _getLitteralDividers(arr: { [key: string]: number }[], letter: string): { [key: string]: number }[] {
|
|
191
|
+
let tmpList: { [key: string]: number }[] = [];
|
|
192
192
|
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
let litt: { [key: string]: number } = {}
|
|
196
|
-
litt[letter] = d
|
|
197
|
-
tmpList.push(litt)
|
|
198
|
-
} else {
|
|
199
|
-
for (let item of arr) {
|
|
193
|
+
for (let d = 0; d <= this.literal[letter]; d++) {
|
|
194
|
+
if (arr.length === 0) {
|
|
200
195
|
let litt: { [key: string]: number } = {}
|
|
201
|
-
for(let currentLetter in item){
|
|
202
|
-
litt[currentLetter] = item[currentLetter]
|
|
203
|
-
}
|
|
204
196
|
litt[letter] = d
|
|
205
197
|
tmpList.push(litt)
|
|
198
|
+
} else {
|
|
199
|
+
for (let item of arr) {
|
|
200
|
+
let litt: { [key: string]: number } = {}
|
|
201
|
+
for (let currentLetter in item) {
|
|
202
|
+
litt[currentLetter] = item[currentLetter]
|
|
203
|
+
}
|
|
204
|
+
litt[letter] = d
|
|
205
|
+
tmpList.push(litt)
|
|
206
|
+
}
|
|
206
207
|
}
|
|
207
208
|
}
|
|
209
|
+
return tmpList;
|
|
208
210
|
}
|
|
209
|
-
return tmpList;
|
|
210
|
-
}
|
|
211
211
|
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
212
|
+
/**
|
|
213
|
+
* Display the monom, forcing the '+' sign to appear
|
|
214
|
+
*/
|
|
215
|
+
get displayWithSign(): string {
|
|
216
|
+
// TODO: Rename or remove this getter ?
|
|
217
|
+
let d: String = this.display;
|
|
218
|
+
return (d[0] !== '-' ? '+' : '') + d;
|
|
219
|
+
}
|
|
220
220
|
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
221
|
+
/**
|
|
222
|
+
* Get the tex output of the monom
|
|
223
|
+
*/
|
|
224
|
+
get tex(): string {
|
|
225
|
+
let L: string = '';
|
|
226
|
+
for (let letter in this._literal) {
|
|
227
|
+
if (this._literal[letter] !== 0) {
|
|
228
|
+
L += `${letter}`;
|
|
229
|
+
if (this._literal[letter] > 1) {
|
|
230
|
+
L += `^${this._literal[letter]}`;
|
|
231
|
+
}
|
|
231
232
|
}
|
|
232
233
|
}
|
|
233
|
-
}
|
|
234
234
|
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
} else {
|
|
243
|
-
if (this._coefficient.value === 1) {
|
|
244
|
-
return L;
|
|
245
|
-
} else if (this._coefficient.value === -1) {
|
|
246
|
-
return `-${L}`;
|
|
247
|
-
} else if (this._coefficient.value === 0) {
|
|
248
|
-
return '0';
|
|
235
|
+
if (L === '') {
|
|
236
|
+
// No setLetter - means it's only a number !
|
|
237
|
+
if (this._coefficient.value != 0) {
|
|
238
|
+
return `${this._coefficient.dfrac}`;
|
|
239
|
+
} else {
|
|
240
|
+
return '0';
|
|
241
|
+
}
|
|
249
242
|
} else {
|
|
250
|
-
|
|
243
|
+
if (this._coefficient.value === 1) {
|
|
244
|
+
return L;
|
|
245
|
+
} else if (this._coefficient.value === -1) {
|
|
246
|
+
return `-${L}`;
|
|
247
|
+
} else if (this._coefficient.value === 0) {
|
|
248
|
+
return '0';
|
|
249
|
+
} else {
|
|
250
|
+
return `${this._coefficient.dfrac}${L}`;
|
|
251
|
+
}
|
|
251
252
|
}
|
|
252
253
|
}
|
|
253
|
-
}
|
|
254
|
-
|
|
255
|
-
// ------------------------------------------
|
|
256
|
-
// Creation / parsing functions
|
|
257
|
-
// -----------------------------------------
|
|
258
|
-
/**
|
|
259
|
-
* Parse a string to a monom. The string may include fraction.
|
|
260
|
-
* @param inputStr
|
|
261
|
-
*/
|
|
262
|
-
parse = (inputStr: string): Monom => {
|
|
263
|
-
// Set the literal part.
|
|
264
|
-
this.literalStr = inputStr;
|
|
265
254
|
|
|
266
|
-
//
|
|
267
|
-
|
|
255
|
+
// ------------------------------------------
|
|
256
|
+
// Creation / parsing functions
|
|
257
|
+
// -----------------------------------------
|
|
258
|
+
/**
|
|
259
|
+
* Parse a string to a monom. The string may include fraction.
|
|
260
|
+
* @param inputStr
|
|
261
|
+
*/
|
|
262
|
+
parse = (inputStr: string): Monom => {
|
|
263
|
+
// Set the literal part.
|
|
264
|
+
this.literalStr = inputStr;
|
|
265
|
+
|
|
266
|
+
// Get the coefficient
|
|
267
|
+
this._coefficient = new Fraction();
|
|
268
|
+
|
|
269
|
+
for (const v of [...inputStr.replace(/([a-z])|(\^[+-]?[0-9]+)/g, ',').split(',')]) {
|
|
270
|
+
// The value is empty.
|
|
271
|
+
if (v.trim() === '') {
|
|
272
|
+
continue;
|
|
273
|
+
}
|
|
268
274
|
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
if (v.trim() === '') {
|
|
272
|
-
continue;
|
|
275
|
+
// Multiple the current coefficient by the new found value.
|
|
276
|
+
this._coefficient.multiply(new Fraction(v.trim()));
|
|
273
277
|
}
|
|
274
278
|
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
}
|
|
278
|
-
|
|
279
|
-
return this;
|
|
280
|
-
};
|
|
279
|
+
return this;
|
|
280
|
+
};
|
|
281
281
|
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
282
|
+
/**
|
|
283
|
+
* Clone the current Monom.
|
|
284
|
+
*/
|
|
285
|
+
clone = (): Monom => {
|
|
286
|
+
let F: Monom = new Monom();
|
|
287
287
|
|
|
288
|
-
|
|
288
|
+
F.coefficient = this._coefficient.clone();
|
|
289
289
|
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
290
|
+
// Copy the literal parts.
|
|
291
|
+
for (let k in this._literal) {
|
|
292
|
+
F.setLetter(k, this._literal[k]);
|
|
293
|
+
}
|
|
294
|
+
return F;
|
|
295
|
+
};
|
|
296
|
+
|
|
297
|
+
/**
|
|
298
|
+
* Create a zero value monom
|
|
299
|
+
*/
|
|
300
|
+
zero = (): Monom => {
|
|
301
|
+
this._coefficient = new Fraction().zero();
|
|
302
|
+
this._literal = {};
|
|
303
|
+
return this;
|
|
304
|
+
};
|
|
305
|
+
|
|
306
|
+
/**
|
|
307
|
+
* Create a one value monom
|
|
308
|
+
*/
|
|
309
|
+
one = (): Monom => {
|
|
310
|
+
this._coefficient = new Fraction().one();
|
|
311
|
+
this._literal = {};
|
|
312
|
+
return this;
|
|
313
|
+
};
|
|
314
|
+
|
|
315
|
+
/**
|
|
316
|
+
* Clean the monom by removing each letters with a power of zero.
|
|
317
|
+
*/
|
|
318
|
+
clean = (): Monom => {
|
|
319
|
+
for (let letter in this._literal) {
|
|
320
|
+
if (this._literal[letter] === 0) {
|
|
321
|
+
delete this._literal[letter];
|
|
322
|
+
}
|
|
322
323
|
}
|
|
323
|
-
}
|
|
324
324
|
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
|
|
325
|
+
return this;
|
|
326
|
+
};
|
|
327
|
+
|
|
328
|
+
// ------------------------------------------
|
|
329
|
+
// Mathematical operations
|
|
330
|
+
// ------------------------------------------
|
|
331
|
+
|
|
332
|
+
/**
|
|
333
|
+
* Get the opposed
|
|
334
|
+
* Returns a monom.
|
|
335
|
+
*/
|
|
336
|
+
opposed = (): Monom => {
|
|
337
|
+
this._coefficient.opposed();
|
|
338
|
+
return this;
|
|
339
|
+
};
|
|
340
|
+
|
|
341
|
+
/**
|
|
342
|
+
* Add all similar monoms. If they aren't similar, they are simply skipped.
|
|
343
|
+
* @param M (Monom[]) The monoms to add.
|
|
344
|
+
*/
|
|
345
|
+
add = (...M: Monom[]): Monom => {
|
|
346
|
+
for (let m of M) {
|
|
347
|
+
if (this.isSameAs(m)) {
|
|
348
|
+
this._coefficient.add(m.coefficient);
|
|
349
|
+
} else {
|
|
350
|
+
console.log('Add: Is not similar: ', m.display);
|
|
351
|
+
}
|
|
351
352
|
}
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
353
|
+
return this;
|
|
354
|
+
};
|
|
355
|
+
|
|
356
|
+
/**
|
|
357
|
+
* Subtract multiple monoms
|
|
358
|
+
* @param M (Monom[]) The monoms to subtract
|
|
359
|
+
*/
|
|
360
|
+
subtract = (...M: Monom[]): Monom => {
|
|
361
|
+
for (let m of M) {
|
|
362
|
+
if (this.isSameAs(m)) {
|
|
363
|
+
this._coefficient.add(m.coefficient.clone().opposed());
|
|
364
|
+
} else {
|
|
365
|
+
console.log('Subtract: Is not similar: ', m.display);
|
|
366
|
+
}
|
|
366
367
|
}
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
368
|
+
return this;
|
|
369
|
+
};
|
|
370
|
+
|
|
371
|
+
/**
|
|
372
|
+
* Multiple multiple monoms to the current monom
|
|
373
|
+
* @param M (Monom[]) The monoms to multiply to.
|
|
374
|
+
*/
|
|
375
|
+
multiply = (...M: Monom[]): Monom => {
|
|
376
|
+
for (let m of M) {
|
|
377
|
+
// Multiply the coefficient.
|
|
378
|
+
this._coefficient.multiply(m.coefficient);
|
|
379
|
+
// Multiply the literal parts.
|
|
380
|
+
for (let letter in m.literal) {
|
|
381
|
+
this._literal[letter] = (this._literal[letter] === undefined) ? m.literal[letter] : this._literal[letter] + m.literal[letter];
|
|
382
|
+
}
|
|
382
383
|
}
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
384
|
+
return this;
|
|
385
|
+
};
|
|
386
|
+
|
|
387
|
+
multiplyByNumber = (F: Fraction | number): Monom => {
|
|
388
|
+
this._coefficient.multiply(F);
|
|
389
|
+
return this;
|
|
390
|
+
}
|
|
391
|
+
|
|
392
|
+
/**
|
|
393
|
+
* Divide the current monoms by multiple monoms
|
|
394
|
+
* @param M (Monom[])
|
|
395
|
+
*/
|
|
396
|
+
divide = (...M: Monom[]): Monom => {
|
|
397
|
+
// Depending on the given value, choose the current item
|
|
398
|
+
for (let v of M) {
|
|
399
|
+
// Divide the coefficient
|
|
400
|
+
this._coefficient.divide(v.coefficient);
|
|
401
|
+
|
|
402
|
+
// Subtract the power values
|
|
403
|
+
for (let letter in v.literal) {
|
|
404
|
+
this._literal[letter] = (this._literal[letter] === undefined) ? -v.literal[letter] : this._literal[letter] - v.literal[letter];
|
|
405
|
+
|
|
406
|
+
// If the power of a particular setLetter is zero, delete it from the literal part..
|
|
407
|
+
if (this._literal[letter] === 0) {
|
|
408
|
+
delete this._literal[letter];
|
|
409
|
+
}
|
|
409
410
|
}
|
|
410
411
|
}
|
|
411
|
-
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
this._coefficient.pow(nb);
|
|
421
|
-
for (let letter in this._literal) {
|
|
422
|
-
this._literal[letter] *= nb;
|
|
423
|
-
}
|
|
424
|
-
return this;
|
|
425
|
-
};
|
|
426
|
-
|
|
427
|
-
/**
|
|
428
|
-
* Get the nth-root of the monom
|
|
429
|
-
* @param p
|
|
430
|
-
*/
|
|
431
|
-
root = (p: number): Monom => {
|
|
432
|
-
// TODO: determiner the nth root of a monom
|
|
433
|
-
return this;
|
|
434
|
-
}
|
|
435
|
-
|
|
436
|
-
/**
|
|
437
|
-
* Return the square root of a monom
|
|
438
|
-
*/
|
|
439
|
-
sqrt = (): Monom => {
|
|
440
|
-
if (this.isSquare()) {
|
|
441
|
-
this._coefficient.sqrt();
|
|
412
|
+
return this;
|
|
413
|
+
};
|
|
414
|
+
|
|
415
|
+
/**
|
|
416
|
+
* Get the pow of a monom.
|
|
417
|
+
* @param nb (number) : Mathematical pow
|
|
418
|
+
*/
|
|
419
|
+
pow = (nb: number): Monom => {
|
|
420
|
+
this._coefficient.pow(nb);
|
|
442
421
|
for (let letter in this._literal) {
|
|
443
|
-
this._literal[letter]
|
|
422
|
+
this._literal[letter] *= nb;
|
|
444
423
|
}
|
|
424
|
+
return this;
|
|
425
|
+
};
|
|
426
|
+
|
|
427
|
+
/**
|
|
428
|
+
* Get the nth-root of the monom
|
|
429
|
+
* @param p
|
|
430
|
+
*/
|
|
431
|
+
root = (p: number): Monom => {
|
|
432
|
+
// TODO: determiner the nth root of a monom
|
|
433
|
+
return this;
|
|
434
|
+
}
|
|
435
|
+
|
|
436
|
+
/**
|
|
437
|
+
* Return the square root of a monom
|
|
438
|
+
*/
|
|
439
|
+
sqrt = (): Monom => {
|
|
440
|
+
if (this.isSquare()) {
|
|
441
|
+
this._coefficient.sqrt();
|
|
442
|
+
for (let letter in this._literal) {
|
|
443
|
+
this._literal[letter] /= 2;
|
|
444
|
+
}
|
|
445
|
+
}
|
|
446
|
+
return this.root(2);
|
|
445
447
|
}
|
|
446
|
-
return this.root(2);
|
|
447
|
-
}
|
|
448
448
|
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
449
|
+
// ------------------------------------------
|
|
450
|
+
// Compare functions
|
|
451
|
+
// ------------------------------------------
|
|
452
|
+
compare = (M: Monom, sign?: string): boolean => {
|
|
453
|
+
// TODO: Build the compare systems.
|
|
454
|
+
if (sign === undefined) {
|
|
455
|
+
sign = '=';
|
|
456
|
+
}
|
|
457
457
|
|
|
458
458
|
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
return false;
|
|
464
|
-
}
|
|
465
|
-
|
|
466
|
-
// The litteral parts are the isSame. The coefficient must be equal
|
|
467
|
-
return this._coefficient.isEqual(M.coefficient);
|
|
468
|
-
case 'same':
|
|
469
|
-
// Get the list of all variables from both monoms.
|
|
470
|
-
let M1: string[] = this.variables,
|
|
471
|
-
M2: string[] = M.variables,
|
|
472
|
-
K: string[] = M1.concat(M2.filter((item) => M1.indexOf(item) < 0));
|
|
473
|
-
|
|
474
|
-
for (let key of K) {
|
|
475
|
-
// The setLetter is not available in one of the monom
|
|
476
|
-
if (this._literal[key] === undefined || M.literal[key] === undefined) {
|
|
459
|
+
switch (sign) {
|
|
460
|
+
case '=':
|
|
461
|
+
// To be equal, they must be the isSame
|
|
462
|
+
if (!this.compare(M, 'same')) {
|
|
477
463
|
return false;
|
|
478
464
|
}
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
465
|
+
|
|
466
|
+
// The litteral parts are the isSame. The coefficient must be equal
|
|
467
|
+
return this._coefficient.isEqual(M.coefficient);
|
|
468
|
+
case 'same':
|
|
469
|
+
// Get the list of all variables from both monoms.
|
|
470
|
+
let M1: string[] = this.variables,
|
|
471
|
+
M2: string[] = M.variables,
|
|
472
|
+
K: string[] = M1.concat(M2.filter((item) => M1.indexOf(item) < 0));
|
|
473
|
+
|
|
474
|
+
for (let key of K) {
|
|
475
|
+
// The setLetter is not available in one of the monom
|
|
476
|
+
if (this._literal[key] === undefined || M.literal[key] === undefined) {
|
|
477
|
+
return false;
|
|
478
|
+
}
|
|
479
|
+
// The setLetter does not have the isSame power in each monoms.
|
|
480
|
+
if (this._literal[key] !== M.literal[key]) {
|
|
481
|
+
return false;
|
|
482
|
+
}
|
|
482
483
|
}
|
|
483
|
-
}
|
|
484
484
|
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
485
|
+
// All are positive check - the monoms are the sames.
|
|
486
|
+
return true;
|
|
487
|
+
default:
|
|
488
|
+
return false;
|
|
489
|
+
}
|
|
489
490
|
}
|
|
490
|
-
}
|
|
491
|
-
|
|
492
|
-
/**
|
|
493
|
-
* Determine if the monom is null
|
|
494
|
-
*/
|
|
495
|
-
isZero(): boolean {
|
|
496
|
-
return this._coefficient.value === 0;
|
|
497
|
-
}
|
|
498
491
|
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
492
|
+
/**
|
|
493
|
+
* Determine if the monom is null
|
|
494
|
+
*/
|
|
495
|
+
isZero(): boolean {
|
|
496
|
+
return this._coefficient.value === 0;
|
|
497
|
+
}
|
|
505
498
|
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
return this.compare(M, '=');
|
|
512
|
-
};
|
|
513
|
-
|
|
514
|
-
/**
|
|
515
|
-
* Determine if two monoms are similar
|
|
516
|
-
* @param M
|
|
517
|
-
*/
|
|
518
|
-
isSameAs = (M: Monom): boolean => {
|
|
519
|
-
return this.compare(M, 'same');
|
|
520
|
-
};
|
|
521
|
-
|
|
522
|
-
isSquare = (): boolean => {
|
|
523
|
-
if (!this.coefficient.isSquare()) {
|
|
524
|
-
return false;
|
|
499
|
+
/**
|
|
500
|
+
* Determine if the monom is one
|
|
501
|
+
*/
|
|
502
|
+
isOne(): boolean {
|
|
503
|
+
return this._coefficient.value === 1 && this.variables.length === 0;
|
|
525
504
|
}
|
|
526
|
-
return this.isLitteralSquare();
|
|
527
|
-
}
|
|
528
505
|
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
506
|
+
/**
|
|
507
|
+
* Determine if two monoms are equals
|
|
508
|
+
* @param M
|
|
509
|
+
*/
|
|
510
|
+
isEqual = (M: Monom): boolean => {
|
|
511
|
+
return this.compare(M, '=');
|
|
512
|
+
};
|
|
513
|
+
|
|
514
|
+
/**
|
|
515
|
+
* Determine if two monoms are similar
|
|
516
|
+
* @param M
|
|
517
|
+
*/
|
|
518
|
+
isSameAs = (M: Monom): boolean => {
|
|
519
|
+
return this.compare(M, 'same');
|
|
520
|
+
};
|
|
521
|
+
|
|
522
|
+
isSquare = (): boolean => {
|
|
523
|
+
if (!this.coefficient.isSquare()) {
|
|
532
524
|
return false;
|
|
533
525
|
}
|
|
526
|
+
return this.isLitteralSquare();
|
|
534
527
|
}
|
|
535
|
-
return true;
|
|
536
|
-
}
|
|
537
|
-
// ------------------------------------------
|
|
538
|
-
// Misc monoms functions
|
|
539
|
-
// -------------------------------------
|
|
540
|
-
/**
|
|
541
|
-
* Determine if a monom contains a setLetter in it's literal part
|
|
542
|
-
* @param letter
|
|
543
|
-
*/
|
|
544
|
-
hasLetter = (letter?: string): boolean => {
|
|
545
|
-
return this._literal[letter === undefined ? 'x' : letter] > 0;
|
|
546
|
-
};
|
|
547
|
-
|
|
548
|
-
/**
|
|
549
|
-
* Set the power of a particular setLetter
|
|
550
|
-
* @param letter (string) Letter to change
|
|
551
|
-
* @param pow (number) Power of the setLetter (must be positive integer.
|
|
552
|
-
*/
|
|
553
|
-
setLetter = (letter: string, pow: number): void => {
|
|
554
|
-
// If the power is not legal or is zero, remove the setLetter from the dict
|
|
555
|
-
if (pow <= 0 || !Number.isSafeInteger(pow)) {
|
|
556
|
-
if (this._literal[letter] !== undefined) {
|
|
557
|
-
delete this._literal[letter];
|
|
558
|
-
}
|
|
559
|
-
} else {
|
|
560
|
-
this._literal[letter] = pow;
|
|
561
|
-
}
|
|
562
|
-
};
|
|
563
|
-
|
|
564
|
-
/**
|
|
565
|
-
* Get the degree of a monom. If no setLetter is given, the result will be the global degree.
|
|
566
|
-
* @param letter (string) Letter to get to degree (power)
|
|
567
|
-
*/
|
|
568
|
-
degree = (letter?: string): number => {
|
|
569
|
-
if (this.variables.length === 0) {
|
|
570
|
-
return 0;
|
|
571
|
-
}
|
|
572
|
-
if (letter === undefined) {
|
|
573
|
-
// Not setLetter given -> we get the global monom degree (sum of all the letters).
|
|
574
|
-
return Object.values(this._literal).reduce((t, n) => t + n);
|
|
575
|
-
} else {
|
|
576
|
-
// A setLetter is given -> get the corresponding power.
|
|
577
|
-
return this._literal[letter] === undefined ? 0 : this._literal[letter];
|
|
578
|
-
}
|
|
579
|
-
};
|
|
580
528
|
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
|
|
529
|
+
isLitteralSquare = (): boolean => {
|
|
530
|
+
for (let letter in this.literal) {
|
|
531
|
+
if (this.literal[letter] % 2 !== 0) {
|
|
532
|
+
return false;
|
|
533
|
+
}
|
|
534
|
+
}
|
|
535
|
+
return true;
|
|
536
|
+
}
|
|
537
|
+
// ------------------------------------------
|
|
538
|
+
// Misc monoms functions
|
|
539
|
+
// -------------------------------------
|
|
540
|
+
/**
|
|
541
|
+
* Determine if a monom contains a setLetter in it's literal part
|
|
542
|
+
* @param letter
|
|
543
|
+
*/
|
|
544
|
+
hasLetter = (letter?: string): boolean => {
|
|
545
|
+
return this._literal[letter === undefined ? 'x' : letter] > 0;
|
|
546
|
+
};
|
|
547
|
+
|
|
548
|
+
/**
|
|
549
|
+
* Set the power of a particular setLetter
|
|
550
|
+
* @param letter (string) Letter to change
|
|
551
|
+
* @param pow (number) Power of the setLetter (must be positive integer.
|
|
552
|
+
*/
|
|
553
|
+
setLetter = (letter: string, pow: number): void => {
|
|
554
|
+
// If the power is not legal or is zero, remove the setLetter from the dict
|
|
555
|
+
if (pow <= 0 || !Number.isSafeInteger(pow)) {
|
|
556
|
+
if (this._literal[letter] !== undefined) {
|
|
557
|
+
delete this._literal[letter];
|
|
558
|
+
}
|
|
559
|
+
} else {
|
|
560
|
+
this._literal[letter] = pow;
|
|
561
|
+
}
|
|
562
|
+
};
|
|
563
|
+
|
|
564
|
+
/**
|
|
565
|
+
* Get the degree of a monom. If no setLetter is given, the result will be the global degree.
|
|
566
|
+
* @param letter (string) Letter to get to degree (power)
|
|
567
|
+
*/
|
|
568
|
+
degree = (letter?: string): number => {
|
|
569
|
+
if (this.variables.length === 0) {
|
|
570
|
+
return 0;
|
|
571
|
+
}
|
|
572
|
+
if (letter === undefined) {
|
|
573
|
+
// Not setLetter given -> we get the global monom degree (sum of all the letters).
|
|
574
|
+
return Object.values(this._literal).reduce((t, n) => t + n);
|
|
575
|
+
} else {
|
|
576
|
+
// A setLetter is given -> get the corresponding power.
|
|
577
|
+
return this._literal[letter] === undefined ? 0 : this._literal[letter];
|
|
578
|
+
}
|
|
579
|
+
};
|
|
587
580
|
|
|
588
|
-
|
|
589
|
-
|
|
581
|
+
/**
|
|
582
|
+
* Evaluate a monom. Each setLetter must be assigned to a Fraction.
|
|
583
|
+
* @param values Dictionary of <setLetter: Fraction>
|
|
584
|
+
*/
|
|
585
|
+
evaluate = (values: { [key: string]: Fraction | number } | Fraction | number): Fraction => {
|
|
586
|
+
let r = this.coefficient.clone();
|
|
590
587
|
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
}
|
|
588
|
+
if (typeof values === 'number' || values instanceof Fraction) {
|
|
589
|
+
let tmpValues: { [key: string]: Fraction | number } = {}
|
|
594
590
|
|
|
595
|
-
|
|
596
|
-
|
|
597
|
-
if (values[L] === undefined) {
|
|
598
|
-
return new Fraction().zero();
|
|
599
|
-
}
|
|
600
|
-
let value = new Fraction(values[L])
|
|
601
|
-
r.multiply(value.pow(this._literal[L]));
|
|
591
|
+
tmpValues[this.variables[0]] = new Fraction(values)
|
|
592
|
+
return this.evaluate(tmpValues);
|
|
602
593
|
}
|
|
603
|
-
}
|
|
604
|
-
return r;
|
|
605
|
-
};
|
|
606
|
-
|
|
607
|
-
/**
|
|
608
|
-
* Derivative the monom
|
|
609
|
-
* @param letter
|
|
610
|
-
*/
|
|
611
|
-
derivative = (letter?: string): Monom => {
|
|
612
|
-
// No setLetter given - assume it's the setLetter 'x'
|
|
613
|
-
if (letter === undefined) {
|
|
614
|
-
letter = 'x';
|
|
615
|
-
}
|
|
616
|
-
if (this.hasLetter(letter)) {
|
|
617
|
-
let d = +this._literal[letter],
|
|
618
|
-
dM = this.clone();
|
|
619
|
-
|
|
620
|
-
// Subtract one to the degree.
|
|
621
|
-
dM._literal[letter] -= 1;
|
|
622
|
-
|
|
623
|
-
// Multiply the coefficient by the previous degree
|
|
624
|
-
dM._coefficient.multiply(new Fraction('' + d));
|
|
625
|
-
return dM;
|
|
626
|
-
} else {
|
|
627
|
-
return new Monom().zero();
|
|
628
|
-
}
|
|
629
|
-
};
|
|
630
594
|
|
|
631
|
-
|
|
632
|
-
|
|
595
|
+
if (typeof values === 'object') {
|
|
596
|
+
for (let L in this._literal) {
|
|
597
|
+
if (values[L] === undefined) {
|
|
598
|
+
return new Fraction().zero();
|
|
599
|
+
}
|
|
600
|
+
let value = new Fraction(values[L])
|
|
601
|
+
r.multiply(value.pow(this._literal[L]));
|
|
602
|
+
}
|
|
603
|
+
}
|
|
604
|
+
return r;
|
|
605
|
+
};
|
|
606
|
+
|
|
607
|
+
/**
|
|
608
|
+
* Derivative the monom
|
|
609
|
+
* @param letter
|
|
610
|
+
*/
|
|
611
|
+
derivative = (letter?: string): Monom => {
|
|
612
|
+
// No setLetter given - assume it's the setLetter 'x'
|
|
613
|
+
if (letter === undefined) {
|
|
614
|
+
letter = 'x';
|
|
615
|
+
}
|
|
616
|
+
if (this.hasLetter(letter)) {
|
|
617
|
+
let d = +this._literal[letter],
|
|
618
|
+
dM = this.clone();
|
|
633
619
|
|
|
634
|
-
|
|
635
|
-
|
|
620
|
+
// Subtract one to the degree.
|
|
621
|
+
dM._literal[letter] -= 1;
|
|
636
622
|
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
623
|
+
// Multiply the coefficient by the previous degree
|
|
624
|
+
dM._coefficient.multiply(new Fraction('' + d));
|
|
625
|
+
return dM;
|
|
626
|
+
} else {
|
|
627
|
+
return new Monom().zero();
|
|
628
|
+
}
|
|
629
|
+
};
|
|
642
630
|
|
|
643
|
-
|
|
644
|
-
if(
|
|
645
|
-
|
|
631
|
+
primitive = (letter?: string): Monom => {
|
|
632
|
+
if (letter === undefined) {
|
|
633
|
+
letter = 'x'
|
|
646
634
|
}
|
|
647
|
-
|
|
648
|
-
|
|
649
|
-
|
|
650
|
-
|
|
651
|
-
|
|
652
|
-
|
|
653
|
-
|
|
654
|
-
|
|
655
|
-
|
|
656
|
-
|
|
657
|
-
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
let M = new Monom(),
|
|
661
|
-
coeffN: number[] = monoms.map(value => value.coefficient.numerator),
|
|
662
|
-
coeffD: number[] = monoms.map(value => value.coefficient.denominator),
|
|
663
|
-
n = Numeric.gcd(...coeffN),
|
|
664
|
-
d = Numeric.lcm(...coeffD);
|
|
665
|
-
|
|
666
|
-
// Get the coefficient.
|
|
667
|
-
M.coefficient = new Fraction(n, d).reduce();
|
|
668
|
-
|
|
669
|
-
// Set the literal parts - go through each monoms literal parts and get only the lowest degree of each letters.
|
|
670
|
-
for (let m of monoms) {
|
|
671
|
-
// Remove the inexistant letters from the resulting monom
|
|
672
|
-
for (let letter in M.literal) {
|
|
673
|
-
if (!(letter in m.literal)) {
|
|
674
|
-
M.literal[letter] = 0;
|
|
635
|
+
|
|
636
|
+
// Zero monom
|
|
637
|
+
let M = this.clone()
|
|
638
|
+
|
|
639
|
+
if (M.hasLetter(letter)) {
|
|
640
|
+
M.coefficient = M.coefficient.clone().divide(M.degree(letter) + 1)
|
|
641
|
+
M.setLetter(letter, M.degree(letter) + 1)
|
|
642
|
+
} else {
|
|
643
|
+
// There is no letter.
|
|
644
|
+
|
|
645
|
+
// The coefficient might be zero (=> x) or a number a (=> ax)
|
|
646
|
+
if (M.coefficient.isZero()) {
|
|
647
|
+
M.coefficient = new Fraction().one()
|
|
675
648
|
}
|
|
649
|
+
M.setLetter(letter, 1)
|
|
676
650
|
}
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
681
|
-
|
|
651
|
+
return M
|
|
652
|
+
}
|
|
653
|
+
// ----------------------------------------
|
|
654
|
+
// Static functions
|
|
655
|
+
// ----------------------------------------
|
|
656
|
+
|
|
657
|
+
/**
|
|
658
|
+
* Get the least common multiple of monoms
|
|
659
|
+
* @param monoms Array of monoms
|
|
660
|
+
*/
|
|
661
|
+
static lcm = (...monoms: Monom[]): Monom => {
|
|
662
|
+
let M = new Monom(),
|
|
663
|
+
coeffN: number[] = monoms.map(value => value.coefficient.numerator),
|
|
664
|
+
coeffD: number[] = monoms.map(value => value.coefficient.denominator),
|
|
665
|
+
n = Numeric.gcd(...coeffN),
|
|
666
|
+
d = Numeric.lcm(...coeffD);
|
|
667
|
+
|
|
668
|
+
// Get the coefficient.
|
|
669
|
+
M.coefficient = new Fraction(n, d).reduce();
|
|
670
|
+
|
|
671
|
+
// Set the literal parts - go through each monoms literal parts and get only the lowest degree of each letters.
|
|
672
|
+
for (let m of monoms) {
|
|
673
|
+
// Remove the inexistant letters from the resulting monom
|
|
674
|
+
for (let letter in M.literal) {
|
|
675
|
+
if (!(letter in m.literal)) {
|
|
676
|
+
M.literal[letter] = 0;
|
|
677
|
+
}
|
|
678
|
+
}
|
|
679
|
+
for (let letter in m.literal) {
|
|
680
|
+
if (M.literal[letter] === undefined && m.literal[letter] > 0) {
|
|
681
|
+
M.literal[letter] = m.literal[letter];
|
|
682
|
+
} else {
|
|
683
|
+
M.literal[letter] = Math.min(m.literal[letter], M.literal[letter]);
|
|
684
|
+
}
|
|
682
685
|
}
|
|
683
686
|
}
|
|
684
|
-
}
|
|
685
687
|
|
|
686
|
-
|
|
687
|
-
|
|
688
|
+
return M;
|
|
689
|
+
};
|
|
688
690
|
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
692
|
-
|
|
693
|
-
|
|
694
|
-
|
|
691
|
+
/**
|
|
692
|
+
* Multiply two monoms and return a NEW monom.
|
|
693
|
+
* @param monoms
|
|
694
|
+
*/
|
|
695
|
+
static xmultiply = (...monoms: Monom[]): Monom => {
|
|
696
|
+
let M = new Monom().one();
|
|
695
697
|
|
|
696
|
-
|
|
697
|
-
|
|
698
|
-
|
|
698
|
+
for (let m of monoms) {
|
|
699
|
+
M.multiply(m);
|
|
700
|
+
}
|
|
699
701
|
|
|
700
|
-
|
|
701
|
-
|
|
702
|
+
return M;
|
|
703
|
+
};
|
|
702
704
|
|
|
703
705
|
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
706
|
+
// TODO: The rest of the functions are not used or unnecessary ?
|
|
707
|
+
/**
|
|
708
|
+
* Determine if multiple monoms are similar
|
|
709
|
+
* @param M
|
|
710
|
+
*/
|
|
711
|
+
areSameAs = (...M: Monom[]): boolean => {
|
|
712
|
+
let result: boolean = true;
|
|
711
713
|
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
714
|
+
// Check all monoms if they are the isSame as the "this" one.
|
|
715
|
+
for (let i = 0; i < M.length; i++) {
|
|
716
|
+
if (!this.isSameAs(M[i])) {
|
|
717
|
+
return false;
|
|
718
|
+
}
|
|
716
719
|
}
|
|
717
|
-
}
|
|
718
720
|
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
|
|
725
|
-
|
|
726
|
-
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
return false;
|
|
731
|
-
}
|
|
732
|
-
|
|
733
|
-
// Check all coefficient. They must be equals.
|
|
734
|
-
for (let m of M) {
|
|
735
|
-
if (!this._coefficient.isEqual(m.coefficient)) {
|
|
721
|
+
// All check passed -> all the monoms are similar.
|
|
722
|
+
return result;
|
|
723
|
+
};
|
|
724
|
+
|
|
725
|
+
/**
|
|
726
|
+
* Determine if multiple monoms are equals
|
|
727
|
+
* @param M
|
|
728
|
+
*/
|
|
729
|
+
areEquals = (...M: Monom[]): boolean => {
|
|
730
|
+
// They are not similar.
|
|
731
|
+
if (!this.areSameAs(...M)) {
|
|
736
732
|
return false;
|
|
737
733
|
}
|
|
738
|
-
}
|
|
739
734
|
|
|
740
|
-
|
|
741
|
-
|
|
742
|
-
|
|
735
|
+
// Check all coefficient. They must be equals.
|
|
736
|
+
for (let m of M) {
|
|
737
|
+
if (!this._coefficient.isEqual(m.coefficient)) {
|
|
738
|
+
return false;
|
|
739
|
+
}
|
|
740
|
+
}
|
|
743
741
|
|
|
744
|
-
|
|
742
|
+
// All checks passed.
|
|
743
|
+
return true;
|
|
744
|
+
};
|
|
745
|
+
|
|
746
|
+
}
|