00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043 #ifndef XFormulaAutomatonH
00044 #define XFormulaAutomatonH
00045
00046
00047 #include <zeusmath/System/Interfaces/IXFormulaAutomaton.hpp>
00048 #include <zeusmath/System/Interfaces/IAngle.hpp>
00049 #include <zeusbase/System/SingleLinkedList.hpp>
00050 #include <zeusbase/System/XObject.h>
00051 #include <zeusbase/System/VariableResolver.h>
00052 #include <zeusbase/System/StringMap.hpp>
00053 #include <zeusbase/System/Set.hpp>
00054 #include <zeusbase/System/XObjectFactory.h>
00055
00056 BEGIN_NAMESPACE_Zeus
00057
00058 class TFormulaParser;
00059 class IXFormulaAutomatonObserver;
00060
00061
00065
00066 zeusmath_class TXFormulaAutomaton : public TXObject, public IXFormulaAutomaton
00067 {
00068 public:
00069 TXFormulaAutomaton(IXMLNode& rNode);
00070
00071
00072 virtual Retval MQUALIFIER getValue(const IString& rName, Float& rfValue);
00073 virtual bool MQUALIFIER isLocked() const;
00074 virtual bool MQUALIFIER isValid() const;
00075 virtual void MQUALIFIER lockEvaluation();
00076 virtual void MQUALIFIER unlockEvaluation();
00077 virtual Retval MQUALIFIER setInputValue(const IString& rName, const Float& rfValue);
00078
00079
00080 virtual bool MQUALIFIER freeze();
00081 virtual bool MQUALIFIER unfreeze();
00082
00083
00084 virtual Retval MQUALIFIER attach(IObserver& rObserver);
00085 virtual Retval MQUALIFIER detach(IObserver& rObserver);
00086
00087
00088 MEMORY_MANAGER_DECL
00089
00090 REG_SUB_BEGIN(TXFormulaAutomaton)
00091 REG_SUB_ADD(TXFormulaAutomaton, L"TXFormulaAutomaton");
00092 REG_SUB_END
00093
00094 protected:
00095 virtual ~TXFormulaAutomaton();
00096
00097 Retval evaluate_internal(bool bAll);
00098
00099 private:
00100
00103
00104 class TPredicate : public TVariableResolver
00105 {
00106 public:
00107 TPredicate(IXMLNode& rNode, IAngle::ESystem eAngleSystem);
00108
00109 void attachObserver(IXFormulaAutomatonObserver& rObserver);
00110 void detachObserver(IXFormulaAutomatonObserver& rObserver);
00111 Retval calculateValue(TSet<TPredicate*>& rSetOfUnCalculatedPredicates);
00112
00113 inline Float getCalculationValue() const { return m_fValue; }
00114 inline TString getCondition() const { return m_strCondition; }
00115 inline TString getFormula() const { return m_mapFormula.getItemConst(TString(L"")); }
00116 inline TString getFormula(const TString& rConditionValue) const { return m_mapFormula.getItemConst(rConditionValue); }
00117 inline TString getName() const { return m_strName; }
00118 inline bool isCalculated() const { return m_bCalculated; }
00119 inline bool isValid() const { return m_bValid; }
00120
00121 void resetCalculationValue();
00122 inline void setCalculationValue(const Float& rValue) { m_fValue = rValue; }
00123
00124 void resolveDependancies(TStringMap<TPredicate*>& rMap);
00125 void releaseDependancies();
00126 void releaseObservers();
00127
00128 protected:
00129 virtual ~TPredicate();
00130 void addPredecessor(TPredicate& rPredicate);
00131 void addSuccessor(TPredicate& rPredicate);
00132 void notifyObservers();
00133
00134
00135 virtual Retval resolveVariable(const TString& rName, TString& rValue);
00136
00137 private:
00139 IXMLNode& m_rNode;
00141 TString m_strName;
00143 TString m_strCondition;
00145 TStringMap<TString> m_mapFormula;
00147 bool m_bCalculated;
00149 bool m_bValid;
00151 Float m_fValue;
00153 TStringMap<TPredicate*> m_mapPredecessors;
00155 TStringMap<TPredicate*> m_mapSuccessors;
00157 IAngle::ESystem m_eAngleSystem;
00159 TSingleLinkedList<IXFormulaAutomatonObserver*> m_lstObservers;
00160 };
00161
00163 Int m_iLock;
00165 TStringMap<TPredicate*> m_mapInputVariables;
00167 TStringMap<TPredicate*> m_mapPredicates;
00169 TStringMap<TPredicate*> m_mapOutputVariables;
00170
00171 void releaseInstances();
00172 };
00173
00174
00177
00178 inline bool MQUALIFIER TXFormulaAutomaton::isLocked() const
00179 {
00180 return (m_iLock > 0);
00181 }
00182
00183
00186
00187 inline void MQUALIFIER TXFormulaAutomaton::lockEvaluation()
00188 {
00189 ++m_iLock;
00190 }
00191
00192
00195
00196 inline void MQUALIFIER TXFormulaAutomaton::unlockEvaluation()
00197 {
00198 m_iLock--;
00199 if (m_iLock <= 0)
00200 {
00201 m_iLock = 0;
00202 evaluate_internal(true);
00203 }
00204 }
00205
00206 END_NAMESPACE_Zeus
00207
00208 #endif