-
Notifications
You must be signed in to change notification settings - Fork 0
/
GotIter.C
124 lines (113 loc) · 2.31 KB
/
GotIter.C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
#include "GotIter.h"
GotIter::
GotIter(Edge* edge) : whereIam( edge )
{}
bool
GotIter::
next(Item*& itm)
{
// wul: whereIam记录当前的edge,每个edge本身有pred成员记录前一个edge
if(!whereIam || !whereIam->item()) return false;
else
{
itm = whereIam->item();
whereIam = whereIam->pred();
return true;
}
}
LeftRightGotIter::
LeftRightGotIter(Edge* edge)
{
// wul: 初始化,即构建iter内部的列表
makelrgi(edge);
}
void
LeftRightGotIter::
makelrgi(Edge* ri)
{
// wul: 先要借助基本的Iter(实现next接口)
GotIter gi(ri);
Item* itm;
bool finishedRight = false;
int spos = ri->start();
/* gotiter return a b head c d in the order d c a b head */
list<Item*>::iterator lri;
list<Item*> lrlist;
while(gi.next(itm))
{
//cerr << "lrgi " << *itm << endl;
if(finishedRight || itm->start() == spos)
{
// if 1st consits is STOP(3, 3) then next can have same start pos.
if(itm->start() == spos && !finishedRight)
{
finishedRight = true;
lri = lrlist.begin();
}
lri = lrlist.insert(lri, itm);
lri++;
}
else lrlist.push_front(itm);
}
lri = lrlist.begin();
int i = 0;
for( ; lri != lrlist.end() ; lri++)
{
assert(i < 127);
lrarray[i] = (*lri);
i++;
}
size_ = i;
pos_ = 0;
}
bool
LeftRightGotIter::
next(Item*& itm)
{
if(pos_ >= size_) return false;
itm = lrarray[pos_];
pos_++;
return true;
}
bool
SuccessorIter::
next(Edge*& edge)
{
if(edgeIter == edge_->sucs_.end()) return false;
edge = *edgeIter;
//cerr << "Si: " << *edge_ << " has " << *edge << endl;
edgeIter++;
return true;
}
NeedmeIter::
NeedmeIter(Item* itm)
{
stackptr = -1;
//cerr << "nmi for " << *itm << endl;
list<Edge*>::iterator eiter = itm->needme().begin();
for( ; eiter != itm->needme().end() ; eiter++)
{
stackptr++;
assert(stackptr < 64000); //was 32;
stack[stackptr] = *eiter;
}
}
bool
NeedmeIter::
next(Edge*& e)
{
if(stackptr < 0 ) return false;
e = stack[stackptr];
//cerr << "nminext = " << *e << endl;
stackptr--;
SuccessorIter si(e);
Edge* suc;
while(si.next(suc))
{
stackptr++;
assert(stackptr < 64000); //was 32.
//cerr << "nmisuc " << *suc << endl;
stack[stackptr] = suc;
}
return true;
}