1 #include "paranoidnumber.h"
13 ParanoidNumber::ParanoidNumber(const char * str) : m_value(0), m_op(ADD), m_next_term(NULL), m_next_factor(NULL)
17 while (str[dp] != '\0' && str[dp] != '.')
22 while (str[end] != '\0')
26 for (int i = dp-1; i >= 0; --i)
28 ParanoidNumber b(str[i]-'0');
30 //Debug("m is %s", m.Str().c_str());
31 //Debug("Add %s", b.Str().c_str());
33 //Debug("Now at %s", Str().c_str());
37 for (int i = dp+1; i < end; ++i)
40 ParanoidNumber b(str[i]-'0');
41 //Debug("%s * %s", b.Str().c_str(), n.Str().c_str());
43 //Debug("b -> %s", b.Str().c_str());
44 //Debug("Add %s", b.Str().c_str());
46 //Debug("Now at %s", Str().c_str());
49 Debug("Constructed {%s} from %s (%f)", Str().c_str(), str, ToDouble());
52 ParanoidNumber & ParanoidNumber::operator=(const ParanoidNumber & a)
58 if (a.m_next_term != NULL)
60 m_next_term = new ParanoidNumber(*(a.m_next_term));
62 if (a.m_next_factor != NULL)
64 m_next_factor = new ParanoidNumber(*(a.m_next_factor));
69 ParanoidNumber & ParanoidNumber::operator+=(const ParanoidNumber & a)
74 ParanoidNumber * nt = m_next_term;
75 ParanoidNumber * nf = m_next_factor;
78 if (m_next_factor != NULL)
80 if (m_next_factor->m_op == MULTIPLY)
81 ca /= (*m_next_factor);
83 ca *= (*m_next_factor);
98 m_next_term = new ParanoidNumber(a, ADD);
99 ParanoidNumber * t = m_next_term;
100 while (t->m_next_term != NULL)
103 //Debug("Simplify {%s} after add", Str().c_str());
108 ParanoidNumber & ParanoidNumber::operator-=(const ParanoidNumber & a)
110 // this = v + t + (a)
113 ParanoidNumber * nt = m_next_term;
114 ParanoidNumber * nf = m_next_factor;
116 ParanoidNumber ca(a, SUBTRACT);
117 if (m_next_factor != NULL)
119 if (m_next_factor->m_op == MULTIPLY)
120 ca /= (*m_next_factor);
122 ca *= (*m_next_factor);
126 m_next_factor = NULL;
137 m_next_term = new ParanoidNumber(a,SUBTRACT);
138 ParanoidNumber * t = m_next_term;
139 while (t->m_next_term != NULL)
145 //Debug("next term {%s}", m_next_term->Str().c_str());
147 //Debug("Simplify {%s} after sub", Str().c_str());
152 ParanoidNumber & ParanoidNumber::operator*=(const ParanoidNumber & a)
154 Debug("{%s} *= {%s}", Str().c_str(), a.Str().c_str());
155 // this = (vf + t) * (a)
156 ParanoidNumber * nf = m_next_factor;
157 m_next_factor = new ParanoidNumber(a, MULTIPLY);
158 ParanoidNumber * t = m_next_factor;
159 while (t->m_next_factor != NULL)
160 t = t->m_next_factor;
161 t->m_next_factor = nf;
162 if (m_next_term != NULL)
163 m_next_term->operator*=(a);
164 //Debug("Simplify after mul");
165 Debug("Simplify {%s}", Str().c_str());
171 ParanoidNumber & ParanoidNumber::operator/=(const ParanoidNumber & a)
173 //Debug("Called %s /= %s", Str().c_str(), a.Str().c_str());
174 // this = (vf + t) * (a)
175 ParanoidNumber * nf = m_next_factor;
176 m_next_factor = new ParanoidNumber(a, DIVIDE);
177 ParanoidNumber * t = m_next_factor;
178 while (t->m_next_factor != NULL)
179 t = t->m_next_factor;
180 t->m_next_factor = nf;
181 if (m_next_term != NULL)
182 m_next_term->operator/=(a);
189 void ParanoidNumber::SimplifyTerms()
191 //Debug("Simplify {%s}", Str().c_str());
192 if (m_next_term == NULL)
194 //Debug("No terms!");
198 for (ParanoidNumber * a = this; a != NULL; a = a->m_next_term)
200 ParanoidNumber * bprev = a;
201 ParanoidNumber * b = a->m_next_term;
204 //Debug("Simplify factors of %s", b->Str().c_str());
205 b->SimplifyFactors();
206 if (b->m_next_factor != NULL)
212 float f = a->m_value;
213 feclearexcept(FE_ALL_EXCEPT);
223 Fatal("Unexpected %c in term list...", OpChar(b->m_op));
226 if (!fetestexcept(FE_ALL_EXCEPT))
229 bprev->m_next_term = b->m_next_term;
230 b->m_next_term = NULL;
240 void ParanoidNumber::SimplifyFactors()
242 //Debug("Simplify {%s}", Str().c_str());
243 if (m_next_factor == NULL)
245 //Debug("No factors!");
249 for (ParanoidNumber * a = this; a != NULL; a = a->m_next_factor)
251 ParanoidNumber * bprev = a;
252 ParanoidNumber * b = a->m_next_factor;
256 if (b->m_next_term != NULL)
259 b = b->m_next_factor;
262 float f = a->m_value;
263 feclearexcept(FE_ALL_EXCEPT);
267 if (a->m_op != DIVIDE)
273 if (a->m_op != DIVIDE)
279 Fatal("Unexpected %c in factor list...",OpChar(b->m_op));
282 if (!fetestexcept(FE_ALL_EXCEPT))
286 bprev->m_next_factor = b->m_next_factor;
287 b->m_next_factor = NULL;
292 //Debug("Failed to simplify %f %c %f", a->m_value, OpChar(b->m_op), b->m_value);
294 b = b->m_next_factor;
299 void ParanoidNumber::Simplify()
305 string ParanoidNumber::Str() const
312 if (m_next_factor != NULL)
314 result += OpChar(m_op);
317 result += m_next_factor->Str();
322 result += OpChar(m_op);
326 if (m_next_term != NULL)
329 result += m_next_term->Str();