1 | /* |
2 | Qalculate |
3 | |
4 | Copyright (C) 2003-2007 Niklas Knutsson (nq@altern.org) |
5 | |
6 | This program is free software; you can redistribute it and/or modify |
7 | it under the terms of the GNU General Public License as published by |
8 | the Free Software Foundation; either version 2 of the License, or |
9 | (at your option) any later version. |
10 | */ |
11 | |
12 | #ifndef VARIABLE_H |
13 | #define VARIABLE_H |
14 | |
15 | #include <libqalculate/ExpressionItem.h> |
16 | #include <libqalculate/includes.h> |
17 | |
18 | /** @file */ |
19 | |
20 | #define DECLARE_BUILTIN_VARIABLE(x) class x : public DynamicVariable { \ |
21 | private: \ |
22 | void calculate() const; \ |
23 | public: \ |
24 | x(); \ |
25 | x(const x *variable) {set(variable);} \ |
26 | ExpressionItem *copy() const {return new x(this);} \ |
27 | }; |
28 | |
29 | /// Type assumption. |
30 | /** |
31 | * Each type is a subset of the type above. |
32 | */ |
33 | typedef enum { |
34 | ASSUMPTION_TYPE_NONE = 0, |
35 | /// Multiplication is NOT commutative |
36 | ASSUMPTION_TYPE_NONMATRIX = 1, |
37 | ASSUMPTION_TYPE_NUMBER = 2, |
38 | /// im(x) != 0 |
39 | ASSUMPTION_TYPE_COMPLEX = 3, |
40 | ASSUMPTION_TYPE_REAL = 4, |
41 | ASSUMPTION_TYPE_RATIONAL = 5, |
42 | ASSUMPTION_TYPE_INTEGER = 6 |
43 | } AssumptionType; |
44 | |
45 | /// Signedness assumption. |
46 | typedef enum { |
47 | /// x = ? |
48 | ASSUMPTION_SIGN_UNKNOWN, |
49 | /// x > 0 |
50 | ASSUMPTION_SIGN_POSITIVE, |
51 | /// x >= 0 |
52 | ASSUMPTION_SIGN_NONNEGATIVE, |
53 | /// x < 0 |
54 | ASSUMPTION_SIGN_NEGATIVE, |
55 | /// x <= 0 |
56 | ASSUMPTION_SIGN_NONPOSITIVE, |
57 | /// x != 0 |
58 | ASSUMPTION_SIGN_NONZERO |
59 | } AssumptionSign; |
60 | |
61 | /// Type of variable |
62 | typedef enum { |
63 | /// class Variable |
64 | SUBTYPE_VARIABLE, |
65 | /// class UnknownVariable |
66 | SUBTYPE_UNKNOWN_VARIABLE, |
67 | /// class KnownVariable |
68 | SUBTYPE_KNOWN_VARIABLE |
69 | } VariableSubtype; |
70 | |
71 | /// An assumption about an unknown mathematical value. |
72 | /** Assumptions have a type and a sign. The type describes the type of the value -- if it represents a number or something else, and what type of number is represented. |
73 | * The sign restricts the signedness of a number. The sign generally only applies the assumptions representing a number. |
74 | * The assumption class also includes max and min values, which however are not used anywhere yet. |
75 | */ |
76 | class Assumptions { |
77 | |
78 | protected: |
79 | |
80 | AssumptionType i_type; |
81 | AssumptionSign i_sign; |
82 | Number *fmin, *fmax; |
83 | bool b_incl_min, b_incl_max; |
84 | |
85 | public: |
86 | |
87 | Assumptions(); |
88 | ~Assumptions(); |
89 | |
90 | bool isPositive(); |
91 | bool isNegative(); |
92 | bool isNonNegative(); |
93 | bool isNonPositive(); |
94 | bool isInteger(); |
95 | bool isNumber(); |
96 | bool isRational(); |
97 | bool isReal(); |
98 | bool isComplex(); |
99 | bool isNonZero(); |
100 | bool isNonMatrix(); |
101 | |
102 | AssumptionType type(); |
103 | AssumptionSign sign(); |
104 | void setType(AssumptionType ant); |
105 | void setSign(AssumptionSign as); |
106 | |
107 | void setMin(const Number *nmin); |
108 | void setIncludeEqualsMin(bool include_equals); |
109 | bool includeEqualsMin() const; |
110 | const Number *min() const; |
111 | void setMax(const Number *nmax); |
112 | void setIncludeEqualsMax(bool include_equals); |
113 | bool includeEqualsMax() const; |
114 | const Number *max() const; |
115 | |
116 | }; |
117 | |
118 | /// Abstract base class for variables. |
119 | /** A variable is an alpha-numerical representation of a known or unknown value. |
120 | */ |
121 | class Variable : public ExpressionItem { |
122 | |
123 | public: |
124 | |
125 | Variable(string cat_, string name_, string title_ = "" , bool is_local = true, bool is_builtin = false, bool is_active = true); |
126 | Variable(); |
127 | Variable(const Variable *variable); |
128 | virtual ~Variable(); |
129 | virtual ExpressionItem *copy() const = 0; |
130 | virtual void set(const ExpressionItem *item); |
131 | virtual int type() const {return TYPE_VARIABLE;} |
132 | /** Returns the subtype of the variable, corresponding to which subsubclass the object belongs to. |
133 | * |
134 | * @returns ::VariableSubtype. |
135 | */ |
136 | virtual int subtype() const {return SUBTYPE_VARIABLE;} |
137 | /** Returns if the variable has a known value (as oppossed to assumptions). |
138 | * |
139 | * @returns true if the variable is of class KnownVariable, false if UnknownVariable. |
140 | */ |
141 | virtual bool isKnown() const = 0; |
142 | |
143 | /** Returns if the variable represents a positive value. |
144 | */ |
145 | virtual bool representsPositive(bool = false) {return false;} |
146 | virtual bool representsNegative(bool = false) {return false;} |
147 | virtual bool representsNonNegative(bool = false) {return false;} |
148 | virtual bool representsNonPositive(bool = false) {return false;} |
149 | virtual bool representsInteger(bool = false) {return false;} |
150 | virtual bool representsNumber(bool = false) {return false;} |
151 | virtual bool representsRational(bool = false) {return false;} |
152 | virtual bool representsReal(bool = false) {return false;} |
153 | virtual bool representsComplex(bool = false) {return false;} |
154 | virtual bool representsNonZero(bool = false) {return false;} |
155 | virtual bool representsEven(bool = false) {return false;} |
156 | virtual bool representsOdd(bool = false) {return false;} |
157 | virtual bool representsUndefined(bool = false, bool = false, bool = false) {return false;} |
158 | virtual bool representsBoolean() {return false;} |
159 | virtual bool representsNonMatrix() {return false;} |
160 | |
161 | }; |
162 | |
163 | /// A variable with unknown value. |
164 | /** Unknown variables have an associated assumption object. |
165 | */ |
166 | class UnknownVariable : public Variable { |
167 | |
168 | protected: |
169 | |
170 | Assumptions *o_assumption; |
171 | |
172 | public: |
173 | |
174 | /** Create an unknown. |
175 | * |
176 | * @param cat_ Category that the variable belongs to. |
177 | * @param name_ Initial name of the variable. |
178 | * @param title_ Descriptive name. |
179 | * @param is_local If the variable is local/user-defined or global. |
180 | * @param is_builtin If the variable is builtin and not modifiable. |
181 | * @param is_active If the variable is active and can be used in expressions. |
182 | */ |
183 | UnknownVariable(string cat_, string name_, string title_ = "" , bool is_local = true, bool is_builtin = false, bool is_active = true); |
184 | /** Create an empty unknown variable. |
185 | */ |
186 | UnknownVariable(); |
187 | /** Create a copy of an unknown variable. |
188 | * |
189 | * @param variable Unknown variable to copy. |
190 | */ |
191 | UnknownVariable(const UnknownVariable *variable); |
192 | virtual ~UnknownVariable(); |
193 | virtual ExpressionItem *copy() const; |
194 | virtual void set(const ExpressionItem *item); |
195 | bool isKnown() const {return false;} |
196 | |
197 | /** Sets the assumptions of the unknown variable. |
198 | * |
199 | * @param ass Assumptions. |
200 | */ |
201 | void setAssumptions(Assumptions *ass); |
202 | /** Returns the assumptions of the unknown variable. |
203 | * |
204 | * @returns Assumptions of the unknown variable. |
205 | */ |
206 | Assumptions *assumptions(); |
207 | int subtype() const {return SUBTYPE_UNKNOWN_VARIABLE;} |
208 | |
209 | virtual bool representsPositive(bool = false); |
210 | virtual bool representsNegative(bool = false); |
211 | virtual bool representsNonNegative(bool = false); |
212 | virtual bool representsNonPositive(bool = false); |
213 | virtual bool representsInteger(bool = false); |
214 | virtual bool representsNumber(bool = false); |
215 | virtual bool representsRational(bool = false); |
216 | virtual bool representsReal(bool = false); |
217 | virtual bool representsComplex(bool = false); |
218 | virtual bool representsNonZero(bool = false); |
219 | virtual bool representsNonMatrix(); |
220 | |
221 | }; |
222 | |
223 | /// A variable with a known value. |
224 | /** Known variables have an associated value. The value can be a simple number or a full mathematical expression. The known variable class is used both for variable values and constants. |
225 | * |
226 | * The value can be provided as an expression in the form of a text string or as a mathematical value in the form of an object of the MathStructure class. |
227 | * The text string is parsed when needed, which saves time when loading many variable definitions which might not be used, at least not immediately. |
228 | */ |
229 | class KnownVariable : public Variable { |
230 | |
231 | protected: |
232 | |
233 | MathStructure *mstruct; |
234 | bool b_expression; |
235 | int calculated_precision; |
236 | string sexpression; |
237 | |
238 | public: |
239 | |
240 | /** Create a known variable with a value. |
241 | * |
242 | * @param cat_ Category that the variable belongs to. |
243 | * @param name_ Initial name of the variable. |
244 | * @param o Value. |
245 | * @param title_ Descriptive name. |
246 | * @param is_local If the variable is local/user-defined or global. |
247 | * @param is_builtin If the variable is builtin and not modifiable. |
248 | * @param is_active If the variable is active and can be used in expressions. |
249 | */ |
250 | KnownVariable(string cat_, string name_, const MathStructure &o, string title_ = "" , bool is_local = true, bool is_builtin = false, bool is_active = true); |
251 | /** Create a known variable with an text string expression. |
252 | * |
253 | * @param cat_ Category that the variable belongs to. |
254 | * @param name_ Initial name of the variable. |
255 | * @param expression_ Expression. |
256 | * @param title_ Descriptive name. |
257 | * @param is_local If the variable is local/user-defined or global. |
258 | * @param is_builtin If the variable is builtin and not modifiable. |
259 | * @param is_active If the variable is active and can be used in expressions. |
260 | */ |
261 | KnownVariable(string cat_, string name_, string expression_, string title_ = "" , bool is_local = true, bool is_builtin = false, bool is_active = true); |
262 | /** Create an empty known variable. Primarily for internal use. |
263 | */ |
264 | KnownVariable(); |
265 | /** Create a copy of a known variable. |
266 | * |
267 | * @param variable Known variable to copy. |
268 | */ |
269 | KnownVariable(const KnownVariable *variable); |
270 | virtual ~KnownVariable(); |
271 | |
272 | virtual ExpressionItem *copy() const; |
273 | virtual void set(const ExpressionItem *item); |
274 | bool isKnown() const {return true;} |
275 | /** Returns if the variable has an text string expression instead of a value. |
276 | * |
277 | * @returns True if the variable has an expression instead of a value. |
278 | */ |
279 | virtual bool isExpression() const; |
280 | /** Returns the variable's string expression or an empty string if it has not got an expression. |
281 | * |
282 | * @returns The variable's expression. |
283 | */ |
284 | virtual string expression() const; |
285 | int subtype() const {return SUBTYPE_KNOWN_VARIABLE;} |
286 | |
287 | /** Sets the value of the variable. If expression is set, it is cleared. |
288 | * |
289 | * @param o Value. |
290 | */ |
291 | virtual void set(const MathStructure &o); |
292 | /** Sets the text string expression of the variable. The value is cleared. |
293 | * |
294 | * @param expression_ Expression. |
295 | */ |
296 | virtual void set(string expression_); |
297 | |
298 | /** Returns the value of the variable. If no value is set or parsed and an expression is set, the expression is parsed and resulting value returned. |
299 | * |
300 | * @returns The value of the variable.. |
301 | */ |
302 | virtual const MathStructure &get(); |
303 | |
304 | virtual bool representsPositive(bool = false); |
305 | virtual bool representsNegative(bool = false); |
306 | virtual bool representsNonNegative(bool = false); |
307 | virtual bool representsNonPositive(bool = false); |
308 | virtual bool representsInteger(bool = false); |
309 | virtual bool representsNumber(bool = false); |
310 | virtual bool representsRational(bool = false); |
311 | virtual bool representsReal(bool = false); |
312 | virtual bool representsComplex(bool = false); |
313 | virtual bool representsNonZero(bool = false); |
314 | virtual bool representsEven(bool = false); |
315 | virtual bool representsOdd(bool = false); |
316 | virtual bool representsUndefined(bool = false, bool = false, bool = false); |
317 | virtual bool representsBoolean(); |
318 | virtual bool representsNonMatrix(); |
319 | |
320 | }; |
321 | |
322 | /// Abstract base class for variables with a value which is recalculated when the precision has changed. |
323 | /** |
324 | */ |
325 | class DynamicVariable : public KnownVariable { |
326 | |
327 | protected: |
328 | |
329 | virtual void calculate() const = 0; |
330 | |
331 | public: |
332 | |
333 | DynamicVariable(string cat_, string name_, string title_ = "" , bool is_local = false, bool is_builtin = true, bool is_active = true); |
334 | DynamicVariable(const DynamicVariable *variable); |
335 | DynamicVariable(); |
336 | virtual ~DynamicVariable(); |
337 | |
338 | ExpressionItem *copy() const = 0; |
339 | void set(const ExpressionItem *item); |
340 | |
341 | const MathStructure &get(); |
342 | |
343 | void set(const MathStructure &o); |
344 | void set(string expression_); |
345 | |
346 | /** Returns the precision of the calculated value. |
347 | * |
348 | * @returns Precision of the calculated value or zero if the value has not yet been calculated. |
349 | */ |
350 | int calculatedPrecision() const; |
351 | |
352 | virtual bool representsPositive(bool = false) {return true;} |
353 | virtual bool representsNegative(bool = false) {return false;} |
354 | virtual bool representsNonNegative(bool = false) {return true;} |
355 | virtual bool representsNonPositive(bool = false) {return false;} |
356 | virtual bool representsInteger(bool = false) {return false;} |
357 | virtual bool representsNumber(bool = false) {return true;} |
358 | virtual bool representsRational(bool = false) {return false;} |
359 | virtual bool representsReal(bool = false) {return true;} |
360 | virtual bool representsComplex(bool = false) {return false;} |
361 | virtual bool representsNonZero(bool = false) {return true;} |
362 | virtual bool representsEven(bool = false) {return false;} |
363 | virtual bool representsOdd(bool = false) {return false;} |
364 | virtual bool representsUndefined(bool = false, bool = false, bool = false) {return false;} |
365 | virtual bool representsBoolean() {return false;} |
366 | virtual bool representsNonMatrix() {return true;} |
367 | |
368 | }; |
369 | |
370 | /// Dynamic variable for Pi |
371 | DECLARE_BUILTIN_VARIABLE(PiVariable) |
372 | /// Dynamic variable for e, the base of natural logarithms |
373 | DECLARE_BUILTIN_VARIABLE(EVariable) |
374 | /// Dynamic variable for Euler's constant |
375 | DECLARE_BUILTIN_VARIABLE(EulerVariable) |
376 | /// Dynamic variable for Catalan's constant |
377 | DECLARE_BUILTIN_VARIABLE(CatalanVariable) |
378 | |
379 | |
380 | #endif |
381 | |