hyb_reachability.cpp
Go to the documentation of this file.
1 /** @file hyb_reachability.cpp Reachable states of linear hybrid automata */
2 
3 /*
4  Hybrid systems plug-in for FAU Discrete Event Systems Library
5 
6  Copyright (C) 2017 Thomas Moor
7 
8 */
9 
10 
11 
12 #include "hyb_reachability.h"
13 #include "hyb_compute.h"
14 
15 namespace faudes {
16 
17 
18 /*
19 *************************************************************
20 *************************************************************
21 
22 Implementation: HybridStateSet
23 
24 *************************************************************
25 *************************************************************
26 */
27 
28 /** constructors */
30 
31 /** copy constrcutor */
33 {
34  Assign(rOther);
35 }
36 
37 /** destructor */
39  /* delete all polyhedra */
40  IndexSet::Iterator qit=LocationsBegin();
41  IndexSet::Iterator qit_end=LocationsEnd();
42  for(;qit!=qit_end;++qit) {
43  Iterator pit=StatesBegin(*qit);
44  Iterator pit_end=StatesEnd(*qit);
45  for(;pit!=pit_end;++pit) delete *pit;
46  }
47 }
48 
49 /** assignment */
51  /* delete all polyhedra */
52  IndexSet::Iterator qit=LocationsBegin();
53  IndexSet::Iterator qit_end=LocationsEnd();
54  for(;qit!=qit_end;++qit) {
55  Iterator pit=StatesBegin(*qit);
56  Iterator pit_end=StatesEnd(*qit);
57  for(;pit!=pit_end;++pit) delete *pit;
58  }
59  mLocations.Clear();
60  mStates.clear();
61  /* copy all polyhedra */
62  qit=rOther.LocationsBegin();
63  qit_end=rOther.LocationsEnd();
64  for(;qit!=qit_end;++qit) {
65  Insert(*qit);
66  Iterator pit=rOther.StatesBegin(*qit);
67  Iterator pit_end=rOther.StatesEnd(*qit);
68  for(;pit!=pit_end;++pit) {
69  Polyhedron* poly = new Polyhedron(**pit);
70  Insert(*qit,poly);
71  }
72  }
73 }
74 
75 /** access to locations */
77  return mLocations;
78 }
79 IndexSet::Iterator HybridStateSet::LocationsBegin(void) const {
80  return mLocations.Begin();
81 }
82 IndexSet::Iterator HybridStateSet::LocationsEnd(void) const {
83  return mLocations.End();
84 }
85 
86 /** access to polyhedra of states */
88  HybridStateSet* fakeconst = const_cast<HybridStateSet*>(this);
89  return fakeconst->mStates[q].begin();
90 }
92  HybridStateSet* fakeconst = const_cast<HybridStateSet*>(this);
93  return fakeconst->mStates[q].end();
94 }
95 
96 /** insert / erase (we take owvership of polyhedra) */
98  mLocations.Insert(q);
99 }
101  mLocations.Insert(q);
102  mStates[q].push_back(states);
103 }
105  /* delete all polyhedra */
106  Iterator pit=StatesBegin(q);
107  Iterator pit_end=StatesEnd(q);
108  for(;pit!=pit_end;++pit) delete *pit;
109  mStates.erase(q);
110 }
112  /* delete all polyhedra */
113  IndexSet::Iterator qit=LocationsBegin();
114  IndexSet::Iterator qit_end=LocationsEnd();
115  for(;qit!=qit_end;++qit)
116  Erase(*qit);
117 }
118 
119 bool HybridStateSet::IsEmpty(void) const {
120  /* test all polyhedra */
121  IndexSet::Iterator qit=LocationsBegin();
122  IndexSet::Iterator qit_end=LocationsEnd();
123  for(;qit!=qit_end;++qit) {
124  Iterator pit=StatesBegin(*qit);
125  Iterator pit_end=StatesEnd(*qit);
126  for(;pit!=pit_end;++pit)
127  if(!PolyIsEmpty(**pit)) return false;
128  }
129  return true;
130 }
131 
132 
133 /** inspect */
135  FAUDES_WRITE_CONSOLE("%%%%% dump: hybrid state set");
136  /* loop all locations */
137  IndexSet::Iterator qit=LocationsBegin();
138  IndexSet::Iterator qit_end=LocationsEnd();
139  for(;qit!=qit_end;++qit) {
140  /* report */
141  FAUDES_WRITE_CONSOLE("%%% location: " << lha.SStr(*qit));
142  /* loop all polyhedra */
143  Iterator pit=StatesBegin(*qit);
144  Iterator pit_end=StatesEnd(*qit);
145  for(;pit!=pit_end;++pit)
146  PolyDWrite(**pit);
147  }
148  FAUDES_WRITE_CONSOLE("%%%%% dump: done");
149 }
150 
151 
152 
153 /*
154 *************************************************************
155 *************************************************************
156 
157 Implementation: Reachability
158 
159 *************************************************************
160 *************************************************************
161 */
162 
163 void LhaReach(
164  const LinearHybridAutomaton& lha,
165  const HybridStateSet& states,
166  std::map< Idx, HybridStateSet* >& ostates,
167  int* pCnt) {
168 
169  // prepare result
170  std::map< Idx, HybridStateSet* >::iterator eit=ostates.begin();
171  for(;eit!=ostates.end();++eit)
172  if(eit->second) delete eit->second;
173  ostates.clear();
174 
175  // loop over all locations
176  IndexSet::Iterator qit = states.LocationsBegin();
177  IndexSet::Iterator qit_end = states.LocationsEnd();
178  for(;qit!=qit_end;++qit) {
179 
180  // get flow/invariant
181  const Polyhedron& rate = lha.Rate(*qit);
182  const Polyhedron& inv = lha.Invariant(*qit);
183  bool noflow = PolyIsEmpty(rate);
184 
185  // loop over all polyhedra
186  HybridStateSet::Iterator pit = states.StatesBegin(*qit);
187  HybridStateSet::Iterator pit_end = states.StatesEnd(*qit);
188  for(;pit!=pit_end;++pit) {
189 
190  // book keeping
191  if(pCnt && ! noflow) ++(*pCnt);
192 
193  // get states
194  Polyhedron& poly = **pit;
195 
196  // apply flow
197  Polyhedron reach;
198  PolyCopy(poly,reach);
199  PolyTimeElapse(rate,reach);
200  PolyIntersection(inv,reach);
201 
202  //FD_WARN("inv - poly - - rate -reach");
203  //inv.Write();
204  //poly.Write();
205  //rate.Write();
206  //reach.Write();
207 
208  // intersect with guard
209  TransSet::Iterator tit = lha.TransRelBegin(*qit);
210  TransSet::Iterator tit_end = lha.TransRelEnd(*qit);
211  for(;tit!=tit_end;++tit) {
212 
213  // intersect with guard
214  Polyhedron* yreach=new Polyhedron();
215  PolyCopy(reach,*yreach);
216  PolyIntersection(lha.Guard(*tit),*yreach);
217 
218  // if empty, delete and continue
219  if(PolyIsEmpty(*yreach)) {
220  delete yreach;
221  continue;
222  }
223 
224  // apply reset, intersect with target invariant
225  PolyLinearRelation(lha.Reset(*tit),*yreach);
226  PolyIntersection(lha.Invariant(tit->X2),*yreach);
227 
228  // if empty, delete and continue
229  /*
230  if(PolyIsEmpty(*yreach)) {
231  delete yreach;
232  continue;
233  }
234  */
235 
236  // record result
237  PolyFinalise(*yreach);
238  if(ostates.find(tit->Ev)==ostates.end())
239  ostates[tit->Ev] = new HybridStateSet();
240  ostates[tit->Ev]->Insert(tit->X2,yreach);
241 
242  } // loop guards
243 
244  } // loop polyherda
245 
246  } // loop locations
247 }
248 
249 } // namespace faudes
#define FAUDES_WRITE_CONSOLE(message)
Debug: output macro for optional redirection of all console output.
Set of states in an hybrid automata.
std::list< Polyhedron * >::const_iterator Iterator
access to polyhedra of states
const IndexSet & Locations(void)
access to locations
std::map< Idx, std::list< Polyhedron * > > mStates
void DWrite(const LinearHybridAutomaton &lha)
inspect
Iterator StatesEnd(Idx q) const
IndexSet::Iterator LocationsBegin(void) const
bool IsEmpty(void) const
test emptyness
HybridStateSet(void)
constructors
StateSet mLocations
payload
void Assign(const HybridStateSet &rOther)
assignment
~HybridStateSet(void)
destructor
void Insert(Idx q)
insert / erase (we take owvership of polyhedra)
Iterator StatesBegin(Idx q) const
access to polyhedra of states
IndexSet::Iterator LocationsEnd(void) const
Set of indices.
Definition: cfl_indexset.h:78
Idx Insert(void)
Insert new index to set.
Polyhedron in R^n.
TBaseSet< Transition, TransSort::X1EvX2 >::Iterator Iterator
Iterator on transition.
Definition: cfl_transset.h:269
Generator with linear hybrid automata extensions.
const Polyhedron & Rate(Idx idx) const
Get rate of state by index.
const Polyhedron & Guard(const Transition &rTrans) const
Get guard of a transition.
const Polyhedron & Invariant(Idx idx) const
Get invariant of state by index.
const LinearRelation & Reset(const Transition &rTrans) const
Get reset of a transition.
TransSet::Iterator TransRelBegin(void) const
Iterator to Begin() of transition relation.
TransSet::Iterator TransRelEnd(void) const
Iterator to End() of transition relation.
std::string SStr(Idx index) const
Return pretty printable state name for index (eg for debugging)
virtual void Clear(void)
Clear all set.
Definition: cfl_baseset.h:1902
Iterator End(void) const
Iterator to the end of set.
Definition: cfl_baseset.h:1896
Iterator Begin(void) const
Iterator to the begin of set.
Definition: cfl_baseset.h:1891
void PolyFinalise(const Polyhedron &fpoly)
convert PPL polyhedron back to faudes data structures; this is required if we manipulate a polyhedron...
Definition: hyb_compute.cpp:53
void PolyTimeElapse(const Polyhedron &rate, Polyhedron &poly)
time elapse
void PolyDWrite(const Polyhedron &fpoly)
poly dump
void PolyCopy(const Polyhedron &src, Polyhedron &dst)
copy method
void PolyIntersection(const Polyhedron &poly, Polyhedron &res)
intersection
bool PolyIsEmpty(const Polyhedron &poly)
test emptyness
void PolyLinearRelation(const LinearRelation &reset, Polyhedron &poly)
apply reset relation A'x' + Ax <= B
libFAUDES resides within the namespace faudes.
uint32_t Idx
Type definition for index type (allways 32bit)
void LhaReach(const LinearHybridAutomaton &lha, const HybridStateSet &states, std::map< Idx, HybridStateSet * > &ostates, int *pCnt)
compute sets of reachable state per successor event

libFAUDES 2.32b --- 2024.03.01 --- c++ api documentaion by doxygen