31 std::ostringstream oss;
32 oss <<
"EnhancedState{original=" <<
originalState <<
", deleted=[";
34 oss << nodeNum <<
",";
69 std::ostringstream oss;
71 oss <<
"color=" << (
color ==
WHITE ?
"WHITE" : (
color ==
RED ?
"RED" :
"GREEN")) <<
", ";
72 oss <<
"children=" <<
children.size() <<
", ";
73 oss <<
"aSet=" <<
aSet.size() <<
", ";
74 oss <<
"rSet=" <<
rSet.size() <<
"}";
92 throw Exception(
"LabeledTree::createNodeWithNumber",
97 throw Exception(
"LabeledTree::createNodeWithNumber",
118 throw Exception(
"LabeledTree::createNode",
128 for(
auto& pair :
nodes) {
136 node.
aSet.erase(nodeNumber);
137 node.
rSet.erase(nodeNumber);
151 return (it !=
idToNumber.end()) ? it->second : -1;
164 std::ostringstream oss;
166 for(
auto& pair :
nodes) {
167 oss << pair.first <<
":" << pair.second.ToString() <<
", ";
169 oss <<
"], deleted=[";
171 oss << nodeNum <<
",";
186 if(
nodes.size() != other.
nodes.size())
return false;
188 for(
auto it1 =
nodes.begin(), it2 = other.
nodes.begin();
189 it1 !=
nodes.end() && it2 != other.
nodes.end(); ++it1, ++it2) {
190 if(it1->first != it2->first)
return false;
191 if(!(it1->second == it2->second))
return false;
204 std::ostringstream oss;
208 for(
int nodeNum : deletedNodes) {
209 oss << nodeNum <<
",";
214 std::function<void(
Idx)> dfs = [&](
Idx nodeId) {
215 if(tree.
nodes.find(nodeId) == tree.
nodes.end())
return;
220 oss << static_cast<int>(node.
color) <<
":";
223 std::vector<std::pair<int, Idx>> childrenWithNumbers;
225 if(tree.
nodes.find(childId) != tree.
nodes.end()) {
226 childrenWithNumbers.push_back({tree.
getNodeNumber(childId), childId});
229 std::sort(childrenWithNumbers.begin(), childrenWithNumbers.end());
231 for(
auto& child : childrenWithNumbers) {
249 FD_DF(
"PseudoDet(" << rGen.
Name() <<
") - Paper Algorithm");
261 const int MAX_STATES = 100000;
262 const int MAX_ITERATIONS = 100000;
263 int stateCounter = 0;
264 int iterationCounter = 0;
267 const int N = 10*rGen.
Size();
268 FD_DF(
"Using N = " << N <<
" fixed nodes");
271 std::map<EnhancedState, LabeledTree> enhancedStateToTree;
274 std::map<std::string, EnhancedState> treeSignatureToEnhancedState;
283 initialTree.
nodes[root].stateLabel.Insert(*sit);
291 enhancedStateToTree[initialEnhancedState] = initialTree;
294 treeSignatureToEnhancedState[initialSig] = initialEnhancedState;
296 std::queue<EnhancedState> stateQueue;
297 stateQueue.push(initialEnhancedState);
301 while(!stateQueue.empty() && stateCounter < MAX_STATES && iterationCounter < MAX_ITERATIONS) {
307 LabeledTree currentTree = enhancedStateToTree[currentEnhancedState];
308 FD_DF(
"Processing enhanced state " << currentEnhancedState.
ToString()
309 <<
" with tree: " << currentTree.
ToString());
321 for(
auto& pair : currentTree.
nodes) {
322 Idx oldId = pair.first;
326 newTree.
nodes[newId] = oldNode;
327 newTree.
nodes[newId].children.clear();
335 for(
auto& pair : currentTree.
nodes) {
336 Idx oldParentId = pair.first;
344 if(currentTree.
nodes.find(oldChildId) == currentTree.
nodes.end())
continue;
346 int childNumber = currentTree.
nodes[oldChildId].nodeNumber;
350 newTree.
nodes[newParentId].children.push_back(newChildId);
356 std::set<int> deletedInThisStep;
359 for(
auto& pair : newTree.
nodes) {
364 std::string eventName = rGen.
EventName(event);
365 bool isEpsilonEvent = (eventName ==
"eps");
367 if (isEpsilonEvent) {
369 for(
auto& pair : newTree.
nodes) {
393 for(StateSet::Iterator sit = rootLabel.
Begin(); sit != rootLabel.
End(); ++sit) {
396 std::string eName = rGen.
EventName(*eit);
400 epsilonSuccessors.
Insert(tit->X2);
407 bool conditionSatisfied =
true;
408 for(StateSet::Iterator sit = epsilonSuccessors.
Begin(); sit != epsilonSuccessors.
End(); ++sit) {
409 if(!rootLabel.
Exists(*sit)) {
410 conditionSatisfied =
false;
415 if(conditionSatisfied) {
417 for(
auto& pair : newTree.
nodes) {
438 if(inputRabinPairs.
Size() > 0) {
442 std::vector<std::pair<Idx, TreeNode>> currentNodes;
443 for(
auto& pair : newTree.
nodes) {
444 currentNodes.push_back(pair);
447 for(
auto& nodePair : currentNodes) {
448 Idx nodeId = nodePair.first;
456 intersectionWithoutI.
Insert(*sit);
461 if(!intersectionWithoutI.
Empty()) {
464 newTree.
nodes[newChild].stateLabel = intersectionWithoutI;
466 newTree.
nodes[newChild].aSet.clear();
467 newTree.
nodes[newChild].rSet.clear();
470 FD_DF(
"Created RED child node " << newChild
471 <<
" (number " << newTree.
getNodeNumber(newChild) <<
") for node " << nodeId);
473 FD_DF(
"Warning: Could not create child node - " << e.
What());
481 for(
auto& pair : newTree.
nodes) {
482 Idx parentId = pair.first;
486 for(
size_t i = 1; i < parent.
children.size(); ++i) {
489 if(newTree.
nodes.find(youngerId) == newTree.
nodes.end())
continue;
492 for(
size_t j = 0; j < i; ++j) {
495 if(newTree.
nodes.find(olderId) == newTree.
nodes.end())
continue;
498 std::vector<Idx> toProcess;
499 toProcess.push_back(youngerId);
501 while(!toProcess.empty()) {
502 Idx currentId = toProcess.back();
503 toProcess.pop_back();
505 if(newTree.
nodes.find(currentId) == newTree.
nodes.end())
continue;
510 for(StateSet::Iterator sit = newTree.
nodes[olderId].stateLabel.Begin();
511 sit != newTree.
nodes[olderId].stateLabel.End(); ++sit) {
517 toProcess.push_back(childId);
525 std::vector<Idx> nodesToRemove;
526 for(
auto& pair : newTree.
nodes) {
527 if(pair.second.stateLabel.Empty()) {
528 nodesToRemove.push_back(pair.first);
532 for(
Idx nodeId : nodesToRemove) {
534 deletedInThisStep.insert(nodeNumber);
539 for(
auto& pair : newTree.
nodes) {
540 Idx nodeId = pair.first;
546 if(newTree.
nodes.find(childId) == newTree.
nodes.end())
continue;
548 for(StateSet::Iterator sit = newTree.
nodes[childId].stateLabel.Begin();
549 sit != newTree.
nodes[childId].stateLabel.End(); ++sit) {
550 unionOfChildren.
Insert(*sit);
555 FD_DF(
"Red breakpoint at node " << nodeId);
559 std::vector<Idx> descendants;
562 if(newTree.
nodes.find(child) != newTree.
nodes.end()) {
567 while(!bfs.empty()) {
568 Idx current = bfs.front();
570 descendants.push_back(current);
572 if(newTree.
nodes.find(current) == newTree.
nodes.end())
continue;
573 for(
Idx child : newTree.
nodes[current].children) {
574 if(newTree.
nodes.find(child) != newTree.
nodes.end()) {
580 for(
Idx descendant : descendants) {
582 deletedInThisStep.insert(nodeNumber);
597 for(
auto& pair : newTree.
nodes) {
598 Idx nodeId = pair.first;
602 FD_DF(
"Green coloring for node " << nodeId <<
" (number " << node.
nodeNumber <<
")");
611 std::set<int> redNodeNumbers;
612 for(
auto& pair : newTree.
nodes) {
614 redNodeNumbers.insert(pair.second.nodeNumber);
618 for(
auto& pair : newTree.
nodes) {
620 for(
int redNodeNumber : redNodeNumbers) {
621 pair.second.rSet.insert(redNodeNumber);
633 auto stateIt = treeSignatureToEnhancedState.find(treeSig);
634 if(stateIt != treeSignatureToEnhancedState.end()) {
636 targetEnhancedState = stateIt->second;
637 FD_DF(
"Found existing enhanced state " << targetEnhancedState.
ToString() <<
" for tree");
641 enhancedStateToTree[targetEnhancedState] = newTree;
642 treeSignatureToEnhancedState[treeSig] = targetEnhancedState;
644 stateQueue.push(targetEnhancedState);
647 FD_DF(
"Created new enhanced state " << targetEnhancedState.
ToString() <<
" for tree");
655 if(stateCounter >= MAX_STATES) {
656 FD_DF(
"Warning: Reached maximum state limit of " << MAX_STATES);
659 if(iterationCounter >= MAX_ITERATIONS) {
660 FD_DF(
"Warning: Reached maximum iteration limit of " << MAX_ITERATIONS);
670 for(
int nodeNumber = 1; nodeNumber <= N; ++nodeNumber) {
675 for(
const auto& enhancedStatePair : enhancedStateToTree) {
676 const EnhancedState& enhancedState = enhancedStatePair.first;
677 const LabeledTree& tree = enhancedStatePair.second;
713 outputRabinPairs.
Insert(newPair);
715 FD_DF(
"Created Rabin pair for node " << nodeNumber
716 <<
": R=" << Rn.
Size() <<
" states, I=" << In.
Size() <<
" states");
722 FD_DF(
"PseudoDet completed with "
723 << stateCounter <<
" states and "
724 << outputRabinPairs.
Size() <<
" Rabin pairs");
734 FD_DF(
"RemoveEps(" << rGen.
Name() <<
") - Two-phase approach");
739 std::string eventName = rGen.
EventName(*evIt);
740 if(eventName ==
"eps") {
747 FD_DF(
"No epsilon event found, copying automaton as-is");
761 Idx sourceState = *sit;
763 std::vector<Transition> nonEpsOutgoing;
764 std::vector<Transition> epsNonSelfLoop;
769 if(tit->Ev == epsEvent) {
770 if(tit->X1 != tit->X2) {
771 epsNonSelfLoop.push_back(*tit);
775 nonEpsOutgoing.push_back(*tit);
780 if(nonEpsOutgoing.empty() && epsNonSelfLoop.size() == 1) {
781 Idx targetState = epsNonSelfLoop[0].X2;
783 FD_DF(
"State " << sourceState <<
" has only eps transition to "
784 << targetState <<
" - relinking all inputs");
787 std::vector<Transition> incomingTrans;
790 if(tit->X2 == sourceState) {
791 incomingTrans.push_back(*tit);
796 for(
const auto& incoming : incomingTrans) {
797 FD_DF(
"Relinking " << incoming.X1 <<
" --"
799 << sourceState <<
" to " << incoming.X1
801 <<
"--> " << targetState);
819 FD_DF(
"Redirected initial state from " << sourceState <<
" to " << targetState);
826 FD_DF(
"Redirected marked state from " << sourceState <<
" to " << targetState);
833 for(RabinAcceptance::Iterator rit = currentRabin.
Begin(); rit != currentRabin.
End(); ++rit) {
838 if(newR.
Exists(sourceState)) {
839 newR.
Erase(sourceState);
844 if(newI.
Exists(sourceState)) {
845 newI.
Erase(sourceState);
850 newPair.
RSet() = newR;
851 newPair.
ISet() = newI;
864 FD_DF(
"Phase 2: Removing all eps self-loops");
866 std::vector<Transition> selfLoopsToRemove;
868 if(tit->Ev == epsEvent && tit->X1 == tit->X2) {
869 selfLoopsToRemove.push_back(*tit);
873 for(
const auto& selfLoop : selfLoopsToRemove) {
874 FD_DF(
"Removing eps self-loop at state " << selfLoop.X1);
880 std::queue<Idx> stateQueue;
884 if(!reachableStates.
Exists(*sit)) {
885 reachableStates.
Insert(*sit);
886 stateQueue.push(*sit);
891 while(!stateQueue.empty()) {
892 Idx current = stateQueue.front();
897 if(!reachableStates.
Exists(tit->X2)) {
898 reachableStates.
Insert(tit->X2);
899 stateQueue.push(tit->X2);
907 if(!reachableStates.
Exists(*sit)) {
908 statesToRemove.
Insert(*sit);
912 for(StateSet::Iterator sit = statesToRemove.
Begin(); sit != statesToRemove.
End(); ++sit) {
914 FD_DF(
"Removed unreachable state " << *sit);
918 bool hasEpsTransitions =
false;
920 if(tit->Ev == epsEvent) {
921 hasEpsTransitions =
true;
927 if(!hasEpsTransitions) {
930 if(*evIt != epsEvent) {
931 newAlphabet.
Insert(*evIt);
935 FD_DF(
"Removed eps from alphabet");
944 if(finalStates.
Empty()) {
945 FD_DF(
"Warning: No states remaining after eps removal");
949 std::map<Idx, Idx> renumberMapping;
951 for(StateSet::Iterator sit = finalStates.
Begin(); sit != finalStates.
End(); ++sit) {
952 renumberMapping[*sit] = newStateId++;
955 FD_DF(
"Renumbering states:");
956 for(
auto& pair : renumberMapping) {
957 FD_DF(
" " << pair.first <<
" -> " << pair.second);
966 for(
auto& pair : renumberMapping) {
982 tempResult.
SetTransition(renumberMapping[tit->X1], tit->Ev, renumberMapping[tit->X2]);
989 for(RabinAcceptance::Iterator rit = originalRabin.
Begin(); rit != originalRabin.
End(); ++rit) {
992 for(StateSet::Iterator sit = rit->RSet().Begin(); sit != rit->RSet().End(); ++sit) {
993 if(renumberMapping.find(*sit) != renumberMapping.end()) {
994 newR.
Insert(renumberMapping[*sit]);
998 for(StateSet::Iterator sit = rit->ISet().Begin(); sit != rit->ISet().End(); ++sit) {
999 if(renumberMapping.find(*sit) != renumberMapping.end()) {
1000 newI.
Insert(renumberMapping[*sit]);
1006 newPair.
RSet() = newR;
1007 newPair.
ISet() = newI;
1008 newRabin.
Insert(newPair);
1017 FD_DF(
"RemoveEps completed using two-phase approach:");
1018 FD_DF(
" Result: " << rRes.
Size() <<
" states (renumbered 1 to " << rRes.
Size() <<
"), "
Idx originalState
Original state ID.
EnhancedState()
Default constructor.
bool operator==(const EnhancedState &other) const
Equality operator.
std::set< int > deletedNodesInPrevStep
Node numbers deleted in previous step.
bool operator<(const EnhancedState &other) const
Comparison operator.
std::string ToString() const
Debug string representation.
virtual const char * What() const
const std::string & Name(void) const
Idx createNode()
Create a new node with auto-assigned number, return its ID.
Idx nextNodeId
Next available node ID.
std::set< int > deletedNodeNumbers
Node numbers deleted in this step.
int getNodeNumber(Idx nodeId) const
Get node number from ID.
std::map< int, Idx > numberToId
Node number -> ID mapping.
std::map< Idx, int > idToNumber
ID -> node number mapping.
Idx getNodeId(int nodeNumber) const
Get node ID from number.
Idx createNodeWithNumber(int nodeNumber)
Create a new node with specific number, return its ID.
bool hasNodeNumber(int nodeNumber) const
Check if node number exists in tree.
static const Idx INVALID_NODE
Invalid node constant.
Idx rootNode
Root node ID.
void deleteNode(Idx nodeId)
Delete a node and clean up references.
std::string ToString() const
Debug string representation.
LabeledTree()
Default constructor.
std::vector< bool > nodeNumberUsed
Track which node numbers are used.
std::map< Idx, TreeNode > nodes
Tree nodes (ID -> node)
int maxNodeCount
Maximum number of nodes (N)
bool operator==(const LabeledTree &other) const
Equality operator.
bool operator<(const LabeledTree &other) const
Comparison operator for ordering.
bool Insert(const Idx &rIndex)
virtual void Insert(const T &rElem)
TBaseSet< Transition, TransSort::X1EvX2 >::Iterator Iterator
const TaEventSet< EventAttr > & Alphabet(void) const
bool SetTransition(Idx x1, Idx ev, Idx x2)
void InjectAlphabet(const EventSet &rNewalphabet)
void RabinAcceptance(const faudes::RabinAcceptance &rRabAcc)
TreeNode()
Default constructor.
std::string ToString() const
Debug string representation.
bool operator<(const TreeNode &other) const
Comparison operator for ordering.
bool operator==(const TreeNode &other) const
Equality operator.
std::vector< Idx > children
child nodes
int nodeNumber
Fixed node number (1 to N)
enum faudes::TreeNode::Color color
std::set< int > rSet
R-set (using node numbers 1..N)
StateSet stateLabel
S: state label.
std::set< int > aSet
A-set (using node numbers 1..N)
std::string ToString(const std::string &rLabel="", const Type *pContext=0) const
StateSet::Iterator StatesBegin(void) const
StateSet::Iterator InitStatesBegin(void) const
TransSet::Iterator TransRelBegin(void) const
void ClrTransition(Idx x1, Idx ev, Idx x2)
void ClrMarkedState(Idx index)
EventSet::Iterator AlphabetBegin(void) const
bool ExistsTransition(const std::string &rX1, const std::string &rEv, const std::string &rX2) const
void SetInitState(Idx index)
StateSet::Iterator MarkedStatesBegin(void) const
StateSet::Iterator StatesEnd(void) const
void ClrInitState(Idx index)
TransSet::Iterator TransRelEnd(void) const
StateSet::Iterator MarkedStatesEnd(void) const
void SetMarkedState(Idx index)
StateSet::Iterator InitStatesEnd(void) const
Idx TransRelSize(void) const
std::string EventName(Idx index) const
EventSet::Iterator AlphabetEnd(void) const
bool ExistsInitState(Idx index) const
bool ExistsMarkedState(Idx index) const
bool Exists(const T &rElem) const
Iterator Begin(void) const
virtual bool Erase(const T &rElem)
void PseudoDet(const RabinAutomaton &rGen, RabinAutomaton &rRes)
std::string ComputeTreeSignature(const LabeledTree &tree, const std::set< int > &deletedNodes)
void RemoveEps(const RabinAutomaton &rGen, RabinAutomaton &rRes)
std::string ToStringInteger(Int number)
std::string CollapsString(const std::string &rString, unsigned int len)